本文共 3858 字,大约阅读时间需要 12 分钟。
导读: 写 ActiveX 控件有时会实现一些 Picture 类型的属性,或者在方法中传递 Picture 类型的参数。在 MFC 里,有一个名为 CPictureHolder 的类可以很方便的帮助程序员做这些工作,但是如果你使用 ATL 或者 BaseCtl 框架开发,则需要自己动手。故把 MFC 里的?CPictureHolder 类抽了出来,使之没有对 MFC 的依赖,以供来者用之。文件名为 picholder.h。 #ifndef __PICHOLDER_H__ #define __PICHOLDER_H__ /* Demo code: 1. IDL code [id(1)] HRESULT GetPicture([out, retval] LPPICTUREDISP *pVal); [id(2)] HRESULT SetPicture([in] LPPICTUREDISP newVal); 2. C++ code CPictureHolder m_pic; STDMETHOD(GetPicture)(LPPICTUREDISP *pVal) { LPPICTUREDISP pPic = m_pic.GetPictureDispatch(); if(pPic != NULL) *pVal = pPic; return pPic ? S_OK : E_FAIL; } STDMETHOD(SetPicture)(LPPICTUREDISP newVal) { m_pic.SetPictureDispatch(newVal); return S_OK; } Note: When you compile an .idl file with IFontDisp or IPictureDisp as parameters of methods in Visual C++ 5.0 or Visual C++ 6.0, you get a MIDL2039 warning. This is due to a bug in Ocidl.idl source. You must add the dual attribute to the interface declarations for IFontDisp and IPictureDisp. Microsoft has confirmed this to be a bug. This problem was corrected in Microsoft Visual C++ .NET. // */ #ifndef ASSERT #ifdef ATLASSERT #define ASSERT ATLASSERT #else #define ASSERT sizeof #endif // ATLASSERT #endif // ASSERT __inline DWORD _Release(LPUNKNOWN* lplpUnknown) { ASSERT(lplpUnknown != NULL); if(*lplpUnknown != NULL) { DWORD dwRef = (*lplpUnknown)->Release(); *lplpUnknown = NULL; return dwRef; } return 0; } #define RELEASE(lpUnk) _Release((LPUNKNOWN*)&lpUnk) class CPictureHolder { public: LPPICTURE m_pPict; public: CPictureHolder() : m_pPict(NULL) { } ~CPictureHolder() { RELEASE(m_pPict); } BOOL CreateEmpty() { RELEASE(m_pPict); PICTDESC pdesc; pdesc.cbSizeofstruct = sizeof(pdesc); pdesc.picType = PICTYPE_NONE; return SUCCEEDED(::OleCreatePictureIndirect(&pdesc, IID_IPicture, FALSE, (LPVOID*)&m_pPict)); } BOOL CreateFromBitmap(HBITMAP hbm, HPALETTE hpal = NULL, BOOL bTransferOwnership = FALSE) { RELEASE(m_pPict); PICTDESC pdesc; pdesc.cbSizeofstruct = sizeof(pdesc); pdesc.picType = PICTYPE_BITMAP; pdesc.bmp.hbitmap = hbm; pdesc.bmp.hpal = hpal; return SUCCEEDED(::OleCreatePictureIndirect(&pdesc, IID_IPicture, bTransferOwnership, (LPVOID*)&m_pPict)); } BOOL CreateFromMetafile(HMETAFILE hmf, int xExt, int yExt, BOOL bTransferOwnership = FALSE) { RELEASE(m_pPict); PICTDESC pdesc; pdesc.cbSizeofstruct = sizeof(pdesc); pdesc.picType = PICTYPE_METAFILE; pdesc.wmf.hmeta = hmf; pdesc.wmf.xExt = xExt; pdesc.wmf.yExt = yExt; return SUCCEEDED(::OleCreatePictureIndirect(&pdesc, IID_IPicture, bTransferOwnership, (LPVOID*)&m_pPict)); } BOOL CreateFromIcon(HICON hIcon, BOOL bTransferOwnership = FALSE) { RELEASE(m_pPict); PICTDESC pdesc; pdesc.cbSizeofstruct = sizeof(pdesc); pdesc.picType = PICTYPE_ICON; pdesc.icon.hicon = hIcon; return SUCCEEDED(::OleCreatePictureIndirect(&pdesc, IID_IPicture, bTransferOwnership, (LPVOID*)&m_pPict)); } LPPICTUREDISP GetPictureDispatch() { LPPICTUREDISP pPictDisp = NULL; if((m_pPict != NULL) &&SUCCEEDED(m_pPict->QueryInterface(IID_IPictureDisp, (LPVOID*)&pPictDisp))) { ASSERT(pPictDisp != NULL); } return pPictDisp; } void SetPictureDispatch(LPPICTUREDISP pDisp) { LPPICTURE pPict = NULL; if(m_pPict != NULL) m_pPict->Release(); if((pDisp != NULL) &&SUCCEEDED(pDisp->QueryInterface(IID_IPicture, (LPVOID*)&pPict))) { ASSERT(pPict != NULL); m_pPict = pPict; } else { m_pPict = NULL; } } void Render(HDC hdc, const RECT& rcRender, const RECT& rcWBounds) { if(m_pPict != NULL) { long hmWidth; long hmHeight; m_pPict->get_Width(&hmWidth); m_pPict->get_Height(&hmHeight); m_pPict->Render(hdc, rcRender.left, rcRender.top, rcRender.right - rcRender.left, rcRender.bottom - rcRender.top, 0, hmHeight-1, hmWidth, -hmHeight, &rcWBounds); } } short GetType() { short sPicType = (short)PICTYPE_UNINITIALIZED; if(m_pPict != NULL) { m_pPict->get_Type(&sPicType); } return sPicType; } }; #endif // __PICHOLDER_H__ 本文转自转载地址:http://iciob.baihongyu.com/