ctlobj.cpp 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427
  1. // This is a part of the Microsoft Foundation Classes C++ library.
  2. // Copyright (C) 1992-1998 Microsoft Corporation
  3. // All rights reserved.
  4. //
  5. // This source code is only intended as a supplement to the
  6. // Microsoft Foundation Classes Reference and related
  7. // electronic documentation provided with the library.
  8. // See these sources for detailed information regarding the
  9. // Microsoft Foundation Classes product.
  10. #include "stdafx.h"
  11. #ifdef AFXCTL_CORE2_SEG
  12. #pragma code_seg(AFXCTL_CORE2_SEG)
  13. #endif
  14. #ifdef _DEBUG
  15. #undef THIS_FILE
  16. static char THIS_FILE[] = __FILE__;
  17. #endif
  18. #define new DEBUG_NEW
  19. /////////////////////////////////////////////////////////////////////////////
  20. // COleControl::XOleObject
  21. STDMETHODIMP_(ULONG) COleControl::XOleObject::AddRef()
  22. {
  23. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  24. return (ULONG)pThis->ExternalAddRef();
  25. }
  26. STDMETHODIMP_(ULONG) COleControl::XOleObject::Release()
  27. {
  28. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  29. return (ULONG)pThis->ExternalRelease();
  30. }
  31. STDMETHODIMP COleControl::XOleObject::QueryInterface(
  32. REFIID iid, LPVOID* ppvObj)
  33. {
  34. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  35. return (HRESULT)pThis->ExternalQueryInterface(&iid, ppvObj);
  36. }
  37. STDMETHODIMP COleControl::XOleObject::SetClientSite(LPOLECLIENTSITE pClientSite)
  38. {
  39. METHOD_PROLOGUE_EX(COleControl, OleObject)
  40. ASSERT_NULL_OR_POINTER(pClientSite, IOleClientSite);
  41. // maintain reference counts
  42. if (pClientSite != NULL)
  43. pClientSite->AddRef();
  44. RELEASE(pThis->m_pClientSite);
  45. pThis->m_pClientSite = pClientSite;
  46. // Release existing pointer to ambient property dispinterface.
  47. pThis->m_ambientDispDriver.ReleaseDispatch();
  48. if (pClientSite != NULL)
  49. {
  50. BOOL bValue;
  51. pThis->m_bAutoClip =
  52. pThis->GetAmbientProperty(DISPID_AMBIENT_AUTOCLIP, VT_BOOL, &bValue) ? bValue : 0;
  53. pThis->m_bMsgReflect =
  54. pThis->GetAmbientProperty(DISPID_AMBIENT_MESSAGEREFLECT, VT_BOOL, &bValue) ? bValue : 0;
  55. pThis->m_bUIDead = (BYTE)(pThis->AmbientUIDead());
  56. }
  57. // Release existing pointer to in-place site, if any.
  58. RELEASE(pThis->m_pInPlaceSite);
  59. // Initialize pointer to control site
  60. LPVOID pInterface;
  61. if (pClientSite == NULL ||
  62. FAILED(pClientSite->QueryInterface(IID_IOleControlSite, &pInterface)))
  63. {
  64. pInterface = NULL;
  65. }
  66. RELEASE(pThis->m_pControlSite);
  67. pThis->m_pControlSite = (LPOLECONTROLSITE) pInterface;
  68. // Initialize pointer to simple frame site
  69. if (pClientSite == NULL || !pThis->m_bSimpleFrame ||
  70. FAILED(pClientSite->QueryInterface(IID_ISimpleFrameSite, &pInterface)))
  71. {
  72. pInterface = NULL;
  73. }
  74. RELEASE(pThis->m_pSimpleFrameSite);
  75. pThis->m_pSimpleFrameSite = (LPSIMPLEFRAMESITE) pInterface;
  76. // Let the control run its own code here.
  77. pThis->OnSetClientSite();
  78. // Unless IPersist*::Load or IPersist*::InitNew is called after this,
  79. // we can't count on ambient properties being available while loading.
  80. pThis->m_bCountOnAmbients = FALSE;
  81. return S_OK;
  82. }
  83. STDMETHODIMP COleControl::XOleObject::GetClientSite(LPOLECLIENTSITE* ppClientSite)
  84. {
  85. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  86. ASSERT_POINTER(ppClientSite, LPOLECLIENTSITE);
  87. LPOLECLIENTSITE pClientSite = pThis->m_pClientSite;
  88. *ppClientSite = pClientSite;
  89. if (pClientSite != NULL)
  90. pClientSite->AddRef();
  91. return (pClientSite != NULL) ? S_OK : E_FAIL;
  92. }
  93. STDMETHODIMP COleControl::XOleObject::SetHostNames(LPCOLESTR, LPCOLESTR)
  94. {
  95. return S_OK;
  96. }
  97. STDMETHODIMP COleControl::XOleObject::Close(DWORD dwSaveOption)
  98. {
  99. METHOD_PROLOGUE_EX(COleControl, OleObject)
  100. pThis->OnClose(dwSaveOption);
  101. return S_OK;
  102. }
  103. void COleControl::OnClose(DWORD dwSaveOption)
  104. {
  105. if (m_bInPlaceActive)
  106. m_xOleInPlaceObject.InPlaceDeactivate();
  107. if (((dwSaveOption == OLECLOSE_SAVEIFDIRTY) || (dwSaveOption == OLECLOSE_PROMPTSAVE)) &&
  108. m_bModified)
  109. {
  110. SendAdvise(OBJECTCODE_SAVEOBJECT);
  111. SendAdvise(OBJECTCODE_SAVED);
  112. }
  113. }
  114. STDMETHODIMP COleControl::XOleObject::SetMoniker(DWORD, LPMONIKER)
  115. {
  116. return E_NOTIMPL;
  117. }
  118. STDMETHODIMP COleControl::XOleObject::GetMoniker(DWORD, DWORD, LPMONIKER*)
  119. {
  120. return E_NOTIMPL;
  121. }
  122. STDMETHODIMP COleControl::XOleObject::InitFromData(LPDATAOBJECT, BOOL, DWORD)
  123. {
  124. return E_NOTIMPL;
  125. }
  126. STDMETHODIMP COleControl::XOleObject::GetClipboardData(DWORD, LPDATAOBJECT*)
  127. {
  128. return E_NOTIMPL;
  129. }
  130. STDMETHODIMP COleControl::XOleObject::DoVerb(LONG iVerb, LPMSG lpmsg,
  131. LPOLECLIENTSITE pActiveSite, LONG lindex, HWND hwndParent,
  132. LPCRECT lprcPosRect)
  133. {
  134. METHOD_PROLOGUE_EX(COleControl, OleObject)
  135. TRY
  136. {
  137. if (pThis->OnDoVerb(iVerb, lpmsg, hwndParent, lprcPosRect))
  138. return S_OK; // Custom verb succeeded
  139. }
  140. CATCH (CException, e)
  141. {
  142. return E_FAIL; // Custom verb failed
  143. }
  144. END_CATCH
  145. // Custom verb not found, invoke standard verb instead.
  146. HRESULT hr;
  147. switch (iVerb)
  148. {
  149. case OLEIVERB_HIDE:
  150. pThis->m_xOleInPlaceObject.UIDeactivate();
  151. return pThis->OnHide();
  152. case OLEIVERB_SHOW:
  153. return pThis->OnOpen(-1, lpmsg); // Try in-place first
  154. case OLEIVERB_UIACTIVATE:
  155. case OLEIVERB_INPLACEACTIVATE:
  156. #ifdef _AFXDLL
  157. if (pThis->m_bOpen)
  158. return OLE_E_NOT_INPLACEACTIVE; // Already open
  159. #endif
  160. // FALL THRU
  161. case OLEIVERB_PRIMARY:
  162. if (lprcPosRect != NULL)
  163. CopyRect(&pThis->m_rcPos, lprcPosRect);
  164. else
  165. memset(&pThis->m_rcPos, 0, sizeof(pThis->m_rcPos));
  166. return pThis->OnActivateInPlace((iVerb != OLEIVERB_INPLACEACTIVATE), lpmsg);
  167. #ifdef _AFXDLL
  168. case OLEIVERB_OPEN:
  169. return pThis->OnOpen(FALSE, lpmsg); // Don't try in-place
  170. #endif
  171. case OLEIVERB_PROPERTIES:
  172. return pThis->OnProperties(lpmsg, hwndParent, lprcPosRect) ?
  173. S_OK : E_FAIL;
  174. default:
  175. // negative verbs not understood should return E_NOTIMPL
  176. if (iVerb < 0)
  177. return E_NOTIMPL;
  178. // positive verb not processed --
  179. // according to OLE spec, primary verb should be executed
  180. // instead.
  181. if (SUCCEEDED(hr = DoVerb(OLEIVERB_PRIMARY, lpmsg, pActiveSite,
  182. lindex, hwndParent, lprcPosRect)))
  183. return OLEOBJ_S_INVALIDVERB;
  184. else
  185. return hr;
  186. }
  187. }
  188. BOOL COleControl::OnDoVerb(LONG iVerb, LPMSG lpMsg, HWND hWndParent,
  189. LPCRECT lpRect)
  190. {
  191. return DoOleVerb(iVerb, lpMsg, hWndParent, lpRect);
  192. }
  193. STDMETHODIMP COleControl::XOleObject::EnumVerbs(LPENUMOLEVERB* ppenumOleVerb)
  194. {
  195. METHOD_PROLOGUE_EX(COleControl, OleObject)
  196. return pThis->OnEnumVerbs(ppenumOleVerb) ?
  197. S_OK : OLEOBJ_E_NOVERBS;
  198. }
  199. BOOL COleControl::OnEnumVerbs(LPENUMOLEVERB* ppenumOleVerb)
  200. {
  201. return EnumOleVerbs(ppenumOleVerb);
  202. }
  203. STDMETHODIMP COleControl::XOleObject::Update()
  204. {
  205. return S_OK;
  206. }
  207. STDMETHODIMP COleControl::XOleObject::IsUpToDate()
  208. {
  209. return S_OK;
  210. }
  211. STDMETHODIMP COleControl::XOleObject::GetUserClassID(CLSID* pClsid)
  212. {
  213. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  214. return pThis->GetClassID(pClsid);
  215. }
  216. STDMETHODIMP COleControl::XOleObject::GetUserType(DWORD, LPOLESTR* ppszUserType)
  217. {
  218. METHOD_PROLOGUE_EX(COleControl, OleObject)
  219. UNUSED(ppszUserType); // not used in release builds
  220. ASSERT_POINTER(ppszUserType, LPOLESTR);
  221. TCHAR szUserType[256];
  222. pThis->GetUserType(szUserType);
  223. *ppszUserType = AfxAllocTaskOleString(szUserType);
  224. return S_OK;
  225. }
  226. void COleControl::GetUserType(LPTSTR pszUserType)
  227. {
  228. ASSERT(pszUserType != NULL);
  229. pszUserType[0] = '\0';
  230. TRY
  231. {
  232. AfxLoadString(GetUserTypeNameID(), pszUserType);
  233. }
  234. END_TRY
  235. }
  236. STDMETHODIMP COleControl::XOleObject::SetExtent(DWORD dwDrawAspect, LPSIZEL lpsizel)
  237. {
  238. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  239. if (dwDrawAspect & DVASPECT_CONTENT)
  240. return pThis->OnSetExtent(lpsizel) ? S_OK : E_FAIL;
  241. else
  242. return E_NOTIMPL;
  243. }
  244. BOOL COleControl::OnSetExtent(LPSIZEL lpSizeL)
  245. {
  246. if (m_bChangingExtent) // Prevent infinite recursion!
  247. return FALSE;
  248. m_bChangingExtent = TRUE;
  249. // Update the control's extent.
  250. m_cxExtent = lpSizeL->cx;
  251. m_cyExtent = lpSizeL->cy;
  252. // Mark the control dirty and force a repaint.
  253. SetModifiedFlag();
  254. InvalidateControl();
  255. SIZEL szlPixels;
  256. _AfxXformSizeInHimetricToPixels(NULL, lpSizeL, &szlPixels);
  257. CRect rectNew(m_rcPos);
  258. rectNew.right = rectNew.left + (int)szlPixels.cx;
  259. rectNew.bottom = rectNew.top + (int)szlPixels.cy;
  260. if ((m_pInPlaceSite != NULL) && m_bInPlaceActive)
  261. {
  262. // If the control is in-place active, tell the container to resize.
  263. m_pInPlaceSite->OnPosRectChange(&rectNew);
  264. }
  265. #ifdef _AFXDLL
  266. else if (m_bOpen)
  267. {
  268. // If the control is open, resize it.
  269. ResizeOpenControl((int)szlPixels.cx, (int)szlPixels.cy);
  270. }
  271. #endif
  272. else
  273. {
  274. CopyRect(m_rcPos, rectNew);
  275. // Resize off-screen window, if any.
  276. if (m_hWnd != NULL)
  277. ::SetWindowPos(m_hWnd, NULL, 0, 0, (int)szlPixels.cx,
  278. (int)szlPixels.cy, SWP_NOZORDER|SWP_NOMOVE|SWP_NOACTIVATE);
  279. }
  280. m_bChangingExtent = FALSE;
  281. return TRUE;
  282. }
  283. STDMETHODIMP COleControl::XOleObject::GetExtent(DWORD dwDrawAspect,
  284. LPSIZEL lpsizel)
  285. {
  286. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  287. if (dwDrawAspect & DVASPECT_CONTENT)
  288. {
  289. lpsizel->cx = pThis->m_cxExtent;
  290. lpsizel->cy = pThis->m_cyExtent;
  291. return S_OK;
  292. }
  293. return E_NOTIMPL;
  294. }
  295. STDMETHODIMP COleControl::XOleObject::Advise(LPADVISESINK pAdvSink,
  296. DWORD* pdwConnection)
  297. {
  298. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  299. // If no advise holder exists, create one.
  300. // Then delegate this call to the advise holder.
  301. if (pThis->m_pOleAdviseHolder == NULL)
  302. {
  303. HRESULT hr;
  304. if (FAILED(hr = CreateOleAdviseHolder(&pThis->m_pOleAdviseHolder)))
  305. return hr;
  306. }
  307. return pThis->m_pOleAdviseHolder->Advise(pAdvSink, pdwConnection);
  308. }
  309. STDMETHODIMP COleControl::XOleObject::Unadvise(DWORD dwConnection)
  310. {
  311. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  312. if (pThis->m_pOleAdviseHolder != NULL)
  313. return pThis->m_pOleAdviseHolder->Unadvise(dwConnection);
  314. return E_FAIL;
  315. }
  316. STDMETHODIMP COleControl::XOleObject::EnumAdvise(LPENUMSTATDATA* ppenumAdvise)
  317. {
  318. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  319. if (pThis->m_pOleAdviseHolder != NULL)
  320. return pThis->m_pOleAdviseHolder->EnumAdvise(ppenumAdvise);
  321. return E_FAIL;
  322. }
  323. STDMETHODIMP COleControl::XOleObject::GetMiscStatus(DWORD dwAspect,
  324. DWORD* pdwStatus)
  325. {
  326. METHOD_PROLOGUE_EX_(COleControl, OleObject)
  327. ASSERT_POINTER(pdwStatus, DWORD);
  328. if (dwAspect == DVASPECT_CONTENT)
  329. *pdwStatus = pThis->GetMiscStatus();
  330. else
  331. *pdwStatus = 0;
  332. return S_OK;
  333. }
  334. STDMETHODIMP COleControl::XOleObject::SetColorScheme(LPLOGPALETTE)
  335. {
  336. return E_NOTIMPL;
  337. }
  338. /////////////////////////////////////////////////////////////////////////////
  339. // Force any extra compiler-generated code into AFX_INIT_SEG
  340. #ifdef AFX_INIT_SEG
  341. #pragma code_seg(AFX_INIT_SEG)
  342. #endif