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.

653 lines
15 KiB

  1. /*++
  2. Copyright (c) 1996 Microsoft Corporation
  3. Module Name:
  4. faxcomponent.h
  5. Abstract:
  6. This file contains my implementation of IComponent.
  7. Environment:
  8. WIN32 User Mode
  9. Author:
  10. Darwin Ouyang (t-darouy) 30-Sept-1997
  11. --*/
  12. // faxcomponent.cpp : Implementation of CFaxComponent
  13. #include "stdafx.h"
  14. #include "faxadmin.h"
  15. #include "faxhelper.h"
  16. #include "faxcomp.h"
  17. #include "faxcompd.h"
  18. #include "faxdataobj.h"
  19. #include "inode.h"
  20. #include "iroot.h"
  21. #include "ilogging.h"
  22. #include "ilogcat.h"
  23. #include "idevices.h"
  24. #include "idevice.h"
  25. #include "adminhlp.h"
  26. #pragma hdrstop
  27. ////////////////////////////////////////////////////////////////////////////////////////////////////
  28. ////////////////////////////////////////////////////////////////////////////////////////////////////
  29. ////////////////////////////////////////////////////////////////////////////////////////////////////
  30. ////////////////////////////////////////////////////////////////////////////////////////////////////
  31. //
  32. //
  33. // Constructor and Destructor
  34. //
  35. //
  36. CFaxComponent::CFaxComponent()
  37. /*++
  38. Routine Description:
  39. Constructor
  40. Arguments:
  41. None.
  42. Return Value:
  43. None.
  44. --*/
  45. {
  46. m_pUnknown = NULL;
  47. m_pConsole = NULL;
  48. m_pConsoleNameSpace = NULL;
  49. m_pConsoleVerb = NULL;
  50. m_pHeaderCtrl = NULL;
  51. m_pImageList = NULL;
  52. m_pResultData = NULL;
  53. m_pControlbar = NULL;
  54. m_dwPropSheetCount = 0;
  55. CFaxComponentExtendContextMenu::m_pFaxComponent = this;
  56. CFaxComponentExtendPropertySheet::m_pFaxComponent = this;
  57. CFaxComponentExtendControlbar::m_pFaxComponent = this;
  58. // initialize CInternalDevices instance data
  59. pDeviceArray = NULL;
  60. numDevices = 0;
  61. // initialize CInternalLogging instance data
  62. pLogPArray = NULL;
  63. pCategories = NULL;
  64. numCategories = 0;
  65. DebugPrint(( TEXT("FaxComponent Created") ));
  66. }
  67. CFaxComponent::~CFaxComponent()
  68. /*++
  69. Routine Description:
  70. Destructor.
  71. Arguments:
  72. None.
  73. Return Value:
  74. None.
  75. --*/
  76. {
  77. DebugPrint(( TEXT("FaxComponent Destroyed") ));
  78. DWORD count;
  79. // release CInternalDevices instance data
  80. if(pDeviceArray != NULL ) {
  81. for( count = 0; count < numDevices; count ++ ) {
  82. if( pDeviceArray[count] != NULL ) {
  83. delete pDeviceArray[count];
  84. pDeviceArray[count] = NULL;
  85. }
  86. }
  87. delete pDeviceArray;
  88. pDeviceArray = NULL;
  89. }
  90. // release CInternalLogging instance data
  91. if( pLogPArray != NULL ) {
  92. for( count = 0; count < numCategories; count++ ) {
  93. if( pLogPArray[count] != NULL ) {
  94. delete pLogPArray[count];
  95. pLogPArray[count] = NULL;
  96. }
  97. }
  98. delete pLogPArray;
  99. pLogPArray = NULL;
  100. }
  101. if( pCategories != NULL ) {
  102. FaxFreeBuffer( (PVOID) pCategories );
  103. pCategories = NULL;
  104. }
  105. }
  106. ////////////////////////////////////////////////////////////////////////////////////////////////////
  107. ////////////////////////////////////////////////////////////////////////////////////////////////////
  108. ////////////////////////////////////////////////////////////////////////////////////////////////////
  109. ////////////////////////////////////////////////////////////////////////////////////////////////////
  110. //
  111. //
  112. // CFaxComponent implementation
  113. //
  114. //
  115. HRESULT
  116. STDMETHODCALLTYPE
  117. CFaxComponent::Initialize(
  118. IN LPCONSOLE lpUnknown)
  119. /*++
  120. Routine Description:
  121. This routine initializes IComponent by querying
  122. for needed interfaces.
  123. Arguments:
  124. lpUnknown - the console's IUnknown/IConsole interface.
  125. Return Value:
  126. HRESULT indicating SUCCEEDED() or FAILED()
  127. --*/
  128. {
  129. assert( lpUnknown != NULL );
  130. HRESULT hr;
  131. do {
  132. m_pUnknown = lpUnknown;
  133. // increment reference on the console
  134. m_pUnknown->AddRef();
  135. hr = m_pUnknown->QueryInterface( IID_IConsole, (void **)&m_pConsole );
  136. assert( SUCCEEDED( hr ));
  137. if( FAILED( hr ) ) {
  138. break;
  139. }
  140. hr = m_pConsole->QueryResultImageList( &m_pImageList );
  141. assert( SUCCEEDED( hr ));
  142. if( FAILED( hr ) ) {
  143. break;
  144. }
  145. hr = m_pUnknown->QueryInterface( IID_IResultData, (void **)&m_pResultData );
  146. assert( SUCCEEDED( hr ));
  147. if( FAILED( hr ) ) {
  148. break;
  149. }
  150. hr = m_pUnknown->QueryInterface( IID_IConsoleNameSpace, (void **)&m_pConsoleNameSpace );
  151. assert( SUCCEEDED( hr ));
  152. if( FAILED( hr ) ) {
  153. break;
  154. }
  155. hr = m_pConsole->QueryConsoleVerb( &m_pConsoleVerb );
  156. assert( SUCCEEDED( hr ));
  157. if( FAILED( hr ) ) {
  158. break;
  159. }
  160. hr = m_pUnknown->QueryInterface( IID_IHeaderCtrl, (void **)&m_pHeaderCtrl );
  161. assert( SUCCEEDED( hr ));
  162. if( FAILED( hr ) ) {
  163. break;
  164. }
  165. // set the header object
  166. hr = m_pConsole->SetHeader( m_pHeaderCtrl );
  167. assert( SUCCEEDED( hr ));
  168. if( FAILED( hr ) ) {
  169. break;
  170. }
  171. } while( 0 );
  172. return hr;
  173. }
  174. HRESULT
  175. STDMETHODCALLTYPE
  176. CFaxComponent::Notify(
  177. IN LPDATAOBJECT lpDataObject,
  178. IN MMC_NOTIFY_TYPE event,
  179. IN LPARAM arg,
  180. IN LPARAM param)
  181. /*++
  182. Routine Description:
  183. This routine dispatches events sent to the IComponent
  184. interface using the cookie extracted from the DataObject.
  185. The cookie stored is a pointer to the class that implements behavior for
  186. that subfolder. So we delegate all the messages by taking the cookie
  187. casting it to a pointer to a folder, and invoking the notify method.
  188. Arguments:
  189. lpDataobject - the data object
  190. event - the event type
  191. arg, param - event arguments
  192. Return Value:
  193. HRESULT indicating SUCCEEDED() or FAILED()
  194. --*/
  195. {
  196. HRESULT hr = S_OK;
  197. CFaxDataObject * dataObject = NULL;
  198. LONG_PTR cookie;
  199. // DebugPrint(( TEXT("Trace: CFaxComponent::Notify") ));
  200. if( event == MMCN_CONTEXTHELP ) {
  201. MMCPropertyHelp(FAXMMC_HTMLHELP_TOPIC);
  202. }
  203. else if( lpDataObject != NULL) {
  204. dataObject = ExtractOwnDataObject( lpDataObject );
  205. if( dataObject == NULL ) {
  206. return E_UNEXPECTED;
  207. }
  208. cookie = dataObject->GetCookie();
  209. if( cookie == NULL) {
  210. // my static node
  211. assert( pOwner );
  212. hr = pOwner->globalRoot->ResultNotify( this, dataObject, event, arg, param );
  213. } else {
  214. // cast the cookie to a pointer
  215. try {
  216. hr = ((CInternalNode *)cookie)->ResultNotify( this, dataObject, event, arg, param );
  217. } catch ( ... ) {
  218. DebugPrint(( TEXT("Invalid Cookie: 0x%08x"), cookie ));
  219. assert( FALSE ); // got passed an INVALID COOKIE!?!?!?!?
  220. hr = E_UNEXPECTED;
  221. }
  222. }
  223. } else {
  224. // some events do not pass a lpDataObject into Notify.
  225. // we need to handle those events here, if you want
  226. // to handle them at all!!
  227. if( event == MMCN_PROPERTY_CHANGE ) {
  228. if( param != NULL ) {
  229. try {
  230. hr = ((CInternalNode *)param)->ResultNotify( this, NULL, event, arg, param );
  231. } catch ( ... ) {
  232. DebugPrint(( TEXT("Invalid Cookie") ));
  233. assert( FALSE ); // got passed an INVALID COOKIE!?!?!?!?
  234. hr = E_UNEXPECTED;
  235. }
  236. }
  237. }
  238. }
  239. return hr;
  240. }
  241. HRESULT
  242. STDMETHODCALLTYPE
  243. CFaxComponent::Destroy(
  244. IN MMC_COOKIE cookie)
  245. /*++
  246. Routine Description:
  247. This method releases all the aquired console interface in preperation
  248. for the IComponent being destroyed.
  249. Arguments:
  250. None.
  251. Return Value:
  252. HRESULT indicating SUCCEEDED() or FAILED()
  253. --*/
  254. {
  255. DebugPrint(( TEXT("Trace: CFaxComponent::Notify") ));
  256. // the prop sheet count should never be negative
  257. assert( QueryPropSheetCount() >= 0 );
  258. // check to see if any property sheets are up
  259. while( QueryPropSheetCount() > 0 ) {
  260. DebugPrint(( TEXT("Trace: QueryPropSheetCount() %d "), QueryPropSheetCount() ));
  261. // don't allow deletion
  262. GlobalStringTable->PopUpMsg( NULL, IDS_PROP_SHEET_STILL_UP, TRUE, NULL );
  263. }
  264. // release the header object
  265. HRESULT hr = m_pConsole->SetHeader( NULL );
  266. assert( SUCCEEDED( hr ));
  267. if( m_pUnknown != NULL ) {
  268. m_pUnknown->Release();
  269. m_pUnknown = NULL;
  270. }
  271. if( m_pConsole != NULL ) {
  272. m_pConsole->Release();
  273. m_pConsole = NULL;
  274. }
  275. if( m_pConsoleNameSpace != NULL ) {
  276. m_pConsoleNameSpace->Release();
  277. m_pConsoleNameSpace = NULL;
  278. }
  279. if( m_pConsoleVerb != NULL ) {
  280. m_pConsoleVerb->Release();
  281. m_pConsoleVerb = NULL;
  282. }
  283. if( m_pHeaderCtrl != NULL ) {
  284. m_pHeaderCtrl->Release();
  285. m_pHeaderCtrl = NULL;
  286. }
  287. if( m_pImageList != NULL ) {
  288. m_pImageList->Release();
  289. m_pImageList = NULL;
  290. }
  291. if( m_pResultData != NULL ) {
  292. m_pResultData->Release();
  293. m_pResultData = NULL;
  294. }
  295. if( m_pControlbar != NULL ) {
  296. m_pControlbar->Release();
  297. m_pControlbar = NULL;
  298. }
  299. return S_OK;
  300. }
  301. HRESULT
  302. STDMETHODCALLTYPE
  303. CFaxComponent::QueryDataObject(
  304. IN MMC_COOKIE cookie,
  305. IN DATA_OBJECT_TYPES type,
  306. OUT LPDATAOBJECT __RPC_FAR *ppDataObject)
  307. /*++
  308. Routine Description:
  309. This method dispatches DataObjects requests to the appropriate
  310. nodes using the cookie.
  311. Arguments:
  312. cookie - the cookie for the associated node
  313. type - the type of the cookie
  314. ppDataobject - a pointer to the new data object is stored here
  315. Return Value:
  316. HRESULT indicating SUCCEEDED() or FAILED()
  317. --*/
  318. {
  319. // DebugPrint(( TEXT("Trace: CFaxComponent::QueryDataObject") ));
  320. HRESULT hr = S_OK;
  321. if( ppDataObject != NULL ) {
  322. if( cookie == NULL ) {
  323. assert( pOwner );
  324. hr = pOwner->globalRoot->ResultQueryDataObject( this, cookie, type, ppDataObject );
  325. } else {
  326. try {
  327. hr = ((CInternalNode *)cookie)->ResultQueryDataObject( this, cookie, type, ppDataObject );
  328. } catch ( ... ) {
  329. DebugPrint(( TEXT("Invalid Cookie: 0x%08x"), cookie ));
  330. assert( FALSE ); // got passed an INVALID COOKIE!?!?!?!?
  331. hr = E_UNEXPECTED;
  332. }
  333. }
  334. } else {
  335. // bad pointer
  336. assert( FALSE );
  337. hr = E_POINTER;
  338. }
  339. return hr;
  340. }
  341. HRESULT
  342. STDMETHODCALLTYPE
  343. CFaxComponent::GetResultViewType(
  344. IN MMC_COOKIE cookie,
  345. OUT LPOLESTR __RPC_FAR *ppViewType,
  346. OUT long __RPC_FAR *pViewOptions)
  347. /*++
  348. Routine Description:
  349. This method dispatches GetResultViewType requests to the appropriate
  350. nodes using the cookie.
  351. Arguments:
  352. cookie - the cookie for the associated node
  353. ppViewType - the viewtype
  354. ppViewOptions - view options
  355. Return Value:
  356. HRESULT indicating SUCCEEDED() or FAILED()
  357. --*/
  358. {
  359. HRESULT hr = S_OK;
  360. assert ( ppViewType != NULL );
  361. if( ppViewType == NULL ) {
  362. return E_POINTER;
  363. }
  364. assert ( pViewOptions != NULL );
  365. if( pViewOptions == NULL ) {
  366. return E_POINTER;
  367. }
  368. if( cookie == NULL ) {
  369. assert( pOwner );
  370. hr = pOwner->globalRoot->ResultGetResultViewType( this, cookie, ppViewType, pViewOptions );
  371. } else {
  372. try {
  373. hr = ((CInternalNode *)cookie)->ResultGetResultViewType( this, cookie, ppViewType, pViewOptions );
  374. } catch ( ... ) {
  375. DebugPrint(( TEXT("Invalid Cookie: 0x%08x"), cookie ));
  376. assert( FALSE ); // got passed an INVALID COOKIE!?!?!?!?
  377. hr = E_UNEXPECTED;
  378. }
  379. }
  380. return hr;
  381. }
  382. HRESULT
  383. STDMETHODCALLTYPE
  384. CFaxComponent::GetDisplayInfo(
  385. IN OUT RESULTDATAITEM __RPC_FAR *pResultDataItem)
  386. /*++
  387. Routine Description:
  388. This method dispatches DisplayInfo requests to the appropriate
  389. nodes using the cookie in pResultDataItem.
  390. Arguments:
  391. pResultDataItem - struct containing information about the scope item.
  392. Return Value:
  393. HRESULT indicating SUCCEEDED() or FAILED()
  394. --*/
  395. {
  396. // DebugPrint(( TEXT("Trace: CFaxComponent::GetDisplayInfo") ));
  397. LONG_PTR cookie;
  398. HRESULT hr = S_OK;
  399. assert( pResultDataItem != NULL );
  400. if( pResultDataItem == NULL ) {
  401. // oops bad pointer
  402. return E_POINTER;
  403. }
  404. cookie = pResultDataItem->lParam;
  405. if( cookie == NULL ) {
  406. // our top node
  407. assert( pOwner );
  408. hr = pOwner->globalRoot->ResultGetDisplayInfo(this, pResultDataItem);
  409. } else {
  410. // another node
  411. try {
  412. hr = ((CInternalNode *)cookie)->ResultGetDisplayInfo(this, pResultDataItem);
  413. } catch ( ... ) {
  414. DebugPrint(( TEXT("Invalid Cookie: 0x%08x"), cookie ));
  415. //assert( FALSE ); // got passed an INVALID COOKIE!?!?!?!?
  416. hr = E_UNEXPECTED;
  417. }
  418. }
  419. return hr;
  420. }
  421. HRESULT
  422. STDMETHODCALLTYPE
  423. CFaxComponent::CompareObjects(
  424. IN LPDATAOBJECT lpDataObjectA,
  425. IN LPDATAOBJECT lpDataObjectB)
  426. /*++
  427. Routine Description:
  428. This method compares two data object to see if they correspond to
  429. the same object by comparing the cookies.
  430. Arguments:
  431. lpDataObjectA - object A
  432. lpDataObjectB - object B
  433. Return Value:
  434. HRESULT indicating S_OK or S_FALSE. E_UNEXPECTED for an error.
  435. --*/
  436. {
  437. CFaxDataObject * aOBJ = ExtractOwnDataObject( lpDataObjectA );
  438. CFaxDataObject * bOBJ = ExtractOwnDataObject( lpDataObjectB );
  439. if( aOBJ == NULL || bOBJ == NULL ) {
  440. return E_UNEXPECTED;
  441. }
  442. if( aOBJ->GetCookie() == bOBJ->GetCookie() ) {
  443. return S_OK;
  444. } else {
  445. return S_FALSE;
  446. }
  447. }
  448. ////////////////////////////////////////////////////////////////////////////////////////////////////
  449. ////////////////////////////////////////////////////////////////////////////////////////////////////
  450. ////////////////////////////////////////////////////////////////////////////////////////////////////
  451. ////////////////////////////////////////////////////////////////////////////////////////////////////
  452. //
  453. //
  454. // Internal Methods
  455. //
  456. //
  457. void
  458. CFaxComponent::SetOwner(
  459. CFaxComponentData * myOwner )
  460. /*++
  461. Routine Description:
  462. Sets the Component's owner - needed for internal stuff
  463. Arguments:
  464. myOwner - the owner of the IComponent instance.
  465. Return Value:
  466. None.
  467. --*/
  468. {
  469. assert( myOwner != NULL );
  470. pOwner = myOwner;
  471. }
  472. HRESULT
  473. CFaxComponent::InsertIconsIntoImageList()
  474. /*++
  475. Routine Description:
  476. oads the component's result pane icons into an image list
  477. Arguments:
  478. None.
  479. Return Value:
  480. HRESULT indicating SUCCEEDED() or FAILED()
  481. --*/
  482. {
  483. HRESULT hr = E_UNEXPECTED;
  484. assert( pOwner != NULL );
  485. assert( m_pImageList != NULL );
  486. if( m_pImageList != NULL ) {
  487. if( pOwner != NULL ) {
  488. hr = pOwner->InsertIconsIntoImageList( m_pImageList );
  489. }
  490. }
  491. return hr;
  492. }