Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

2336 lines
58 KiB

  1. // Copyright (C) Microsoft Corporation 1996-1997, All Rights reserved.
  2. #include "header.h"
  3. #include "contain.h"
  4. #include "autocont.h"
  5. #include "htmlpriv.h"
  6. #include "htmlhelp.h"
  7. #include "strtable.h"
  8. #include <exdisp.h>
  9. #include "unicode.h"
  10. static const WCHAR gszHHRegKey[] = L"Software\\Microsoft\\HtmlHelp";
  11. // pointer to external IServiceProvider (fix for HelpCenter)
  12. //
  13. IServiceProvider *g_pExternalHostServiceProvider = NULL;
  14. #ifdef _DEBUG
  15. #undef THIS_FILE
  16. static const char THIS_FILE[] = __FILE__;
  17. #endif
  18. /*
  19. * CContainer::CContainer
  20. * CContainer::~CContainer
  21. *
  22. * Constructor Parameters:
  23. */
  24. CContainer::CContainer()
  25. {
  26. m_cRef = 0;
  27. m_pIStorage = NULL;
  28. m_pOleObject = NULL;
  29. m_pIAdviseSink = NULL;
  30. m_pIOleInPlaceSite = NULL;
  31. m_pIOleClientSite = NULL;
  32. m_pIOleInPlaceFrame = NULL;
  33. m_pIOleControlSite = NULL;
  34. m_pWebBrowser = NULL;
  35. m_pWebBrowserApp = NULL;
  36. m_pIDispatch = NULL;
  37. m_pIOleItemContainer = NULL;
  38. // m_pCallback = NULL;
  39. m_pIE3CmdTarget = NULL;
  40. m_dwEventCookie = 0;
  41. m_pWebBrowserEvents = NULL;
  42. m_pCDocHostUIHandler = NULL;
  43. m_pCDocHostShowUI = NULL;
  44. m_pInPlaceActive = 0;
  45. #ifdef _DEBUG
  46. m_fDeleting = FALSE;
  47. #endif
  48. }
  49. CContainer::~CContainer(void)
  50. {
  51. #ifdef _DEBUG
  52. ASSERT(!m_fDeleting)
  53. m_fDeleting = TRUE;
  54. #endif
  55. // if (m_pInPlaceActive)
  56. // m_pInPlaceActive->Release();
  57. // do this before we release m_pIAdviseSink
  58. // Reset the View Advise
  59. LPVIEWOBJECT2 lpViewObject2;
  60. if (m_pOleObject && SUCCEEDED(m_pOleObject->QueryInterface(IID_IViewObject2, (LPVOID FAR *) &lpViewObject2))) {
  61. lpViewObject2->SetAdvise(DVASPECT_CONTENT, ADVF_PRIMEFIRST, NULL );
  62. lpViewObject2->Release();
  63. }
  64. if (m_pIAdviseSink)
  65. m_pIAdviseSink->Release();
  66. if (m_pIOleInPlaceSite)
  67. m_pIOleInPlaceSite->Release();
  68. if (m_pIOleClientSite)
  69. m_pIOleClientSite->Release();
  70. if (m_pIOleInPlaceFrame)
  71. m_pIOleInPlaceFrame->Release();
  72. if (m_pIOleItemContainer)
  73. m_pIOleItemContainer->Release();
  74. if (m_pIOleControlSite)
  75. delete m_pIOleControlSite;
  76. // if (m_pIPropNoteSink)
  77. // delete m_pIPropNoteSink;
  78. if (m_pIE3CmdTarget)
  79. m_pIE3CmdTarget->Release();
  80. if ( m_pCDocHostUIHandler )
  81. m_pCDocHostUIHandler->Release();
  82. if ( m_pCDocHostShowUI )
  83. m_pCDocHostShowUI->Release();
  84. if (m_pWebBrowserApp) {
  85. m_pWebBrowserApp->Quit();
  86. delete m_pWebBrowserApp;
  87. }
  88. if (m_pIStorage)
  89. m_pIStorage->Release();
  90. if (m_pOleObject)
  91. m_pOleObject->Release();
  92. return;
  93. }
  94. HRESULT CContainer::ShutDown(void)
  95. {
  96. if (m_pIDispatch)
  97. {
  98. // Unhook event interface, delete our interface object
  99. //
  100. LPCONNECTIONPOINTCONTAINER pCPC;
  101. if (SUCCEEDED(m_pOleObject->QueryInterface(IID_IConnectionPointContainer, (void **) &pCPC)))
  102. {
  103. LPCONNECTIONPOINT pCP;
  104. if (SUCCEEDED(pCPC->FindConnectionPoint(IID_IDispatch, &pCP)))
  105. {
  106. pCP->Unadvise(m_dwEventCookie);
  107. pCP->Release();
  108. }
  109. // Cleanup
  110. pCPC->Release() ;
  111. }
  112. // Cleanup m_pIDispatch pointer
  113. m_pIDispatch->Release();
  114. m_pIDispatch = NULL; // part of fix for 4373
  115. }
  116. if(m_pOleObject)
  117. {
  118. m_pOleObject->Close(OLECLOSE_NOSAVE);
  119. m_pOleObject->SetClientSite(NULL);
  120. }
  121. delete this;
  122. return S_OK;
  123. }
  124. /*
  125. * CContainer::QueryInterface
  126. *
  127. * Purpose:
  128. * IUnknown members for CContainer object.
  129. */
  130. STDMETHODIMP CContainer::QueryInterface(REFIID riid, LPVOID * ppv)
  131. {
  132. #ifdef DEBUG
  133. char sz[256];
  134. wsprintf(sz,"CContainer::QueryInterface('{%8.8X-%4.4X-%4.4X-%2.2X%2.2X-%2.2X%2.2X%2.2X%2.2X%2.2X%2.2X}',...);\r\n",
  135. riid.Data1, riid.Data2, riid.Data3, riid.Data4[0], riid.Data4[1],
  136. riid.Data4[2], riid.Data4[3], riid.Data4[4], riid.Data4[5], riid.Data4[6],riid.Data4[7]);
  137. OutputDebugString(sz);
  138. #endif
  139. *ppv=NULL;
  140. if ((IID_IUnknown == riid) || (IID_IServiceProvider == riid))
  141. *ppv = this;
  142. else if (IID_IOleClientSite == riid)
  143. *ppv = m_pIOleClientSite;
  144. else if (IID_IAdviseSink2==riid || IID_IAdviseSink==riid)
  145. *ppv = m_pIAdviseSink;
  146. else if (IID_IOleWindow==riid || IID_IOleInPlaceSite==riid)
  147. *ppv = m_pIOleInPlaceSite;
  148. else if (IID_IOleItemContainer == riid || IID_IOleContainer == riid || IID_IParseDisplayName == riid)
  149. *ppv = m_pIOleItemContainer;
  150. else if (riid == DIID_DWebBrowserEvents) {
  151. DBWIN("QueryInterface for DIID_DWebBrowserEvents");
  152. *ppv = (LPDISPATCH)m_pIDispatch;
  153. }
  154. else if (riid == DIID_DWebBrowserEvents2) {
  155. DBWIN("QueryInterface for DIID_DWebBrowserEvents2");
  156. *ppv = (LPDISPATCH)m_pIDispatch;
  157. }
  158. else if (IID_IOleControlSite==riid)
  159. {
  160. DBWIN("QueryInterface for IID_IOleControlSite");
  161. *ppv=m_pIOleControlSite;
  162. }
  163. else if ( riid == IID_IDocHostUIHandler )
  164. {
  165. DBWIN("QueryInterface for IID_IDocHostUIHandler");
  166. *ppv = m_pCDocHostUIHandler;
  167. }
  168. else if ( riid == IID_IDocHostShowUI )
  169. {
  170. DBWIN("QueryInterface for IID_IDocHostShowUI");
  171. *ppv = m_pCDocHostShowUI;
  172. }
  173. // BUGBUG what to do about this ?
  174. // Queries for IDispatch return the ambient properties interface *ppv=m_pIDispatch;
  175. else if (IID_IDispatch==riid)
  176. {
  177. DBWIN("QueryInterface for IID_IDispatch");
  178. *ppv = (IDispatch*)m_pIDispatch;
  179. }
  180. //End CONTROLMOD
  181. if (*ppv)
  182. {
  183. ((LPUNKNOWN)*ppv)->AddRef();
  184. return NOERROR;
  185. }
  186. return ResultFromScode(E_NOINTERFACE);
  187. }
  188. STDMETHODIMP CContainer::QueryService(REFGUID rsid, REFIID riid, void ** pv)
  189. {
  190. HRESULT hr = E_NOINTERFACE;
  191. // Hack for HelpCenter...
  192. if (g_pExternalHostServiceProvider)
  193. {
  194. hr = g_pExternalHostServiceProvider->QueryService(rsid, riid, pv);
  195. }
  196. return hr;
  197. }
  198. STDMETHODIMP_(ULONG) CContainer::AddRef(void)
  199. {
  200. return ++m_cRef;
  201. }
  202. STDMETHODIMP_(ULONG) CContainer::Release(void)
  203. {
  204. ULONG cRefT = --m_cRef;
  205. // we only delete when specifically told to
  206. // if (m_cRef == 0)
  207. // delete this;
  208. return cRefT;
  209. }
  210. HRESULT CContainer::Create(HWND hWnd, LPRECT lpRect, BOOL bInstallEventSink)
  211. {
  212. LPUNKNOWN pObj;
  213. CLSID clsidWB1 = { 0xeab22ac3, 0x30c1, 0x11cf, { 0xa7, 0xeb, 0x0, 0x0, 0xc0, 0x5b, 0xae, 0xb } };
  214. CLSID clsidWB2 = { 0x8856f961, 0x340a, 0x11d0, { 0xa9, 0x6b, 0x0, 0xc0, 0x4f, 0xd7, 0x5, 0xa2 } };
  215. UINT uRet = (UINT) E_FAIL;
  216. HRESULT hr;
  217. m_hWnd = hWnd;
  218. // Create storage, use OLE's temporary compound file support. (ie NULL as first arg.)
  219. if ((hr = StgCreateDocfile(NULL, (STGM_READWRITE | STGM_TRANSACTED | STGM_SHARE_EXCLUSIVE | STGM_DELETEONRELEASE),
  220. 0, &m_pIStorage)) != S_OK) {
  221. DEBUG_ReportOleError(hr);
  222. return E_FAIL;
  223. }
  224. // Create the client site.
  225. m_pIOleClientSite = new CIOleClientSite(this);
  226. m_pIOleClientSite->AddRef();
  227. // Create the control site.
  228. m_pIOleControlSite = new CIOleControlSite(this);
  229. m_pIOleControlSite->AddRef();
  230. // Create the advise sink.
  231. m_pIAdviseSink = new CIAdviseSink(this);
  232. m_pIAdviseSink->AddRef();
  233. // Create the InPlaceSite.
  234. m_pIOleInPlaceSite = new CIOleInPlaceSite(this);
  235. m_pIOleInPlaceSite->AddRef();
  236. // Create the InPlaceFrame;
  237. m_pIOleInPlaceFrame = new CIOleInPlaceFrame(this);
  238. m_pIOleInPlaceFrame->AddRef();
  239. //
  240. // We don't install a sink for the special printing instance. HtmlHelp bug 5550.
  241. //
  242. if ( bInstallEventSink )
  243. {
  244. m_pIDispatch = new CAutomateContent(this);
  245. m_pIDispatch->AddRef();
  246. }
  247. m_pIOleItemContainer = new CIOleItemContainer(this);
  248. m_pIOleItemContainer->AddRef();
  249. /*
  250. * The OLE Control specifications mention that a a control might
  251. * implement IPersistStreamInit instead of IPersistStorage. In that
  252. * case you cannot use OleCreate on a control but must rather use
  253. * CoCreateInstance since OleCreate assumes that IPersistStorage is
  254. * available. With a control, you would have to create the object
  255. * first, then check if OLEMISC_SETCLIENTSITEFIRST is set, then send it
  256. * your IOleClientSite first. Then you check for IPersistStorage and
  257. * failing that, try IPersistStreamInit.
  258. * In this sample we do none of this and just assume controls are
  259. * normal embedded objects because there are questions as to dealing
  260. * with loading and initialization that are not resolved.
  261. */
  262. // These are IE4 specific.
  263. //
  264. m_pCDocHostUIHandler = new CDocHostUIHandler(this);
  265. m_pCDocHostUIHandler->AddRef();
  266. m_pCDocHostShowUI = new CDocHostShowUI(this);
  267. m_pCDocHostShowUI->AddRef();
  268. // first try for the IE4 object, if that fails, try for the IE3 object.
  269. //
  270. if ((hr = OleCreate(clsidWB2, IID_IOleObject, OLERENDER_NONE, NULL, m_pIOleClientSite, m_pIStorage, (void**)&pObj)) != S_OK )
  271. {
  272. if ((hr = OleCreate(clsidWB1, IID_IOleObject, OLERENDER_NONE, NULL, m_pIOleClientSite, m_pIStorage, (void**)&pObj)) != S_OK )
  273. {
  274. m_pIStorage->Release();
  275. m_pIOleClientSite->Release();
  276. return hr;
  277. }
  278. m_bIE4 = FALSE;
  279. }
  280. else
  281. m_bIE4 = TRUE;
  282. if ((hr = pObj->QueryInterface(IID_IOleObject, (void **) &m_pOleObject)) == S_OK) {
  283. LPVIEWOBJECT2 lpViewObject2;
  284. // Set a View Advise
  285. if (SUCCEEDED(m_pOleObject->QueryInterface(IID_IViewObject2, (LPVOID FAR *) &lpViewObject2))) {
  286. lpViewObject2->SetAdvise(DVASPECT_CONTENT, ADVF_PRIMEFIRST, m_pIAdviseSink);
  287. lpViewObject2->Release();
  288. }
  289. // 13-Oct-1997 [ralphw] Shouldn't need this...
  290. // m_pOleObject->SetHostNames(OLESTR("DevIV Package"), OLESTR("DevIV Container"));
  291. // inform object handler/DLL object that it is used in the embedding container's context
  292. OleSetContainedObject(m_pOleObject, TRUE);
  293. // Hook iDispatch up to COleDispatchDriver interface.
  294. LPDISPATCH pDispatch;
  295. if ((hr = m_pOleObject->QueryInterface(IID_IDispatch, (void **) &pDispatch)) == S_OK) {
  296. m_pWebBrowserApp = new IWebBrowserAppImpl(pDispatch);
  297. }
  298. //
  299. // We don't install a sink for the special printing instance. HtmlHelp bug 5550.
  300. //
  301. if ( bInstallEventSink )
  302. {
  303. // Hook event interface.
  304. LPCONNECTIONPOINTCONTAINER pCPC;
  305. if (SUCCEEDED(hr = m_pOleObject->QueryInterface(IID_IConnectionPointContainer, (void **) &pCPC)))
  306. {
  307. LPCONNECTIONPOINT pCP;
  308. if (SUCCEEDED(pCPC->FindConnectionPoint(DIID_DWebBrowserEvents2, &pCP))) {
  309. pCP->Advise((IDispatch*)m_pIDispatch, &m_dwEventCookie);
  310. pCP->Release();
  311. }
  312. else
  313. if (SUCCEEDED(pCPC->FindConnectionPoint(DIID_DWebBrowserEvents, &pCP))) {
  314. pCP->Advise((IDispatch*)m_pIDispatch, &m_dwEventCookie);
  315. pCP->Release();
  316. }
  317. pCPC->Release();
  318. }
  319. }
  320. // Let's get an interface pointer to IOleCommandTarget
  321. hr = m_pOleObject->QueryInterface(IID_IOleCommandTarget, (void **)&m_pIE3CmdTarget);
  322. if (FAILED(hr))
  323. m_pIE3CmdTarget = NULL;
  324. // Show the control.
  325. m_pOleObject->DoVerb(OLEIVERB_SHOW, NULL, m_pIOleClientSite, -1, m_hWnd, lpRect);
  326. uRet = S_OK;
  327. }
  328. pObj->Release(); // always release this ?
  329. if (uRet != S_OK) {
  330. m_pIStorage->Release();
  331. m_pIOleClientSite->Release();
  332. return uRet;
  333. }
  334. return uRet;
  335. }
  336. //
  337. // Called when the window containing IE is losing activation (focus).
  338. //
  339. void CContainer::UIDeactivateIE()
  340. {
  341. IOleInPlaceObject* pIOleInPlaceObject;
  342. HRESULT hr;
  343. if ( SUCCEEDED((hr = m_pOleObject->QueryInterface(IID_IOleInPlaceObject, (void**)&pIOleInPlaceObject))) )
  344. {
  345. pIOleInPlaceObject->UIDeactivate();
  346. pIOleInPlaceObject->Release();
  347. }
  348. }
  349. void CContainer::SetFocus(BOOL bForceActivation)
  350. {
  351. HWND hwnd_child;
  352. TCHAR szClassName[150];
  353. if (! m_pInPlaceActive || bForceActivation )
  354. m_pOleObject->DoVerb(OLEIVERB_UIACTIVATE, NULL, m_pIOleClientSite, -1, m_hWnd, NULL);
  355. m_hwndChild = m_hWnd;
  356. while ((hwnd_child = GetWindow(m_hwndChild, GW_CHILD)) && IsWindowEnabled(hwnd_child) )
  357. {
  358. m_hwndChild = hwnd_child;
  359. GetClassName(hwnd_child, szClassName, sizeof(szClassName));
  360. if ( strstr(szClassName, "Internet Explorer") )
  361. break;
  362. }
  363. if ( hwnd_child && !IsWindowEnabled(hwnd_child) )
  364. m_hwndChild = GetParent(m_hwndChild);
  365. ::SetFocus(m_hwndChild);
  366. }
  367. //
  368. // This needs to be called from the apps message pump to give shdocvw a crack at accelerators
  369. // it implements. For example ^C for copy selected text.
  370. //
  371. // This function will return TRUE if shdocvw traslated the message and FALSE if it did not.
  372. // Note that you can run into trouble if the app and shdocvw share acclerators. We'll want to
  373. // always call TranslateAccelartor() from the message pump for the apps accelators and only if
  374. // it returns false will we call this function to give IE a crack at the message.
  375. //
  376. // mikecole
  377. //
  378. unsigned CContainer::TranslateMessage(MSG * pMsg)
  379. {
  380. if (m_pInPlaceActive)
  381. {
  382. if ( pMsg->message == WM_KEYDOWN && pMsg->wParam == VK_F1 )
  383. return TAMSG_NOT_IE_ACCEL;
  384. if (pMsg->message == WM_KEYDOWN)
  385. {
  386. if (GetKeyState(VK_CONTROL))
  387. {
  388. if (pMsg->wParam == 0x4F ||
  389. pMsg->wParam == 0x4C ||
  390. pMsg->wParam == 0x4E)
  391. return TAMSG_NOT_IE_ACCEL;
  392. }
  393. }
  394. if (m_pInPlaceActive->TranslateAccelerator(pMsg) == S_OK)
  395. return TAMSG_IE_ACCEL;
  396. else
  397. {
  398. if ( (pMsg->message == WM_KEYDOWN) && (pMsg->wParam == VK_TAB) )
  399. {
  400. if ( IsUIActive() && !m_bIE4)
  401. { // translateAccelerator does not work for the tab key in IE3,
  402. // so forward the VK_TAB key message to IE3
  403. ForwardMessage(pMsg->message, pMsg->wParam, pMsg->lParam);
  404. return TAMSG_IE_ACCEL;
  405. }
  406. UIDeactivateIE();
  407. SetFocus();
  408. }
  409. }
  410. }
  411. return TAMSG_NOT_IE_ACCEL;
  412. }
  413. LRESULT CContainer::ForwardMessage(UINT msg, WPARAM wParam, LPARAM lParam)
  414. {
  415. HWND hwnd_child;
  416. HWND hwnd = m_hWnd;
  417. while ( (hwnd_child = GetWindow(hwnd, GW_CHILD)) && IsWindowEnabled(hwnd_child) )
  418. hwnd = hwnd_child;
  419. if ( hwnd_child && !IsWindowEnabled(hwnd_child) )
  420. hwnd = GetParent(hwnd);
  421. if (hwnd)
  422. return ::SendMessage(hwnd, msg, wParam, lParam);
  423. else
  424. return 0;
  425. }
  426. void CContainer::SizeIt(int width, int height)
  427. {
  428. IOleInPlaceObject* pIOleInPlaceObject;
  429. if ( m_bIE4 )
  430. {
  431. if ( SUCCEEDED((m_pOleObject->QueryInterface(IID_IOleInPlaceObject, (void**)&pIOleInPlaceObject))) )
  432. {
  433. RECT rc;
  434. rc.left = rc.top = 0;
  435. rc.bottom = height;
  436. rc.right = width;
  437. pIOleInPlaceObject->SetObjectRects(&rc,&rc);
  438. pIOleInPlaceObject->Release();
  439. }
  440. }
  441. else
  442. {
  443. SIZEL sizel;
  444. sizel.cx = width;
  445. sizel.cy = height;
  446. HDC hdc = GetDC(NULL);
  447. SetMapMode(hdc, MM_HIMETRIC);
  448. DPtoLP(hdc, (LPPOINT) &sizel, 1);
  449. ReleaseDC(NULL, hdc);
  450. sizel.cy = abs(sizel.cy);
  451. m_pOleObject->SetExtent(DVASPECT_CONTENT, &sizel);
  452. }
  453. }
  454. /**************************************************************************************
  455. * AdviseSink code
  456. *
  457. *
  458. * CIAdviseSink implementation begins here!
  459. *
  460. **************************************************************************************/
  461. /*
  462. * CIAdviseSink::CIAdviseSink
  463. * CIAdviseSink::~CIAdviseSink
  464. *
  465. * Parameters (Constructor):
  466. * pCContainer pCContainer of the Container we're in.
  467. * pUnkOuter LPUNKNOWN to which we delegate.
  468. */
  469. CIAdviseSink::CIAdviseSink(PCONTAINER pCContainer)
  470. {
  471. m_cRef=0;
  472. m_pUnkOuter = m_pContainer = pCContainer;
  473. return;
  474. }
  475. CIAdviseSink::~CIAdviseSink(void)
  476. {
  477. return;
  478. }
  479. /*
  480. * CIAdviseSink::QueryInterface
  481. * CIAdviseSink::AddRef
  482. * CIAdviseSink::Release
  483. *
  484. * Purpose:
  485. * IUnknown members for CIAdviseSink object.
  486. */
  487. STDMETHODIMP CIAdviseSink::QueryInterface(REFIID riid, LPVOID * ppv)
  488. {
  489. return m_pUnkOuter->QueryInterface(riid, ppv);
  490. }
  491. STDMETHODIMP_(ULONG) CIAdviseSink::AddRef(void)
  492. {
  493. m_pUnkOuter->AddRef();
  494. return ++m_cRef;
  495. }
  496. STDMETHODIMP_(ULONG) CIAdviseSink::Release(void)
  497. {
  498. ULONG ul = --m_cRef;
  499. m_pUnkOuter->Release();
  500. if (ul <= 0)
  501. delete this;
  502. return ul;
  503. }
  504. /*
  505. * CIAdviseSink::OnDataChange
  506. *
  507. * Unused since we don't IDataObject::Advise.
  508. */
  509. STDMETHODIMP_(void) CIAdviseSink::OnDataChange(LPFORMATETC pFEIn, LPSTGMEDIUM pSTM)
  510. {
  511. return;
  512. }
  513. /*
  514. * CIAdviseSink::OnViewChange
  515. *
  516. * Purpose:
  517. * Notifes the advise sink that presentation data changed in the
  518. * data object to which we're connected providing the right time
  519. * to update displays using such presentations.
  520. *
  521. * Parameters:
  522. * dwAspect DWORD indicating which aspect has changed.
  523. * lindex LONG indicating the piece that changed.
  524. *
  525. * Return Value:
  526. * None
  527. */
  528. STDMETHODIMP_(void) CIAdviseSink::OnViewChange(DWORD dwAspect, LONG lindex)
  529. {
  530. //Repaint only if this is the right aspect
  531. //m_pContainer->Repaint();
  532. return;
  533. }
  534. /*
  535. * CIAdviseSink::OnRename
  536. *
  537. * Purpose:
  538. * Informs the advise sink that a linked object has been renamed.
  539. * Generally only the OLE default handler cares about this.
  540. *
  541. * Parameters:
  542. * pmk LPMONIKER providing the new name of the object
  543. *
  544. * Return Value:
  545. * None
  546. */
  547. STDMETHODIMP_(void) CIAdviseSink::OnRename(LPMONIKER pmk)
  548. {
  549. /*
  550. * As a container this is unimportant to us since it really
  551. * tells the handler's implementation of IOleLink that the
  552. * object's moniker has changed. Since we get this call
  553. * from the handler, we don't have to do anything ourselves.
  554. */
  555. return;
  556. }
  557. /*
  558. * CIAdviseSink::OnSave
  559. *
  560. * Purpose:
  561. * Informs the advise sink that the OLE object has been saved
  562. * persistently. The primary purpose of this is for containers
  563. * that want to make optimizations for objects that are not in a
  564. * saved state, so on this you have to disable such optimizations.
  565. *
  566. * Parameters:
  567. * None
  568. *
  569. * Return Value:
  570. * None
  571. */
  572. STDMETHODIMP_(void) CIAdviseSink::OnSave(void)
  573. {
  574. /*
  575. * A Container has nothing to do here as this notification is
  576. * only useful when we have an ADVFCACHE_ONSAVE advise set up,
  577. * which we don't. So we ignore it.
  578. */
  579. return;
  580. }
  581. /*
  582. * CIAdviseSink::OnClose
  583. *
  584. * Purpose:
  585. * Informs the advise sink that the OLE object has closed and is
  586. * no longer bound in any way.
  587. *
  588. * Parameters:
  589. * None
  590. *
  591. * Return Value:
  592. * None
  593. */
  594. STDMETHODIMP_(void) CIAdviseSink::OnClose(void)
  595. {
  596. /*
  597. * This doesn't have anything to do with us again as it's only
  598. * used to notify the handler's IOleLink implementation of the
  599. * change in the object. We don't have to do anything since
  600. * we'll also get an IOleClientSite::OnShowWindow(FALSE) to
  601. * tell us to repaint.
  602. */
  603. return;
  604. }
  605. /*
  606. * CIAdviseSink2::OnLinkSrcChange
  607. *
  608. * Purpose:
  609. * Informs the advise sink that a linked compound document object
  610. * has changed its link source to the object identified by the
  611. * given moniker. This is generally only of interest to the OLE
  612. * default handler's implementation of linked objects.
  613. *
  614. * Parameters:
  615. * pmk LPMONIKER specifying the new link source.
  616. *
  617. * Return Value:
  618. * None
  619. */
  620. STDMETHODIMP_(void) CIAdviseSink::OnLinkSrcChange(LPMONIKER pmk)
  621. {
  622. return;
  623. }
  624. /**************************************************************************************
  625. *
  626. * ClientSite code
  627. *
  628. *
  629. * CIOleClientSite implementation begins here!
  630. *
  631. **************************************************************************************/
  632. /*
  633. * CIOleClientSite::CIOleClientSite
  634. * CIOleClientSite::~CIOleClientSite
  635. *
  636. * Parameters (Constructor):
  637. * pCContainer PCContainer of the container we're in.
  638. * pUnkOuter LPUNKNOWN to which we delegate.
  639. */
  640. CIOleClientSite::CIOleClientSite(PCONTAINER pCContainer)
  641. {
  642. m_cRef=0;
  643. m_pUnkOuter = m_pContainer = pCContainer;
  644. return;
  645. }
  646. CIOleClientSite::~CIOleClientSite(void)
  647. {
  648. return;
  649. }
  650. /*
  651. * CIOleClientSite::QueryInterface
  652. * CIOleClientSite::AddRef
  653. * CIOleClientSite::Release
  654. *
  655. * Purpose:
  656. * IUnknown members for CIOleClientSite object.
  657. */
  658. STDMETHODIMP CIOleClientSite::QueryInterface(REFIID riid, LPVOID * ppv)
  659. {
  660. return m_pUnkOuter->QueryInterface(riid, ppv);
  661. }
  662. STDMETHODIMP_(ULONG) CIOleClientSite::AddRef(void)
  663. {
  664. m_pUnkOuter->AddRef();
  665. return ++m_cRef;
  666. }
  667. STDMETHODIMP_(ULONG) CIOleClientSite::Release(void)
  668. {
  669. ULONG ul = --m_cRef;
  670. m_pUnkOuter->Release();
  671. if (ul <= 0)
  672. delete this;
  673. return ul;
  674. }
  675. /*
  676. * CIOleClientSite::SaveObject
  677. *
  678. * Purpose:
  679. * Requests that the container call OleSave for the object that
  680. * lives here. Typically this happens on server shutdown.
  681. *
  682. * Parameters:
  683. * None
  684. *
  685. * Return Value:
  686. * HRESULT Standard.
  687. */
  688. STDMETHODIMP CIOleClientSite::SaveObject(void)
  689. {
  690. // We're already set up with the tenant to save; this is trivial.
  691. //pCContainer->Update();
  692. return NOERROR;
  693. }
  694. /*
  695. * CIOleClientSite::GetMoniker
  696. *
  697. * Purpose:
  698. * Retrieves the moniker for the site in which this object lives,
  699. * either the moniker relative to the container or the full
  700. * moniker.
  701. *
  702. * Parameters:
  703. * dwAssign DWORD specifying that the object wants moniker
  704. * assignment. Yeah. Right. Got any bridges to
  705. * sell?
  706. * dwWhich DWORD identifying which moniker the object
  707. * wants, either the container's moniker, the
  708. * moniker relative to this client site, or the
  709. * full moniker.
  710. *
  711. * Return Value:
  712. * HRESULT Standard.
  713. */
  714. STDMETHODIMP CIOleClientSite::GetMoniker(DWORD dwAssign, DWORD dwWhich, LPMONIKER *ppmk)
  715. {
  716. *ppmk=NULL;
  717. switch (dwWhich)
  718. {
  719. case OLEWHICHMK_CONTAINER:
  720. //This is just the file we're living in.
  721. break;
  722. case OLEWHICHMK_OBJREL:
  723. //This is everything but the filename.
  724. break;
  725. case OLEWHICHMK_OBJFULL:
  726. //Concatenate file and relative monikers for this one.
  727. break;
  728. }
  729. if (NULL==*ppmk)
  730. return ResultFromScode(E_FAIL);
  731. (*ppmk)->AddRef();
  732. return NOERROR;
  733. }
  734. /*
  735. * CIOleClientSite::GetContainer
  736. *
  737. * Purpose:
  738. * Returns a pointer to the document's IOleContainer interface.
  739. *
  740. * Parameters:
  741. * ppContainer LPOLECONTAINER * in which to return the
  742. * interface.
  743. *
  744. * Return Value:
  745. * HRESULT Standard.
  746. */
  747. STDMETHODIMP CIOleClientSite::GetContainer(LPOLECONTAINER* ppContainer)
  748. {
  749. if (m_pContainer)
  750. return m_pContainer->QueryInterface(IID_IOleItemContainer, (LPVOID *)ppContainer);
  751. return ResultFromScode(E_FAIL);
  752. }
  753. /*
  754. * CIOleClientSite::ShowObject
  755. *
  756. * Purpose:
  757. * Tells the container to bring the object fully into view as much
  758. * as possible, that is, scroll the document.
  759. *
  760. * Parameters:
  761. * None
  762. *
  763. * Return Value:
  764. * HRESULT Standard.
  765. */
  766. STDMETHODIMP CIOleClientSite::ShowObject(void)
  767. {
  768. // deligate back to CContainer
  769. // m_pContainer->ShowObject();
  770. return NOERROR;
  771. }
  772. /*
  773. * CIOleClientSite::OnShowWindow
  774. *
  775. * Purpose:
  776. * Informs the container if the object is showing itself or
  777. * hiding itself. This is done only in the opening mode and allows
  778. * the container to know when to shade or unshade the object.
  779. *
  780. * Parameters:
  781. * fShow BOOL indiciating that the object is being shown
  782. * (TRUE) or hidden (FALSE).
  783. * Return Value:
  784. * HRESULT Standard.
  785. */
  786. STDMETHODIMP CIOleClientSite::OnShowWindow(BOOL fShow)
  787. {
  788. // deligate back to CContainer
  789. // m_pContainer->OnShowWindow(fShow);
  790. return NOERROR;
  791. }
  792. /*
  793. * CIOleClientSite::RequestNewObjectLayout
  794. *
  795. * Purpose:
  796. * Called when the object would like to have its layout
  797. * reinitialized. This is used by OLE Controls.
  798. *
  799. * Parameters:
  800. * None
  801. *
  802. * Return Value:
  803. * HRESULT Standard.
  804. */
  805. STDMETHODIMP CIOleClientSite::RequestNewObjectLayout(void)
  806. {
  807. // deligate back to CContainer
  808. // m_pContainer->RequestNewObjectLayout();
  809. return NOERROR;
  810. }
  811. /**************************************************************************************
  812. *
  813. * InPlaceSite code
  814. *
  815. *
  816. * CIOleInPlaceSite implementation begins here!
  817. *
  818. **************************************************************************************/
  819. /*
  820. * CIOleInPlaceSite::CIOleInPlaceSite
  821. * CIOleInPlaceSite::~CIOleInPlaceSite
  822. *
  823. * Parameters (Constructor):
  824. * pCContainer Pointer to the container we're in.
  825. * pUnkOuter LPUNKNOWN to which we delegate.
  826. */
  827. CIOleInPlaceSite::CIOleInPlaceSite(PCONTAINER pCContainer)
  828. {
  829. m_cRef=0;
  830. m_pUnkOuter = m_pContainer = pCContainer;
  831. return;
  832. }
  833. CIOleInPlaceSite::~CIOleInPlaceSite(void)
  834. {
  835. ASSERT(m_cRef == 0);
  836. return;
  837. }
  838. /*
  839. * CIOleInPlaceSite::QueryInterface
  840. * CIOleInPlaceSite::AddRef
  841. * CIOleInPlaceSite::Release
  842. *
  843. * Purpose:
  844. * IUnknown members for CIOleInPlaceSite object.
  845. */
  846. STDMETHODIMP CIOleInPlaceSite::QueryInterface(REFIID riid, LPVOID * ppv)
  847. {
  848. return m_pUnkOuter->QueryInterface(riid, ppv);
  849. }
  850. STDMETHODIMP_(ULONG) CIOleInPlaceSite::AddRef(void)
  851. {
  852. m_pUnkOuter->AddRef();
  853. return ++m_cRef;
  854. }
  855. STDMETHODIMP_(ULONG) CIOleInPlaceSite::Release(void)
  856. {
  857. ULONG ul = --m_cRef;
  858. m_pUnkOuter->Release();
  859. if (ul <= 0)
  860. delete this;
  861. return ul;
  862. }
  863. /*
  864. * CIOleInPlaceActiveObject::GetWindow
  865. *
  866. * Purpose:
  867. * Retrieves the handle of the window associated with the object
  868. * on which this interface is implemented.
  869. *
  870. * Parameters:
  871. * phWnd HWND * in which to store the window handle.
  872. *
  873. * Return Value:
  874. * HRESULT NOERROR if successful, E_FAIL if there is no
  875. * window.
  876. */
  877. STDMETHODIMP CIOleInPlaceSite::GetWindow(HWND *phWnd)
  878. {
  879. *phWnd = m_pContainer->m_hWnd;
  880. return NOERROR;
  881. }
  882. /*
  883. * CIOleInPlaceActiveObject::ContextSensitiveHelp
  884. *
  885. * Purpose:
  886. * Instructs the object on which this interface is implemented to
  887. * enter or leave a context-sensitive help mode.
  888. *
  889. * Parameters:
  890. * fEnterMode BOOL TRUE to enter the mode, FALSE otherwise.
  891. *
  892. * Return Value:
  893. * HRESULT NOERROR
  894. */
  895. STDMETHODIMP CIOleInPlaceSite::ContextSensitiveHelp(BOOL fEnterMode)
  896. {
  897. return NOERROR;
  898. }
  899. /*
  900. * CIOleInPlaceSite::CanInPlaceActivate
  901. *
  902. * Purpose:
  903. * Answers the server whether or not we can currently in-place
  904. * activate its object. By implementing this interface we say
  905. * that we support in-place activation, but through this function
  906. * we indicate whether the object can currently be activated
  907. * in-place. Iconic aspects, for example, cannot, meaning we
  908. * return S_FALSE.
  909. *
  910. * Parameters:
  911. * None
  912. *
  913. * Return Value:
  914. * HRESULT NOERROR if we can in-place activate the object
  915. * in this site, S_FALSE if not.
  916. */
  917. STDMETHODIMP CIOleInPlaceSite::CanInPlaceActivate(void)
  918. {
  919. return NOERROR;
  920. }
  921. /*
  922. * CIOleInPlaceSite::OnInPlaceActivate
  923. *
  924. * Purpose:
  925. * Informs the container that an object is being activated in-place
  926. * such that the container can prepare appropriately. The
  927. * container does not, however, make any user interface changes at
  928. * this point. See OnUIActivate.
  929. *
  930. * Parameters:
  931. * None
  932. *
  933. * Return Value:
  934. * HRESULT NOERROR or an appropriate error code.
  935. */
  936. STDMETHODIMP CIOleInPlaceSite::OnInPlaceActivate(void)
  937. {
  938. // BUGBUG: Mikecole - Does this belong here ?
  939. //if (FAILED(m_pOleObject->QueryInterface(IID_IOleInPlaceActiveObject, (void**)&m_pInPlaceActive)))
  940. // m_pInPlaceActive = 0;
  941. return NOERROR;
  942. }
  943. /*
  944. * CIOleInPlaceSite::OnInPlaceDeactivate
  945. *
  946. * Purpose:
  947. * Notifies the container that the object has deactivated itself
  948. * from an in-place state. Opposite of OnInPlaceActivate. The
  949. * container does not change any UI at this point.
  950. *
  951. * Parameters:
  952. * None
  953. *
  954. * Return Value:
  955. * HRESULT NOERROR or an appropriate error code.
  956. */
  957. STDMETHODIMP CIOleInPlaceSite::OnInPlaceDeactivate(void)
  958. {
  959. // BUGBUG: Mikecole - Does this belong here ?
  960. //if (FAILED(m_pOleObject->QueryInterface(IID_IOleInPlaceActiveObject, (void**)&m_pInPlaceActive)))
  961. // m_pInPlaceActive = 0;
  962. return NOERROR;
  963. }
  964. /*
  965. * CIOleInPlaceSite::OnUIActivate
  966. *
  967. * Purpose:
  968. * Informs the container that the object is going to start munging
  969. * around with user interface, like replacing the menu. The
  970. * container should remove any relevant UI in preparation.
  971. *
  972. * Parameters:
  973. * None
  974. *
  975. * Return Value:
  976. * HRESULT NOERROR or an appropriate error code.
  977. */
  978. STDMETHODIMP CIOleInPlaceSite::OnUIActivate(void)
  979. {
  980. return NOERROR;
  981. }
  982. /*
  983. * CIOleInPlaceSite::OnUIDeactivate
  984. *
  985. * Purpose:
  986. * Informs the container that the object is deactivating its
  987. * in-place user interface at which time the container may
  988. * reinstate its own. Opposite of OnUIActivate.
  989. *
  990. * Parameters:
  991. * fUndoable BOOL indicating if the object will actually
  992. * perform an Undo if the container calls
  993. * ReactivateAndUndo.
  994. *
  995. * Return Value:
  996. * HRESULT NOERROR or an appropriate error code.
  997. */
  998. STDMETHODIMP CIOleInPlaceSite::OnUIDeactivate(BOOL fUndoable)
  999. {
  1000. return NOERROR;
  1001. }
  1002. /*
  1003. * CIOleInPlaceSite::DeactivateAndUndo
  1004. *
  1005. * Purpose:
  1006. * If immediately after activation the object does an Undo, the
  1007. * action being undone is the activation itself, and this call
  1008. * informs the container that this is, in fact, what happened.
  1009. * The container should call IOleInPlaceObject::UIDeactivate.
  1010. *
  1011. * Parameters:
  1012. * None
  1013. *
  1014. * Return Value:
  1015. * HRESULT NOERROR or an appropriate error code.
  1016. */
  1017. STDMETHODIMP CIOleInPlaceSite::DeactivateAndUndo(void)
  1018. {
  1019. //CONTROLMOD
  1020. /*
  1021. * Note that we don't pay attention to the locking
  1022. * from IOleControlSite::LockInPlaceActive since only
  1023. * the object calls this function and should know
  1024. * that it's going to be deactivated.
  1025. */
  1026. //End CONTROLMOD
  1027. return NOERROR;
  1028. }
  1029. /*
  1030. * CIOleInPlaceSite::DiscardUndoState
  1031. *
  1032. * Purpose:
  1033. * Informs the container that something happened in the object
  1034. * that means the container should discard any undo information
  1035. * it currently maintains for the object.
  1036. *
  1037. * Parameters:
  1038. * None
  1039. *
  1040. * Return Value:
  1041. * HRESULT NOERROR or an appropriate error code.
  1042. */
  1043. STDMETHODIMP CIOleInPlaceSite::DiscardUndoState(void)
  1044. {
  1045. return ResultFromScode(E_NOTIMPL);
  1046. }
  1047. /*
  1048. * CIOleInPlaceSite::GetWindowContext
  1049. *
  1050. * Purpose:
  1051. * Provides an in-place object with pointers to the frame and
  1052. * document level in-place interfaces (IOleInPlaceFrame and
  1053. * IOleInPlaceUIWindow) such that the object can do border
  1054. * negotiation and so forth. Also requests the position and
  1055. * clipping rectangles of the object in the container and a
  1056. * pointer to an OLEINPLACEFRAME info structure which contains
  1057. * accelerator information.
  1058. *
  1059. * Note that the two interfaces this call returns are not
  1060. * available through QueryInterface on IOleInPlaceSite since they
  1061. * live with the frame and document, but not the site.
  1062. *
  1063. * Parameters:
  1064. * ppIIPFrame LPOLEINPLACEFRAME * in which to return the
  1065. * AddRef'd pointer to the container's
  1066. * IOleInPlaceFrame.
  1067. * ppIIPUIWindow LPOLEINPLACEUIWINDOW * in which to return
  1068. * the AddRef'd pointer to the container document's
  1069. * IOleInPlaceUIWindow.
  1070. * prcPos LPRECT in which to store the object's position.
  1071. * prcClip LPRECT in which to store the object's visible
  1072. * region.
  1073. * pFI LPOLEINPLACEFRAMEINFO to fill with accelerator
  1074. * stuff.
  1075. *
  1076. * Return Value:
  1077. * HRESULT NOERROR
  1078. */
  1079. STDMETHODIMP CIOleInPlaceSite::GetWindowContext(LPOLEINPLACEFRAME FAR* lplpFrame,
  1080. LPOLEINPLACEUIWINDOW FAR* lplpDoc, LPRECT lprcPosRect,
  1081. LPRECT lprcClipRect, LPOLEINPLACEFRAMEINFO lpFrameInfo)
  1082. {
  1083. RECT rect;
  1084. // the frame is associated with the application object.
  1085. // need to AddRef() it...
  1086. m_pContainer->m_pIOleInPlaceFrame->AddRef();
  1087. *lplpFrame = m_pContainer->m_pIOleInPlaceFrame;
  1088. *lplpDoc = NULL; // must be NULL, cause we're SDI.
  1089. // get the size of the object in pixels
  1090. ::GetClientRect(m_pContainer->m_hWnd, &rect); // This may be bogus!
  1091. // Copy this to the passed buffer
  1092. CopyRect(lprcPosRect, &rect);
  1093. // fill the clipping region
  1094. CopyRect(lprcClipRect, &rect);
  1095. // fill the FRAMEINFO
  1096. lpFrameInfo->fMDIApp = FALSE;
  1097. lpFrameInfo->hwndFrame = m_pContainer->m_hWnd;
  1098. lpFrameInfo->haccel = NULL;
  1099. lpFrameInfo->cAccelEntries = 0;
  1100. return ResultFromScode(S_OK);
  1101. }
  1102. /*
  1103. * CIOleInPlaceSite::Scroll
  1104. *
  1105. * Purpose:
  1106. * Asks the container to scroll the document, and thus the object,
  1107. * by the given amounts in the sz parameter.
  1108. *
  1109. * Parameters:
  1110. * sz SIZE containing signed horizontal and vertical
  1111. * extents by which the container should scroll.
  1112. * These are in device units.
  1113. *
  1114. * Return Value:
  1115. * HRESULT NOERROR
  1116. */
  1117. STDMETHODIMP CIOleInPlaceSite::Scroll(SIZE sz)
  1118. {
  1119. return NOERROR;
  1120. }
  1121. /*
  1122. * CIOleInPlaceSite::OnPosRectChange
  1123. *
  1124. * Purpose:
  1125. * Informs the container that the in-place object was resized.
  1126. * The container must call IOleInPlaceObject::SetObjectRects.
  1127. * This does not change the site's rectangle in any case.
  1128. *
  1129. * Parameters:
  1130. * prcPos LPCRECT containing the new size of the object.
  1131. *
  1132. * Return Value:
  1133. * HRESULT NOERROR
  1134. */
  1135. STDMETHODIMP CIOleInPlaceSite::OnPosRectChange(LPCRECT prcPos)
  1136. {
  1137. // m_pContainer->UpdateInPlaceObjectRects(prcPos, FALSE);
  1138. return NOERROR;
  1139. }
  1140. /**************************************************************************************
  1141. *
  1142. * InPlaceFrame code
  1143. *
  1144. *
  1145. * CIOleInPlaceFrame implementation begins here!
  1146. *
  1147. **************************************************************************************/
  1148. /*
  1149. * CIOleInPlaceFrame::CIOleInPlaceFrame
  1150. * CIOleInPlaceFrame::~CIOleInPlaceFrame
  1151. *
  1152. * Parameters (Constructor):
  1153. * pTen PCTenant of the tenant we're in.
  1154. * pUnkOuter LPUNKNOWN to which we delegate.
  1155. */
  1156. CIOleInPlaceFrame::CIOleInPlaceFrame(PCONTAINER pCContainer)
  1157. {
  1158. m_cRef=0;
  1159. m_pUnkOuter = m_pContainer = pCContainer;
  1160. return;
  1161. }
  1162. CIOleInPlaceFrame::~CIOleInPlaceFrame(void)
  1163. {
  1164. ASSERT(m_cRef == 0);
  1165. return;
  1166. }
  1167. /*
  1168. * CIOleInPlaceFrame::QueryInterface
  1169. * CIOleInPlaceFrame::AddRef
  1170. * CIOleInPlaceFrame::Release
  1171. *
  1172. * Purpose:
  1173. * IUnknown members for CIOleInPlaceFrame object.
  1174. */
  1175. STDMETHODIMP CIOleInPlaceFrame::QueryInterface(REFIID riid, LPVOID * ppv)
  1176. {
  1177. //We only know IUnknown and IOleInPlaceFrame
  1178. *ppv=NULL;
  1179. //Remember to do ALL base interfaces
  1180. if ( IID_IUnknown == riid ||
  1181. IID_IOleInPlaceUIWindow == riid ||
  1182. IID_IOleWindow == riid ||
  1183. IID_IOleInPlaceFrame == riid )
  1184. *ppv=(LPOLEINPLACEFRAME)this;
  1185. if (NULL!=*ppv)
  1186. {
  1187. ((LPUNKNOWN)*ppv)->AddRef();
  1188. return NOERROR;
  1189. }
  1190. return ResultFromScode(E_NOINTERFACE);
  1191. }
  1192. STDMETHODIMP_(ULONG) CIOleInPlaceFrame::AddRef(void)
  1193. {
  1194. m_pUnkOuter->AddRef();
  1195. return ++m_cRef;
  1196. }
  1197. STDMETHODIMP_(ULONG) CIOleInPlaceFrame::Release(void)
  1198. {
  1199. ULONG ul = --m_cRef;
  1200. m_pUnkOuter->Release();
  1201. if (ul <= 0)
  1202. delete this;
  1203. return ul;
  1204. }
  1205. /*
  1206. * CIOleInPlaceFrame::GetWindow
  1207. *
  1208. * Purpose:
  1209. * Retrieves the handle of the window associated with the object
  1210. * on which this interface is implemented.
  1211. *
  1212. * Parameters:
  1213. * phWnd HWND * in which to store the window handle.
  1214. *
  1215. * Return Value:
  1216. * HRESULT NOERROR if successful, E_FAIL if there is no
  1217. * window.
  1218. */
  1219. STDMETHODIMP CIOleInPlaceFrame::GetWindow(HWND *phWnd)
  1220. {
  1221. *phWnd = m_pContainer->m_hWnd;
  1222. return NOERROR;
  1223. }
  1224. /*
  1225. * CIOleInPlaceFrame::ContextSensitiveHelp
  1226. *
  1227. * Purpose:
  1228. * Instructs the object on which this interface is implemented to
  1229. * enter or leave a context-sensitive help mode.
  1230. *
  1231. * Parameters:
  1232. * fEnterMode BOOL TRUE to enter the mode, FALSE otherwise.
  1233. *
  1234. * Return Value:
  1235. * HRESULT NOERROR
  1236. */
  1237. STDMETHODIMP CIOleInPlaceFrame::ContextSensitiveHelp(BOOL fEnterMode)
  1238. {
  1239. // If we had an embedded control with menus, this would get called on an
  1240. // f1 keypress with a menu pulled down.
  1241. //
  1242. return NOERROR;
  1243. }
  1244. /*
  1245. * CIOleInPlaceFrame::GetBorder
  1246. *
  1247. * Purpose:
  1248. * Returns the rectangle in which the container is willing to
  1249. * negotiate about an object's adornments.
  1250. *
  1251. * Parameters:
  1252. * prcBorder LPRECT in which to store the rectangle.
  1253. *
  1254. * Return Value:
  1255. * HRESULT NOERROR if all is well, INPLACE_E_NOTOOLSPACE
  1256. * if there is no negotiable space.
  1257. */
  1258. STDMETHODIMP CIOleInPlaceFrame::GetBorder(LPRECT prcBorder)
  1259. {
  1260. if (NULL==prcBorder)
  1261. return ResultFromScode(E_INVALIDARG);
  1262. /*
  1263. * We return all the client area space sans the StatStrip,
  1264. * which we control
  1265. */
  1266. GetClientRect(m_pContainer->m_hWnd, prcBorder);
  1267. return NOERROR;
  1268. }
  1269. /*
  1270. * CIOleInPlaceFrame::RequestBorderSpace
  1271. *
  1272. * Purpose:
  1273. * Asks the container if it can surrender the amount of space
  1274. * in pBW that the object would like for it's adornments. The
  1275. * container does nothing but validate the spaces on this call.
  1276. *
  1277. * Parameters:
  1278. * pBW LPCBORDERWIDTHS containing the requested space.
  1279. * The values are the amount of space requested
  1280. * from each side of the relevant window.
  1281. *
  1282. * Return Value:
  1283. * HRESULT NOERROR if we can give up space,
  1284. * INPLACE_E_NOTOOLSPACE otherwise.
  1285. */
  1286. STDMETHODIMP CIOleInPlaceFrame::RequestBorderSpace(LPCBORDERWIDTHS pBW)
  1287. {
  1288. //Everything is fine with us, so always return an OK.
  1289. // mikecole/douglash Should either return inplace_e_notoolspace or we should honor the
  1290. // request for border space below in setborderspace().
  1291. return INPLACE_E_NOTOOLSPACE;
  1292. }
  1293. /*
  1294. * CIOleInPlaceFrame::SetBorderSpace
  1295. *
  1296. * Purpose:
  1297. * Called when the object now officially requests that the
  1298. * container surrender border space it previously allowed
  1299. * in RequestBorderSpace. The container should resize windows
  1300. * appropriately to surrender this space.
  1301. *
  1302. * Parameters:
  1303. * pBW LPCBORDERWIDTHS containing the amount of space
  1304. * from each side of the relevant window that the
  1305. * object is now reserving.
  1306. *
  1307. * Return Value:
  1308. * HRESULT NOERROR
  1309. */
  1310. STDMETHODIMP CIOleInPlaceFrame::SetBorderSpace(LPCBORDERWIDTHS pBW)
  1311. {
  1312. return NOERROR;
  1313. }
  1314. /*
  1315. * CIOleInPlaceFrame::InsertMenus
  1316. *
  1317. * Purpose:
  1318. * Instructs the container to place its in-place menu items where
  1319. * necessary in the given menu and to fill in elements 0, 2, and 4
  1320. * of the OLEMENUGROUPWIDTHS array to indicate how many top-level
  1321. * items are in each group.
  1322. *
  1323. * Parameters:
  1324. * hMenu HMENU in which to add popups.
  1325. * pMGW LPOLEMENUGROUPWIDTHS in which to store the
  1326. * width of each container menu group.
  1327. *
  1328. * Return Value:
  1329. * HRESULT NOERROR
  1330. */
  1331. STDMETHODIMP CIOleInPlaceFrame::InsertMenus(HMENU hMenu, LPOLEMENUGROUPWIDTHS pMGW)
  1332. {
  1333. return NOERROR;
  1334. }
  1335. /*
  1336. * CIOleInPlaceFrame::SetMenu
  1337. *
  1338. * Purpose:
  1339. * Instructs the container to replace whatever menu it's currently
  1340. * using with the given menu and to call OleSetMenuDescritor so OLE
  1341. * knows to whom to dispatch messages.
  1342. *
  1343. * Parameters:
  1344. * hMenu HMENU to show.
  1345. * hOLEMenu HOLEMENU to the menu descriptor.
  1346. * hWndObj HWND of the active object to which messages are
  1347. * dispatched.
  1348. * Return Value:
  1349. * HRESULT NOERROR
  1350. */
  1351. STDMETHODIMP CIOleInPlaceFrame::SetMenu(HMENU hMenu, HOLEMENU hOLEMenu, HWND hWndObj)
  1352. {
  1353. /*
  1354. * Our responsibilities here are to put the menu on the frame
  1355. * window and call OleSetMenuDescriptor.
  1356. * CPatronClient::SetMenu which we call here takes care of
  1357. * MDI/SDI differences.
  1358. *
  1359. * We also want to save the object's hWnd for use in WM_SETFOCUS
  1360. * processing.
  1361. */
  1362. return NOERROR;
  1363. }
  1364. /*
  1365. * CIOleInPlaceFrame::RemoveMenus
  1366. *
  1367. * Purpose:
  1368. * Asks the container to remove any menus it put into hMenu in
  1369. * InsertMenus.
  1370. *
  1371. * Parameters:
  1372. * hMenu HMENU from which to remove the container's
  1373. * items.
  1374. *
  1375. * Return Value:
  1376. * HRESULT NOERROR
  1377. */
  1378. STDMETHODIMP CIOleInPlaceFrame::RemoveMenus(HMENU hMenu)
  1379. {
  1380. /*
  1381. * To be defensive, loop through this menu removing anything
  1382. * we recognize (that is, anything in m_phMenu) just in case
  1383. * the server didn't clean it up right. At least we can
  1384. * give ourselves the prophylactic benefit.
  1385. */
  1386. /*
  1387. * Walk backwards down the menu. For each popup, see if it
  1388. * matches any other popup we know about, and if so, remove
  1389. * it from the shared menu.
  1390. */
  1391. return NOERROR;
  1392. }
  1393. /*
  1394. * CIOleInPlaceFrame::SetStatusText
  1395. *
  1396. * Purpose:
  1397. * Asks the container to place some text in a status line, if one
  1398. * exists. If the container does not have a status line it
  1399. * should return E_FAIL here in which case the object could
  1400. * display its own.
  1401. *
  1402. * Parameters:
  1403. * pszText LPCTSTR to display.
  1404. *
  1405. * Return Value:
  1406. * HRESULT NOERROR if successful, S_TRUNCATED if not all
  1407. * of the text could be displayed, or E_FAIL if
  1408. * the container has no status line.
  1409. */
  1410. STDMETHODIMP CIOleInPlaceFrame::SetStatusText(LPCOLESTR pszText)
  1411. {
  1412. /*
  1413. * Just send this to the StatStrip. Unfortunately it won't tell
  1414. * us about truncation. Oh well, we'll just act like it worked.
  1415. */
  1416. if (pszText) {
  1417. #if 0
  1418. char buf[256];
  1419. 25-Sep-1997 [ralphw] Can't find SetPrompt in IV source code
  1420. if (ConvertWz(pszText, buf, sizeof(buf))) {
  1421. if (*pszText)
  1422. SetPrompt(buf, TRUE);
  1423. else
  1424. SetPrompt();
  1425. }
  1426. #endif
  1427. }
  1428. return NOERROR;
  1429. }
  1430. /*
  1431. * CIOleInPlaceFrame::EnableModeless
  1432. *
  1433. * Purpose:
  1434. * Instructs the container to show or hide any modeless popup
  1435. * windows that it may be using.
  1436. *
  1437. * Parameters:
  1438. * fEnable BOOL indicating to enable/show the windows
  1439. * (TRUE) or to hide them (FALSE).
  1440. *
  1441. * Return Value:
  1442. * HRESULT NOERROR
  1443. */
  1444. STDMETHODIMP CIOleInPlaceFrame::EnableModeless(BOOL fEnable)
  1445. {
  1446. return NOERROR;
  1447. }
  1448. /*
  1449. * CIOleInPlaceFrame::TranslateAccelerator
  1450. *
  1451. * Purpose:
  1452. * When dealing with an in-place object from an EXE server, this
  1453. * is called to give the container a chance to process accelerators
  1454. * after the server has looked at the message.
  1455. *
  1456. * Parameters:
  1457. * pMSG LPMSG for the container to examine.
  1458. * wID WORD the identifier in the container's
  1459. * accelerator table (from IOleInPlaceSite
  1460. * ::GetWindowContext) for this message (OLE does
  1461. * some translation before calling).
  1462. *
  1463. * Return Value:
  1464. * HRESULT NOERROR if the keystroke was used,
  1465. * S_FALSE otherwise.
  1466. */
  1467. STDMETHODIMP CIOleInPlaceFrame::TranslateAccelerator(LPMSG pMSG, WORD wID)
  1468. {
  1469. /*
  1470. * wID already has anything translated from m_hAccelIP for us,
  1471. * so we can just check for the commands we want and process
  1472. * them instead of calling TranslateAccelerator which would be
  1473. * redundant and which also has a possibility of dispatching to
  1474. * the wrong window.
  1475. */
  1476. // if (pMSG->message == WM_KEYDOWN && pMSG->wParam == VK_ESCAPE)
  1477. // PostMessage(CUR_HWND, WM_CLOSE, 0, 0);
  1478. return S_FALSE;
  1479. }
  1480. /***********************************************************************
  1481. *
  1482. * COleInPlaceFrame::SetActiveObject
  1483. *
  1484. * Purpose:
  1485. *
  1486. *
  1487. * Parameters:
  1488. *
  1489. * LPOLEINPLACEACTIVEOBJECT lpActiveObject - Pointer to the
  1490. * objects
  1491. * IOleInPlaceActiveObject
  1492. * interface
  1493. *
  1494. * @@WTK WIN32, UNICODE
  1495. * //LPCSTR lpszObjName - Name of the object
  1496. * LPCOLESTR lpszObjName - Name of the object
  1497. *
  1498. * Return Value:
  1499. *
  1500. * S_OK
  1501. *
  1502. * Function Calls:
  1503. * Function Location
  1504. *
  1505. * OutputDebugString Windows API
  1506. * IOleInPlaceActiveObject::AddRef Object
  1507. * IOleInPlaceActiveObject::Release Object
  1508. * ResultFromScode OLE API
  1509. *
  1510. * Comments:
  1511. *
  1512. ********************************************************************/
  1513. STDMETHODIMP CIOleInPlaceFrame::SetActiveObject(LPOLEINPLACEACTIVEOBJECT lpActiveObject,
  1514. LPCOLESTR lpszObjName)
  1515. {
  1516. // in an MDI app, this method really shouldn't be called,
  1517. // this method associated with the doc is called instead.
  1518. // should set window title here
  1519. if ( m_pContainer->m_pInPlaceActive )
  1520. m_pContainer->m_pInPlaceActive->Release();
  1521. if (lpActiveObject)
  1522. lpActiveObject->AddRef();
  1523. m_pContainer->m_pInPlaceActive = lpActiveObject;
  1524. return NOERROR;
  1525. }
  1526. /*********************************************************************
  1527. *
  1528. * CIOleControlSite Implementation starts here.
  1529. *
  1530. *
  1531. /*
  1532. * CIOleControlSite::CIOleControlSite
  1533. * CIOleControlSite::~CIOleControlSite
  1534. *
  1535. * Parameters (Constructor):
  1536. * pTen PCTenant of the object we're in.
  1537. * pUnkOuter LPUNKNOWN to which we delegate.
  1538. */
  1539. CIOleControlSite::CIOleControlSite(PCONTAINER pCContainer)
  1540. {
  1541. m_cRef=0;
  1542. m_pUnkOuter = m_pContainer = pCContainer;
  1543. return;
  1544. }
  1545. CIOleControlSite::~CIOleControlSite(void)
  1546. {
  1547. return;
  1548. }
  1549. /*
  1550. * CIOleControlSite::QueryInterface
  1551. * CIOleControlSite::AddRef
  1552. * CIOleControlSite::Release
  1553. *
  1554. * Purpose:
  1555. * Delegating IUnknown members for CIOleControlSite.
  1556. */
  1557. STDMETHODIMP CIOleControlSite::QueryInterface(REFIID riid, LPVOID *ppv)
  1558. {
  1559. return m_pUnkOuter->QueryInterface(riid, ppv);
  1560. }
  1561. STDMETHODIMP_(ULONG) CIOleControlSite::AddRef(void)
  1562. {
  1563. ++m_cRef;
  1564. return m_pUnkOuter->AddRef();
  1565. }
  1566. STDMETHODIMP_(ULONG) CIOleControlSite::Release(void)
  1567. {
  1568. --m_cRef;
  1569. return m_pUnkOuter->Release();
  1570. }
  1571. /*
  1572. * CIOleControlSite::OnControlInfoChanged
  1573. *
  1574. * Purpose:
  1575. * Informs the site that the CONTROLINFO for the control has
  1576. * changed and we thus need to reload the data.
  1577. *
  1578. * Parameters:
  1579. * None
  1580. *
  1581. * Return Value:
  1582. * HRESULT NOERROR
  1583. */
  1584. STDMETHODIMP CIOleControlSite::OnControlInfoChanged(void)
  1585. {
  1586. return NOERROR;
  1587. }
  1588. /*
  1589. * CIOleControlSite::LockInPlaceActive
  1590. *
  1591. * Purpose:
  1592. * Forces the container to keep this control in-place active
  1593. * (but not UI active) regardless of other considerations, or
  1594. * removes this lock.
  1595. *
  1596. * Parameters:
  1597. * fLock BOOL indicating to lock (TRUE) or unlock (FALSE)
  1598. * in-place activation.
  1599. *
  1600. * Return Value:
  1601. * HRESULT NOERROR
  1602. */
  1603. STDMETHODIMP CIOleControlSite::LockInPlaceActive(BOOL fLock)
  1604. {
  1605. return NOERROR;
  1606. }
  1607. /*
  1608. * CIOleControlSite::GetExtendedControl
  1609. *
  1610. * Purpose:
  1611. * Returns a pointer to the container's extended control that wraps
  1612. * the actual control in this site, if one exists.
  1613. *
  1614. * Parameters:
  1615. * ppDispatch LPDISPATCH * in which to return the pointer
  1616. * to the extended control's IDispatch interface.
  1617. *
  1618. * Return Value:
  1619. * HRESULT NOERROR or a general error value.
  1620. */
  1621. STDMETHODIMP CIOleControlSite::GetExtendedControl(LPDISPATCH* ppDispatch)
  1622. {
  1623. *ppDispatch=NULL;
  1624. return ResultFromScode(E_NOTIMPL);
  1625. }
  1626. /*
  1627. * CIOleControlSite::TransformCoords
  1628. *
  1629. * Purpose:
  1630. * Converts coordinates in HIMETRIC units into those used by the
  1631. * container.
  1632. *
  1633. * Parameters:
  1634. * pptlHiMet POINTL * containing either the coordinates to
  1635. * transform to container or where to store the
  1636. * transformed container coordinates.
  1637. * pptlCont POINTF * containing the container coordinates.
  1638. * dwFlags DWORD containing instructional flags.
  1639. *
  1640. * Return Value:
  1641. * HRESULT NOERROR or a general error value.
  1642. */
  1643. STDMETHODIMP CIOleControlSite::TransformCoords(POINTL *pptlHiMet, POINTF *pptlCont, DWORD dwFlags)
  1644. {
  1645. if (NULL==pptlHiMet || NULL==pptlCont)
  1646. return ResultFromScode(E_POINTER);
  1647. /*
  1648. * Convert coordinates. We use MM_LOMETRIC which means that
  1649. * to convert from HIMETRIC we divide by 10 and negate the y
  1650. * coordinate. Conversion to HIMETRIC means negate the y
  1651. * and multiply by 10. Note that size and position are
  1652. * considered the same thing, that is, we don't differentiate
  1653. * the two.
  1654. */
  1655. if (XFORMCOORDS_HIMETRICTOCONTAINER & dwFlags)
  1656. {
  1657. pptlCont->x=(float)(pptlHiMet->x/10);
  1658. pptlCont->y=(float)-(pptlHiMet->y/10);
  1659. }
  1660. else
  1661. {
  1662. pptlHiMet->x=(long)(pptlCont->x*10);
  1663. pptlHiMet->y=(long)-(pptlCont->y*10);
  1664. }
  1665. return NOERROR;
  1666. }
  1667. /*
  1668. * CIOleControlSite::TranslateAccelerator
  1669. *
  1670. * Purpose:
  1671. * Instructs the container to translate a keyboard accelerator
  1672. * message that the control has picked up instead.
  1673. *
  1674. * Parameters:
  1675. * pMsg LPMSG to the message to translate.
  1676. * grfModifiers DWORD flags with additional instructions.
  1677. *
  1678. * Return Value:
  1679. * HRESULT NOERROR or a general error value.
  1680. */
  1681. STDMETHODIMP CIOleControlSite::TranslateAccelerator(LPMSG pMsg, DWORD grfModifiers)
  1682. {
  1683. #ifdef _DEBUG
  1684. char sz[1000];
  1685. HWND hWnd;
  1686. hWnd = GetFocus();
  1687. wsprintf(sz,"CIOleControlSite::TranslateAccelerator()\nGetFocus == %X\npMsg->hwnd = %X\npMsg->message = %X\npMsg->wParam = %X\npMsg->lParam = %X\npMsg->time = %X\npMsg->pt.x = %X\npMsg->pt.y = %X\n",
  1688. hWnd,pMsg->hwnd,pMsg->message,pMsg->wParam,pMsg->lParam,pMsg->time,pMsg->pt.x,pMsg->pt.y);
  1689. OutputDebugString(sz);
  1690. #endif
  1691. return ResultFromScode(E_NOTIMPL);
  1692. }
  1693. /*
  1694. * CIOleControlSite::OnFocus
  1695. *
  1696. * Purpose:
  1697. * Informs the container that focus has either been lost or
  1698. * gained in the control.
  1699. *
  1700. * Parameters:
  1701. * fGotFocus BOOL indicating that the control gained (TRUE)
  1702. * or lost (FALSE) focus.
  1703. *
  1704. * Return Value:
  1705. * HRESULT NOERROR or a general error value.
  1706. */
  1707. STDMETHODIMP CIOleControlSite::OnFocus(BOOL fGotFocus)
  1708. {
  1709. //We don't handle default buttons, so this is not interesting
  1710. return NOERROR;
  1711. }
  1712. /*
  1713. * CIOleControlSite::ShowPropertyFrame
  1714. *
  1715. * Purpose:
  1716. * Instructs the container to show the property frame if
  1717. * this is, in fact, an extended object.
  1718. *
  1719. * Parameters:
  1720. * None
  1721. *
  1722. * Return Value:
  1723. * HRESULT NOERROR or a general error value.
  1724. */
  1725. STDMETHODIMP CIOleControlSite::ShowPropertyFrame(void)
  1726. {
  1727. //We don't do extended objects, so nothing to do here.
  1728. return ResultFromScode(E_NOTIMPL);
  1729. }
  1730. //#endif // CIOleControlSite
  1731. /********************************************************************
  1732. *
  1733. * Implementation of IOleItemContainer
  1734. *
  1735. * We don't actually use this interface, but need to return one so
  1736. * the IE control can QI it for IDispatch. Why they don't just QI the
  1737. * site I don't know.
  1738. */
  1739. CIOleItemContainer::CIOleItemContainer(IUnknown * pOuter)
  1740. {
  1741. m_cRef = 0;
  1742. m_pOuter = pOuter;
  1743. }
  1744. // aggregating IUnknown methods
  1745. STDMETHODIMP CIOleItemContainer::QueryInterface(REFIID riid, LPVOID * ppv)
  1746. {
  1747. *ppv = 0;
  1748. if (m_pOuter)
  1749. return m_pOuter->QueryInterface(riid,ppv);
  1750. else
  1751. return E_NOINTERFACE;
  1752. #if 0
  1753. if (riid == IID_IUnknown || riid == IID_IOleItemContainer
  1754. || riid == IID_IOleContainer || riid == IID_IParseDisplayName)
  1755. {
  1756. *ppv = (LPVOID)(IDispatch*)this;
  1757. AddRef();
  1758. return S_OK;
  1759. }
  1760. return E_NOINTERFACE;
  1761. #endif
  1762. }
  1763. STDMETHODIMP_(ULONG) CIOleItemContainer::AddRef(void)
  1764. {
  1765. m_cRef++;
  1766. if (m_pOuter)
  1767. m_pOuter->AddRef();
  1768. return m_cRef;
  1769. }
  1770. STDMETHODIMP_(ULONG) CIOleItemContainer::Release(void)
  1771. {
  1772. ULONG c = --m_cRef;
  1773. if (m_pOuter)
  1774. m_pOuter->Release();
  1775. if (c <= 0)
  1776. delete this;
  1777. return c;
  1778. }
  1779. STDMETHODIMP CIOleItemContainer::ParseDisplayName(IBindCtx *, LPOLESTR,ULONG*,IMoniker**)
  1780. {
  1781. return E_NOTIMPL;
  1782. }
  1783. STDMETHODIMP CIOleItemContainer::EnumObjects(DWORD,LPENUMUNKNOWN*)
  1784. {
  1785. return E_NOTIMPL;
  1786. }
  1787. STDMETHODIMP CIOleItemContainer::LockContainer(BOOL)
  1788. {
  1789. return E_NOTIMPL;
  1790. }
  1791. STDMETHODIMP CIOleItemContainer::GetObject(LPOLESTR,DWORD,IBindCtx*,REFIID,void**)
  1792. {
  1793. return E_NOTIMPL;
  1794. }
  1795. STDMETHODIMP CIOleItemContainer::GetObjectStorage(LPOLESTR,IBindCtx*,REFIID,void**)
  1796. {
  1797. return E_NOTIMPL;
  1798. }
  1799. STDMETHODIMP CIOleItemContainer::IsRunning(LPOLESTR)
  1800. {
  1801. return S_FALSE;
  1802. }
  1803. int ConvertWz(const WCHAR * pwz, char * psz, int len)
  1804. {
  1805. BOOL fDefault = FALSE;
  1806. return WideCharToMultiByte(CP_ACP, 0, pwz, wcslen(pwz) + 1, psz, len, "*", &fDefault);
  1807. }
  1808. /*********************************************************************************************
  1809. *
  1810. * CDocHostUIHandler
  1811. *
  1812. * IE4 only QI()'s our control site for one of these. Most of these functions are called from
  1813. * IE's IOleInPlaceActiveObject coorisponding members. This gives us a great deal of control
  1814. * over UI compared to what we had with IE3. Using IDocHostUIHandler members me can:
  1815. *
  1816. * Control the right click context menu.
  1817. * Control the window border.
  1818. * Keep seperate registry settings from IE.
  1819. * Handle keyboard accelarators more intelegently.
  1820. */
  1821. CDocHostUIHandler::CDocHostUIHandler(IUnknown * pOuter)
  1822. {
  1823. m_cRef = 0;
  1824. m_pOuter = pOuter;
  1825. }
  1826. STDMETHODIMP CDocHostUIHandler::QueryInterface(REFIID riid, LPVOID * ppv)
  1827. {
  1828. *ppv = 0;
  1829. if (m_pOuter)
  1830. return m_pOuter->QueryInterface(riid,ppv);
  1831. else
  1832. return E_NOINTERFACE;
  1833. }
  1834. STDMETHODIMP_(ULONG) CDocHostUIHandler::AddRef(void)
  1835. {
  1836. m_cRef++;
  1837. if (m_pOuter)
  1838. m_pOuter->AddRef();
  1839. return m_cRef;
  1840. }
  1841. STDMETHODIMP_(ULONG) CDocHostUIHandler::Release(void)
  1842. {
  1843. ULONG c = --m_cRef;
  1844. if (m_pOuter)
  1845. m_pOuter->Release();
  1846. if (c <= 0)
  1847. delete this;
  1848. return c;
  1849. }
  1850. STDMETHODIMP CDocHostUIHandler::ShowContextMenu(DWORD dwID, POINT *ppt, IUnknown *pcmdtReserved, IDispatch *pdispReserved)
  1851. {
  1852. // We cannot define these below since they are already incorrectly defined in include\mshtmlhst.h
  1853. // so we will just use the hard-coded values instead
  1854. //#define CONTEXT_MENU_DEFAULT 0 // typically blank areas in the topic
  1855. //#define CONTEXT_MENU_IMAGE 1 // bitmaps, etc.
  1856. //#define CONTEXT_MENU_CONTROL 2
  1857. //#define CONTEXT_MENU_TABLE 3
  1858. //#define CONTEXT_MENU_DEBUG 4 // seleted text uses this id
  1859. //#define CONTEXT_MENU_1DSELECT 5 // these are links
  1860. //#define CONTEXT_MENU_ANCHOR 6
  1861. //#define CONTEXT_MENU_IMGDYNSRC 7
  1862. if( dwID == 0 || dwID == 1 || dwID == 5 ) {
  1863. if( HMENU hMenu = CreatePopupMenu() ) {
  1864. #define IDTB_REBASE 1000
  1865. #define HTMLID_REBASE 2000
  1866. if( dwID == 0 ) {
  1867. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, IDTB_REBASE+IDTB_BACK, GetStringResource(IDS_OPTION_BACK) );
  1868. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, IDTB_REBASE+IDTB_FORWARD, GetStringResource(IDS_OPTION_FORWARD) );
  1869. AppendMenu( hMenu, MF_SEPARATOR, -1, NULL );
  1870. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, OLECMDID_SELECTALL, GetStringResource(IDS_OPTION_SELECTALL) );
  1871. AppendMenu( hMenu, MF_SEPARATOR, -1, NULL );
  1872. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, HTMLID_REBASE+HTMLID_VIEWSOURCE, GetStringResource(IDS_OPTION_VIEWSOURCE) );
  1873. AppendMenu( hMenu, MF_SEPARATOR, -1, NULL );
  1874. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, OLECMDID_PRINT, GetStringResource(IDS_OPTION_PRINT) );
  1875. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, OLECMDID_REFRESH, GetStringResource(IDS_OPTION_REFRESH) );
  1876. AppendMenu( hMenu, MF_SEPARATOR, -1, NULL );
  1877. }
  1878. if( dwID == 1 ) {
  1879. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, OLECMDID_COPY, GetStringResource(IDS_OPTION_COPY) );
  1880. AppendMenu( hMenu, MF_SEPARATOR, -1, NULL );
  1881. }
  1882. HxAppendMenu( hMenu, MF_STRING | MF_ENABLED, OLECMDID_PROPERTIES, GetStringResource(IDS_OPTION_PROPERTIES) );
  1883. VARIANT vaIn;
  1884. VARIANT vaOut;
  1885. ::VariantInit(&vaIn);
  1886. ::VariantInit(&vaOut);
  1887. HWND hWndParent = NULL;
  1888. hWndParent = ((CContainer*) m_pOuter)->m_hwndChild;
  1889. if( !IsValidWindow(hWndParent) )
  1890. hWndParent = GetActiveWindow();
  1891. if( !hWndParent )
  1892. hWndParent = GetDesktopWindow();
  1893. int iCmd = TrackPopupMenu( hMenu,
  1894. TPM_LEFTALIGN | TPM_TOPALIGN | TPM_RIGHTBUTTON | TPM_RETURNCMD | TPM_NONOTIFY,
  1895. (*ppt).x, (*ppt).y, 0, hWndParent, NULL);
  1896. DestroyMenu( hMenu );
  1897. if( iCmd < IDTB_REBASE ) {
  1898. if( iCmd == OLECMDID_PROPERTIES ) { // Trident folks say the In value must be set to the mouse pos
  1899. V_VT(&vaIn) = VT_I4;
  1900. V_I4(&vaIn) = MAKELONG((*ppt).x,(*ppt).y);
  1901. }
  1902. ((IOleCommandTarget*)pcmdtReserved)->Exec( NULL, iCmd,
  1903. OLECMDEXECOPT_DODEFAULT, &vaIn, &vaOut );
  1904. }
  1905. else if( iCmd < HTMLID_REBASE ) {
  1906. iCmd -=IDTB_REBASE;
  1907. if( iCmd == IDTB_BACK )
  1908. ((CContainer*) m_pOuter)->m_pWebBrowserApp->GoBack();
  1909. else if( iCmd == IDTB_FORWARD )
  1910. ((CContainer*) m_pOuter)->m_pWebBrowserApp->GoForward();
  1911. }
  1912. else {
  1913. iCmd -=HTMLID_REBASE;
  1914. ((IOleCommandTarget*)pcmdtReserved)->Exec( &CGID_IWebBrowserPriv, iCmd,
  1915. OLECMDEXECOPT_DODEFAULT, &vaIn, &vaOut );
  1916. }
  1917. }
  1918. return S_OK;
  1919. }
  1920. else
  1921. return S_FALSE;
  1922. }
  1923. STDMETHODIMP CDocHostUIHandler::GetHostInfo(DOCHOSTUIINFO *pInfo)
  1924. {
  1925. pInfo->dwFlags = 0;
  1926. pInfo->dwDoubleClick = DOCHOSTUIDBLCLK_DEFAULT;
  1927. return S_OK;
  1928. }
  1929. STDMETHODIMP CDocHostUIHandler::ShowUI(DWORD dwID, IOleInPlaceActiveObject *pActiveObject, IOleCommandTarget *pCommandTarget,
  1930. IOleInPlaceFrame *pFrame, IOleInPlaceUIWindow *pDoc)
  1931. {
  1932. return S_OK;
  1933. }
  1934. STDMETHODIMP CDocHostUIHandler::HideUI(void)
  1935. {
  1936. return S_OK;
  1937. }
  1938. STDMETHODIMP CDocHostUIHandler::UpdateUI(void)
  1939. {
  1940. return S_OK;
  1941. }
  1942. STDMETHODIMP CDocHostUIHandler::EnableModeless(BOOL fEnable)
  1943. {
  1944. return S_OK;
  1945. }
  1946. STDMETHODIMP CDocHostUIHandler::OnDocWindowActivate(BOOL fActivate)
  1947. {
  1948. return S_OK;
  1949. }
  1950. STDMETHODIMP CDocHostUIHandler::OnFrameWindowActivate(BOOL fActivate)
  1951. {
  1952. return S_OK;
  1953. }
  1954. STDMETHODIMP CDocHostUIHandler::ResizeBorder(LPCRECT prcBorder, IOleInPlaceUIWindow *pUIWindow, BOOL fRameWindow)
  1955. {
  1956. return S_OK;
  1957. }
  1958. STDMETHODIMP CDocHostUIHandler::TranslateAccelerator(LPMSG lpMsg, const GUID *pguidCmdGroup, DWORD nCmdID)
  1959. {
  1960. return S_FALSE;
  1961. }
  1962. STDMETHODIMP CDocHostUIHandler::GetOptionKeyPath(LPOLESTR *pchKey, DWORD dw)
  1963. {
  1964. #if 0
  1965. // The key given will be stored under HKEY_CURRETN_USER.
  1966. //
  1967. if ( (*pchKey = (LPOLESTR)CoTaskMemAlloc((lstrlenW(gszHHRegKey)*sizeof(WCHAR))+sizeof(WCHAR))) )
  1968. {
  1969. wcscpy(*pchKey, gszHHRegKey);
  1970. return S_OK;
  1971. }
  1972. #endif
  1973. return S_FALSE;
  1974. }
  1975. STDMETHODIMP CDocHostUIHandler::GetDropTarget(IDropTarget *pDropTarget, IDropTarget **ppDropTarget)
  1976. {
  1977. return E_NOTIMPL;
  1978. }
  1979. STDMETHODIMP CDocHostUIHandler::GetExternal(IDispatch **ppDispatch)
  1980. {
  1981. *ppDispatch = NULL;
  1982. return E_NOTIMPL;
  1983. }
  1984. STDMETHODIMP CDocHostUIHandler::TranslateUrl(DWORD dwTranslate, OLECHAR *pchURLIn, OLECHAR **ppchURLOut)
  1985. {
  1986. return S_FALSE;
  1987. }
  1988. STDMETHODIMP CDocHostUIHandler::FilterDataObject(IDataObject *pDO, IDataObject **ppDORet)
  1989. {
  1990. return S_FALSE;
  1991. }
  1992. /*********************************************************************************************
  1993. *
  1994. * CDocHostShowUI
  1995. *
  1996. */
  1997. CDocHostShowUI::CDocHostShowUI(IUnknown * pOuter)
  1998. {
  1999. m_cRef = 0;
  2000. m_pOuter = pOuter;
  2001. }
  2002. STDMETHODIMP CDocHostShowUI::QueryInterface(REFIID riid, LPVOID * ppv)
  2003. {
  2004. *ppv = 0;
  2005. if (m_pOuter)
  2006. return m_pOuter->QueryInterface(riid,ppv);
  2007. else
  2008. return E_NOINTERFACE;
  2009. }
  2010. STDMETHODIMP_(ULONG) CDocHostShowUI::AddRef(void)
  2011. {
  2012. m_cRef++;
  2013. if (m_pOuter)
  2014. m_pOuter->AddRef();
  2015. return m_cRef;
  2016. }
  2017. STDMETHODIMP_(ULONG) CDocHostShowUI::Release(void)
  2018. {
  2019. ULONG c = --m_cRef;
  2020. if (m_pOuter)
  2021. m_pOuter->Release();
  2022. if (c <= 0)
  2023. delete this;
  2024. return c;
  2025. }
  2026. STDMETHODIMP CDocHostShowUI::ShowHelp( HWND hwnd, LPOLESTR pszHelpFile, UINT uCommand, DWORD dwData, POINT ptMouse, IDispatch* pDispatchObjectHit )
  2027. {
  2028. return S_FALSE;
  2029. }
  2030. STDMETHODIMP CDocHostShowUI::ShowMessage( HWND hwnd, LPOLESTR lpstrText, LPOLESTR lpstrCaption, DWORD dwType, LPOLESTR lpstrHelpFile, DWORD dwHelpContext, LRESULT* plResult )
  2031. {
  2032. return S_FALSE;
  2033. }