Leaked source code of windows server 2003
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.

227 lines
6.4 KiB

  1. /*++
  2. Module Name:
  3. mmcdispl.cpp
  4. Abstract:
  5. This class implements IDataObject interface and also provides a template
  6. for Display Object Classes.
  7. --*/
  8. #include "stdafx.h"
  9. #include "MmcDispl.h"
  10. #include "DfsGUI.h"
  11. #include "Utils.h" // For LoadStringFromResource
  12. #include "DfsNodes.h"
  13. // Register the clipboard formats that MMC expects us to register
  14. CLIPFORMAT CMmcDisplay::mMMC_CF_NodeType = (CLIPFORMAT)RegisterClipboardFormat(CCF_NODETYPE);
  15. CLIPFORMAT CMmcDisplay::mMMC_CF_NodeTypeString = (CLIPFORMAT)RegisterClipboardFormat(CCF_SZNODETYPE);
  16. CLIPFORMAT CMmcDisplay::mMMC_CF_DisplayName = (CLIPFORMAT)RegisterClipboardFormat(CCF_DISPLAY_NAME);
  17. CLIPFORMAT CMmcDisplay::mMMC_CF_CoClass = (CLIPFORMAT)RegisterClipboardFormat(CCF_SNAPIN_CLASSID);
  18. CLIPFORMAT CMmcDisplay::mMMC_CF_Dfs_Snapin_Internal = (CLIPFORMAT)RegisterClipboardFormat(CCF_DFS_SNAPIN_INTERNAL);
  19. CMmcDisplay::CMmcDisplay() : m_dwRefCount(1), m_hrValueFromCtor(S_OK)
  20. {
  21. dfsDebugOut((_T("CMmcDisplay::CMmcDisplay this=%p\n"), this));
  22. ZeroMemory(&m_CLSIDClass, sizeof(m_CLSIDClass));
  23. ZeroMemory(&m_CLSIDNodeType, sizeof(m_CLSIDNodeType));
  24. }
  25. CMmcDisplay::~CMmcDisplay()
  26. {
  27. dfsDebugOut((_T("CMmcDisplay::~CMmcDisplay this=%p\n"), this));
  28. }
  29. //
  30. // IUnknown Interface Implementation
  31. //
  32. STDMETHODIMP
  33. CMmcDisplay::QueryInterface(
  34. IN const struct _GUID & i_refiid,
  35. OUT void ** o_pUnk
  36. )
  37. {
  38. if (!o_pUnk)
  39. return E_INVALIDARG;
  40. if (i_refiid == __uuidof(IDataObject))
  41. *o_pUnk = (IDataObject *)this;
  42. else if (i_refiid == __uuidof(IUnknown))
  43. *o_pUnk = (IUnknown *)this;
  44. else
  45. return E_NOINTERFACE;
  46. m_dwRefCount++;
  47. return S_OK;
  48. }
  49. unsigned long __stdcall
  50. CMmcDisplay::AddRef()
  51. {
  52. m_dwRefCount++;
  53. return(m_dwRefCount);
  54. }
  55. unsigned long __stdcall
  56. CMmcDisplay::Release()
  57. {
  58. m_dwRefCount--;
  59. if (0 == m_dwRefCount)
  60. {
  61. delete this;
  62. return 0;
  63. }
  64. return(m_dwRefCount);
  65. }
  66. //
  67. // Saves the CLSID of the object.
  68. //
  69. STDMETHODIMP
  70. CMmcDisplay::put_CoClassCLSID(IN CLSID newVal)
  71. {
  72. ZeroMemory(&m_CLSIDClass, sizeof m_CLSIDClass);
  73. m_CLSIDClass = newVal;
  74. return S_OK;
  75. }
  76. STDMETHODIMP
  77. CMmcDisplay::GetDataHere(
  78. IN LPFORMATETC i_lpFormatetc,
  79. OUT LPSTGMEDIUM o_lpMedium
  80. )
  81. /*++
  82. Routine Description:
  83. Return the Data expected. The clipboard format specifies what kind of data
  84. is expected.
  85. Arguments:
  86. i_lpFormatetc - Indicates what kind of data is expected back.
  87. o_lpMedium - The data is return here.
  88. --*/
  89. {
  90. RETURN_INVALIDARG_IF_NULL(i_lpFormatetc);
  91. RETURN_INVALIDARG_IF_NULL(o_lpMedium);
  92. // Based on the required clipboard format, write data to the stream
  93. const CLIPFORMAT clipFormat = i_lpFormatetc->cfFormat;
  94. if ( clipFormat == mMMC_CF_NodeType ) // CCF_NODETYPE
  95. return WriteToStream(reinterpret_cast<const void*>(&m_CLSIDNodeType), sizeof(m_CLSIDNodeType), o_lpMedium);
  96. if ( clipFormat == mMMC_CF_Dfs_Snapin_Internal ) // CCF_DFS_SNAPIN_INTERNAL
  97. {
  98. PVOID pThis = this;
  99. return WriteToStream(reinterpret_cast<const void*>(&pThis), sizeof(pThis), o_lpMedium);
  100. }
  101. if ( clipFormat == mMMC_CF_NodeTypeString ) // CCF_SZNODETYPE
  102. return WriteToStream(m_bstrDNodeType, (m_bstrDNodeType.Length() + 1) * sizeof(TCHAR), o_lpMedium);
  103. if ( clipFormat == mMMC_CF_DisplayName ) // CCF_DISPLAY_NAME
  104. {
  105. CComBSTR bstrDisplayName;
  106. LoadStringFromResource(IDS_NODENAME, &bstrDisplayName);
  107. return WriteToStream(bstrDisplayName, (bstrDisplayName.Length() + 1) * sizeof(TCHAR), o_lpMedium);
  108. }
  109. if ( clipFormat == mMMC_CF_CoClass ) // CCF_SNAPIN_CLASSID
  110. return WriteToStream(reinterpret_cast<const void*>(&m_CLSIDClass), sizeof(m_CLSIDClass), o_lpMedium);
  111. return DV_E_CLIPFORMAT;
  112. }
  113. HRESULT
  114. CMmcDisplay::WriteToStream(
  115. IN const void* i_pBuffer,
  116. IN int i_iBufferLen,
  117. OUT LPSTGMEDIUM o_lpMedium
  118. )
  119. /*++
  120. Routine Description:
  121. Writes data given in a buffer to a Global stream created on a handle passed in
  122. the STGMEDIUM structure.
  123. Only HGLOBAL is supported as the medium
  124. Arguments:
  125. i_pBuffer - The buffer to be written to the stream
  126. i_iBufferLen - The length of the buffer.
  127. o_lpMedium - The data is return here.
  128. --*/
  129. {
  130. RETURN_INVALIDARG_IF_NULL(i_pBuffer);
  131. RETURN_INVALIDARG_IF_NULL(o_lpMedium);
  132. if (i_iBufferLen <= 0)
  133. return E_INVALIDARG;
  134. // Make sure the type medium is HGLOBAL
  135. if (TYMED_HGLOBAL != o_lpMedium->tymed)
  136. return DV_E_TYMED;
  137. // Create the stream on the hGlobal passed in
  138. LPSTREAM lpStream = NULL;
  139. HRESULT hr = CreateStreamOnHGlobal(o_lpMedium->hGlobal, FALSE, &lpStream);
  140. if (SUCCEEDED(hr))
  141. {
  142. // Write to the stream the number of bytes
  143. ULONG ulBytesWritten = 0;
  144. hr = lpStream->Write(i_pBuffer, i_iBufferLen, &ulBytesWritten);
  145. // Only the stream is released here. The caller will free the HGLOBAL
  146. lpStream->Release();
  147. }
  148. return hr;
  149. }
  150. // Add images for the result pane.
  151. // A snap-in must load and destroy its image bitmap each time it responds to
  152. // a MMCN_ADD_IMAGES notification; failure to do so can result in undesirable
  153. // results if the user changes display settings.
  154. HRESULT
  155. CMmcDisplay::OnAddImages(IImageList *pImageList, HSCOPEITEM hsi)
  156. {
  157. HRESULT hr = S_OK;
  158. HBITMAP pBMapSm = NULL;
  159. HBITMAP pBMapLg = NULL;
  160. if (!(pBMapSm = LoadBitmap(_Module.GetModuleInstance(),
  161. MAKEINTRESOURCE(IDB_SCOPE_IMAGES_16x16))) ||
  162. !(pBMapLg = LoadBitmap(_Module.GetModuleInstance(),
  163. MAKEINTRESOURCE(IDB_SCOPE_IMAGES_32x32))))
  164. {
  165. hr = HRESULT_FROM_WIN32(GetLastError());
  166. } else
  167. {
  168. hr = pImageList->ImageListSetStrip(
  169. (LONG_PTR *)pBMapSm,
  170. (LONG_PTR *)pBMapLg,
  171. 0,
  172. RGB(255, 0, 255)
  173. );
  174. }
  175. if (pBMapSm)
  176. DeleteObject(pBMapSm);
  177. if (pBMapLg)
  178. DeleteObject(pBMapLg);
  179. return hr;
  180. }