bullseye.cpp
来自「《ATL深入解析》随书源码」· C++ 代码 · 共 718 行 · 第 1/2 页
CPP
718 行
// BullsEye.cpp : Implementation of CBullsEye
#include "stdafx.h"
#include "BullsEyeCtl.h"
#include "BullsEye.h"
#include "ocidl.h" // Added by ClassView
#include "AboutDlg.h"
/////////////////////////////////////////////////////////////////////////////
// CBullsEyeLicense class static member variables
// {956FC2C2-5AF8-11d2-BD05-00A0C9C8E50D}
const GUID CBullsEyeLicense::RunTimeLicenseKey =
{ 0x956fc2c2, 0x5af8, 0x11d2, { 0xbd, 0x5, 0x0, 0xa0, 0xc9, 0xc8, 0xe5, 0xd } };
HRESULT SetStrings(/*[in*/ ULONG cElems, /*[in]*/ const LPCOLESTR* rgpsz, /*[out]*/ CALPOLESTR* pStrings);
HRESULT SetCookies(/*[in*/ ULONG cElems, /*[in*/ const DWORD* pdwCookies, /*[out]*/ CADWORD* pcaCookies);
/////////////////////////////////////////////////////////////////////////////
// CBullsEye class construction, initialization and desruction
CLIPFORMAT CBullsEye::m_cfEmbeddedObject;
CLIPFORMAT CBullsEye::m_cfObjectDescriptor;
/***************/
/* Constructor */
/***************/
CBullsEye::CBullsEye()
{
// Stock properties
m_nBackStyle = 0; // Opaque = 0, Transparent = 1
m_nBorderStyle = 0; // No border = 0, Fixed single = 1
m_nBorderWidth = 1;
m_clrBackColor = RGB (255,255,255);
m_clrForeColor = RGB ( 0, 0, 0);
m_bEnabled = TRUE;
// Custom properties
m_clrAlternateColor = RGB ( 0, 0, 0);
m_clrCenterColor = RGB (255, 0, 0);
m_beep = VARIANT_TRUE;
// Control state
m_alternateBrush = NULL;
m_backBrush = NULL;
m_centerBrush = NULL;
m_borderPen = NULL;
m_nAppearance = 0;
m_bAmbientsFetched = false;
}
/******************/
/* FinalConstruct */
/******************/
HRESULT CBullsEye::FinalConstruct ()
{
FreezeEvents (TRUE);
put_RingCount (5);
FreezeEvents (FALSE);
return S_OK;
}
/**************/
/* Destructor */
/**************/
CBullsEye::~CBullsEye()
{
if (m_alternateBrush) ::DeleteObject (m_alternateBrush);
if (m_backBrush) ::DeleteObject (m_backBrush);
if (m_centerBrush) ::DeleteObject (m_centerBrush);
if (m_borderPen) ::DeleteObject (m_borderPen);
}
/////////////////////////////////////////////////////////////////////////////
// IPerPropertyBrowsing method overrides
/********************/
/* GetDisplayString */
/********************/
STDMETHODIMP CBullsEye::GetDisplayString(DISPID dispid,BSTR *pBstr)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::GetDisplayString\n"));
switch (dispid) {
case DISPID_BEEP:
if (VARIANT_TRUE == m_beep)
*pBstr = SysAllocString (OLESTR("Yes"));
else
*pBstr = SysAllocString (OLESTR("No"));
return *pBstr ? S_OK : E_OUTOFMEMORY;
case DISPID_BACKSTYLE:
if (1 == m_nBackStyle)
*pBstr = SysAllocString (OLESTR("Opaque"));
else
*pBstr = SysAllocString (OLESTR("Transparent"));
return *pBstr ? S_OK : E_OUTOFMEMORY;
case DISPID_ALTERNATECOLOR: // Make Visual Basic apply default formatting
case DISPID_BACKCOLOR: // for these color properties
case DISPID_CENTERCOLOR: // Otherwise it displays color values in decimal
case DISPID_FORECOLOR: // and doesn't draw the color sample correctly
case DISPID_RINGCOUNT:
return S_FALSE; // This is an undocumented return value that works...
}
return IPerPropertyBrowsingImpl<CBullsEye>::GetDisplayString(dispid, pBstr);
}
/*********************/
/* MapPropertyToPage */
/*********************/
STDMETHODIMP CBullsEye::MapPropertyToPage(DISPID dispid, CLSID *pClsid)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::MapPropertyToPage\n"));
// Look up the property page CLSID in the PROP MAP
HRESULT hr = IPerPropertyBrowsingImpl<CBullsEye>::MapPropertyToPage(dispid, pClsid);
// When there is no property page for a listed property, fail the call
if (SUCCEEDED(hr) && CLSID_NULL == *pClsid) hr = E_INVALIDARG;
return hr;
}
/************************/
/* GetPredefinedStrings */
/************************/
#define DIM(a) (sizeof(a)/sizeof(a[0]))
static const LPCOLESTR rszBeepStrings [] = { OLESTR("Yes, make noise"), OLESTR("No, be mute") };
static const DWORD rdwBeepCookies [] = { 0, 1 };
static const VARIANT_BOOL rvbBeepValues [] = { VARIANT_TRUE, VARIANT_FALSE };
static const UINT cBeepStrings = DIM(rszBeepStrings);
static const UINT cBeepCookies = DIM(rdwBeepCookies);
static const UINT cBeepValues = DIM(rvbBeepValues);
static const LPCOLESTR rszBackStyleStrings [] = { OLESTR("Opaque"), OLESTR("Transparent") };
static const DWORD rdwBackStyleCookies [] = { 0, 1 };
static const long rvbBackStyleValues [] = { 1, 0 };
static const UINT cBackStyleStrings = DIM(rszBackStyleStrings);
static const UINT cBackStyleCookies = DIM(rdwBackStyleCookies);
static const UINT cBackStyleValues = DIM(rvbBackStyleValues);
STDMETHODIMP CBullsEye::GetPredefinedStrings(/*[in]*/ DISPID dispid, /*[out]*/ CALPOLESTR *pcaStringsOut, /*[out]*/ CADWORD *pcaCookiesOut)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::GetPredefinedStrings\n"));
if (NULL == pcaStringsOut || NULL == pcaCookiesOut) return E_POINTER;
ATLASSERT (cBeepStrings == cBeepCookies);
ATLASSERT (cBeepStrings == cBeepValues);
ATLASSERT (cBackStyleStrings == cBackStyleCookies);
ATLASSERT (cBackStyleStrings == cBackStyleValues);
pcaStringsOut->cElems = 0;
pcaStringsOut->pElems = NULL;
pcaCookiesOut->cElems = 0;
pcaCookiesOut->pElems = NULL;
HRESULT hr = S_OK;
switch (dispid) {
case DISPID_BEEP:
hr = SetStrings (cBeepValues, rszBeepStrings, pcaStringsOut);
if (FAILED (hr)) return hr;
return SetCookies (cBeepValues, rdwBeepCookies, pcaCookiesOut);
case DISPID_BACKSTYLE:
hr = SetStrings (cBackStyleValues, rszBackStyleStrings, pcaStringsOut);
if (FAILED (hr)) return hr;
return SetCookies (cBackStyleValues, rdwBackStyleCookies, pcaCookiesOut);
}
return IPerPropertyBrowsingImpl<CBullsEye>::GetPredefinedStrings(dispid, pcaStringsOut, pcaCookiesOut);
}
/**********************/
/* GetPredefinedValue */
/**********************/
STDMETHODIMP CBullsEye::GetPredefinedValue(DISPID dispid, DWORD dwCookie, VARIANT* pVarOut)
{
if (NULL == pVarOut) return E_POINTER;
ULONG i;
switch (dispid) {
case DISPID_BEEP:
// Walk through cookie array looking for matching value
for (i = 0; i < cBeepCookies; i++) {
if (rdwBeepCookies[i] == dwCookie) {
pVarOut->vt = VT_BOOL;
pVarOut->boolVal = rvbBeepValues [i];
return S_OK;
}
}
return E_INVALIDARG;
case DISPID_BACKSTYLE:
// Walk through cookie array looking for matching value
for (i = 0; i < cBackStyleCookies; i++) {
if (rdwBackStyleCookies[i] == dwCookie) {
pVarOut->vt = VT_I4;
pVarOut->lVal = rvbBackStyleValues [i];
return S_OK;
}
}
return E_INVALIDARG;
}
return IPerPropertyBrowsingImpl<CBullsEye>::GetPredefinedValue(dispid, dwCookie, pVarOut);
}
/////////////////////////////////////////////////////////////////////////////
// ICategorizeProperties interface implementation
/*************************/
/* MapPropertyToCategory */
/*************************/
STDMETHODIMP CBullsEye::MapPropertyToCategory(/*[in]*/ DISPID dispid, /*[out]*/ PROPCAT* ppropcat)
{
if (NULL == ppropcat) return E_POINTER;
switch (dispid) {
case DISPID_FORECOLOR:
case DISPID_BACKCOLOR:
case DISPID_CENTERCOLOR:
case DISPID_ALTERNATECOLOR:
case DISPID_RINGCOUNT:
case DISPID_BACKSTYLE:
*ppropcat = PROPCAT_Appearance;
return S_OK;
case DISPID_BEEP:
case DISPID_ENABLED:
*ppropcat = PROPCAT_Behavior;
return S_OK;
case DISPID_RINGVALUE:
*ppropcat = PROPCAT_Scoring;
return S_OK;
default:
return E_FAIL;
}
}
/*******************/
/* GetCategoryName */
/*******************/
STDMETHODIMP CBullsEye::GetCategoryName(/*[in]*/ PROPCAT propcat, /*[in]*/ LCID lcid, /*[out]*/ BSTR* pbstrName)
{
if(PROPCAT_Scoring == propcat) {
*pbstrName = ::SysAllocString(L"Scoring");
return S_OK;
}
return E_FAIL;
}
/////////////////////////////////////////////////////////////////////////////
// IViewObjectExImpl method overrides
/*****************/
/* GetViewStatus */
/*****************/
STDMETHODIMP CBullsEye::GetViewStatus(DWORD* pdwStatus)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::GetViewStatus\n"));
*pdwStatus = m_nBackStyle == 1 ? // Opaque?
VIEWSTATUS_SOLIDBKGND | VIEWSTATUS_OPAQUE :
VIEWSTATUS_DVASPECTTRANSPARENT ;
return S_OK;
}
/*****************/
/* QueryHitPoint */
/*****************/
STDMETHODIMP CBullsEye::QueryHitPoint(DWORD dwAspect, LPCRECT pRectBounds, POINT ptlLoc, LONG /* lCloseHint */, DWORD *pHitResult)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::QueryHitPoint\n"));
switch (dwAspect) {
case DVASPECT_CONTENT:
case DVASPECT_OPAQUE:
case DVASPECT_TRANSPARENT:
// Compute point relative to control's origin
CPoint pt (ptlLoc.x - pRectBounds->left, ptlLoc.y - pRectBounds->top);
if (-1 != HitTest (pt))
*pHitResult = HITRESULT_HIT;
else
*pHitResult = HITRESULT_OUTSIDE;
return S_OK;
}
ATLTRACE2(atlTraceControls,2,_T("Wrong DVASPECT\n"));
return E_FAIL;
}
/****************/
/* QueryHitRect */
/****************/
STDMETHODIMP CBullsEye::QueryHitRect(DWORD dwAspect, LPCRECT pRectBounds, LPCRECT prcLoc, LONG /* lCloseHint */, DWORD* pHitResult)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::QueryHitRect\n"));
switch (dwAspect) {
case DVASPECT_CONTENT:
case DVASPECT_OPAQUE:
case DVASPECT_TRANSPARENT:
RECT rc;
*pHitResult = UnionRect(&rc, pRectBounds, prcLoc) ? HITRESULT_HIT : HITRESULT_OUTSIDE;
return S_OK;
}
ATLTRACE2(atlTraceControls,2,_T("Wrong DVASPECT\n"));
return E_FAIL;
}
/////////////////////////////////////////////////////////////////////////////
// IDataObject method overrides
/****************/
/* QueryGetData */
/****************/
STDMETHODIMP CBullsEye::QueryGetData(FORMATETC* pformatetc)
{
ATLTRACE2(atlTraceControls,2,_T("CBullsEye::QueryGetData\n"));
if (NULL == pformatetc) return E_POINTER;
if (pformatetc->lindex != -1) return DV_E_LINDEX;
if ((pformatetc->tymed & TYMED_MFPICT) == 0) return DV_E_TYMED ;
if (pformatetc->dwAspect != DVASPECT_CONTENT) return DV_E_DVASPECT;
return S_OK;
}
/*****************/
/* EnumFormatEtc */
/*****************/
STDMETHODIMP CBullsEye::EnumFormatEtc(DWORD dwDirection, IEnumFORMATETC** ppenumFormatEtc)
{
static FORMATETC array[] = {
{ CF_METAFILEPICT, NULL, DVASPECT_CONTENT, -1, TYMED_MFPICT }, };
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?