added some development tools
[windows-sources.git] / developer / VSSDK / VisualStudioIntegration / Common / Source / CPP / VSL / Include / VSLHierarchy.h
blobffc1f918cef483ecf5c8e17a87b6363a3fcfe6e6
1 /***************************************************************************
3 Copyright (c) Microsoft Corporation. All rights reserved.
4 This code is licensed under the Visual Studio SDK license terms.
5 THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF
6 ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY
7 IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR
8 PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.
10 This code is a part of the Visual Studio Library.
12 ***************************************************************************/
14 #ifndef VSLHIERARCHY_H_10C49CA1_2F46_11D3_A504_00C04F5E0BA5
15 #define VSLHIERARCHY_H_10C49CA1_2F46_11D3_A504_00C04F5E0BA5
17 #if _MSC_VER > 1000
18 #pragma once
19 #endif
21 // VSL includes
22 #include <VSLVsSite.h>
23 #include <VSLHierarchyNode.h>
24 #include <VSLControls.h>
26 namespace VSL
29 class IVsHierarchyItem
32 VSL_DECLARE_NONINSTANTIABLE_BASE_CLASS(IVsHierarchyItem)
34 public:
35 typedef IVsHierarchyItem ItemInterface;
37 virtual const GUID& GetGuidProperty(_In_ VSHPROPID propid) const = 0;
39 virtual void SetGuidProperty(_In_ VSHPROPID propid, _In_ REFGUID rguid) = 0;
41 virtual void GetProperty(_In_ VSHPROPID propid, _Out_ VARIANT* pVar) = 0;
43 virtual void SetProperty(_In_ VSHPROPID propid, _In_ VARIANT& rVar) = 0;
45 #ifdef VSL_TEST_HIERARCHY_METHODS_CALLED
46 virtual const ATL::CComBSTR& GetCanonicalName() const = 0;
48 virtual VSITEMID ParseCanonicalName(_In_ LPCOLESTR pszName) const = 0;
49 #endif // VSL_TEST_HIERARCHY_METHODS_CALLED
51 virtual VSITEMID GetVSITEMID() const = 0;
53 #ifdef VSL_TEST_HIERARCHY_METHODS_CALLED
54 virtual const GUID& GetTypeGuid() const = 0;
55 #endif // VSL_TEST_HIERARCHY_METHODS_CALLED
57 virtual IVsHierarchyEvents* GetIVsHierarchyEvents() = 0;
60 class IVsUIHierarchyItem :
61 public IVsHierarchyItem
64 VSL_DECLARE_NONINSTANTIABLE_BASE_CLASS(IVsUIHierarchyItem)
66 public:
67 typedef IVsUIHierarchyItem ItemInterface;
69 enum
71 SupportsUI
74 virtual IOleCommandTarget* GetIOleCommandTarget() = 0;
76 virtual IDispatch* GetIDispatch() = 0;
78 #ifdef VSL_TEST_HIERARCHY_METHODS_CALLED
79 virtual IVsUserContext* GetIVsUserContext() = 0;
80 #endif // VSL_TEST_HIERARCHY_METHODS_CALLED
82 virtual bool IsVisible() const = 0;
84 virtual const GUID& GetCmdUIGuid() const = 0;
86 virtual const ATL::CComBSTR& GetCaption() const = 0;
88 #ifdef VSL_TEST_HIERARCHY_METHODS_CALLED
89 virtual const ATL::CComBSTR& GetName() const = 0;
91 virtual const ATL::CComBSTR& GetEditLabel() const = 0;
92 virtual void SetEditLabel(BSTR rbstrEditLabel) = 0;
93 #endif // VSL_TEST_HIERARCHY_METHODS_CALLED
95 virtual UINT GetIconIndex() const = 0;
97 virtual HICON GetIconHandle() const = 0;
99 virtual HICON GetOpenFolderIconHandle() const = 0;
101 virtual UINT GetOpenFolderIconIndex() const = 0;
103 virtual bool IsExpandable() const = 0;
105 virtual bool IsExpandedByDefault() const = 0;
107 virtual bool IsExpanded() const = 0;
109 virtual void SetExpanded(bool bExpanded) = 0;
112 template <class ItemInterface_T = IVsHierarchyItem>
113 class IVsHierarchyRootItem
116 VSL_DECLARE_NONINSTANTIABLE_BASE_CLASS(IVsHierarchyRootItem)
118 public:
119 typedef ItemInterface_T ItemInterface;
121 virtual ItemInterface& GetItem(_In_ VSITEMID itemid) = 0;
123 virtual const GUID& GetGuidProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid) const = 0;
125 virtual void SetGuidProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _In_ REFGUID rguid) = 0;
127 virtual void GetProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _Out_ VARIANT* pVar) const = 0;
129 virtual void SetProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _In_ VARIANT& rVar) = 0;
132 template <class Base_T = IVsHierarchyRootItem<IVSUIHierarchyItem> >
133 class IVsUIHierarchyRootItem :
134 public Base_T
137 VSL_DECLARE_NONINSTANTIABLE_BASE_CLASS(IVsUIHierarchyRootItem)
139 public:
141 virtual ImageListWin32Control& GetIconImageList() = 0;
144 #pragma warning(push)
145 #pragma warning(disable : 4355) // 'this' : used in base member initializer list
146 // Warning disabled as this is safe, as the node just holds the item, but doesn't call into it
147 // This must be disable at the class scope rather then the at the scope of each constructor
149 template <
150 class Base_T = IVsHierarchyItem,
151 class HierarchyNode_T = HierarchyNode<HierarchyNodeTraits<Base_T::ItemInterface*> > >
152 class VsHierarchyItemBase :
153 public Base_T
155 private:
157 const VsHierarchyItemBase& operator=(const VsHierarchyItemBase& rToCopy);
159 public:
161 typedef typename HierarchyNode_T HierarchyNode;
163 protected:
165 VsHierarchyItemBase():
166 m_pNode()
168 // No default construction allowed, this method should never actually
169 // be called, but it needs to be present to compile correctly in some circumstances
170 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED);
173 VsHierarchyItemBase(typename HierarchyNode::Item& item):
174 m_pNode(new HierarchyNode(item))
178 ~VsHierarchyItemBase()
180 // Don't delete m_pNode, it's parent node owns it
183 public:
184 explicit VsHierarchyItemBase(VsHierarchyItemBase& rParent):
185 m_pNode(rParent.m_pNode->AddDescendant(this))
189 // compile generated destructor is fine
190 // Except for the root node, all of the nodes are deleted by their parent node
191 // The root item is responsible for deleting the root node
193 virtual const GUID& GetGuidProperty(_In_ VSHPROPID propid) const
195 switch(propid)
197 // intentional fall through below
198 case VSHPROPID_Parent:
199 case VSHPROPID_FirstChild:
200 case VSHPROPID_NextSibling:
201 case VSHPROPID_Root:
202 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
203 break;
204 case VSHPROPID_TypeGuid:
205 __if_exists(ItemInterface::GetTypeGuid)
207 return GetTypeGuid();
209 break;
210 case VSHPROPID_SaveName:
211 case VSHPROPID_Caption:
212 case VSHPROPID_IconImgList:
213 case VSHPROPID_IconIndex:
214 case VSHPROPID_Expandable:
215 case VSHPROPID_ExpandByDefault:
216 case VSHPROPID_Name: // == VSHPROPID_ProjectName
217 case VSHPROPID_IconHandle:
218 case VSHPROPID_OpenFolderIconHandle:
219 case VSHPROPID_OpenFolderIconIndex:
220 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
221 break;
222 case VSHPROPID_CmdUIGuid:
223 __if_exists(ItemInterface::SupportsUI)
225 return GetCmdUIGuid();
227 break;
228 // intentional fall through below
229 case VSHPROPID_SelContainer:
230 case VSHPROPID_BrowseObject:
231 case VSHPROPID_AltHierarchy:
232 case VSHPROPID_AltItemid:
233 case VSHPROPID_ProjectDir:
234 case VSHPROPID_SortPriority:
235 case VSHPROPID_UserContext:
236 case VSHPROPID_EditLabel:
237 case VSHPROPID_ExtObject:
238 case VSHPROPID_ExtSelectedItem:
239 case VSHPROPID_StateIconIndex:
240 case VSHPROPID_TypeName: // == VSHPROPID_ProjectType
241 case VSHPROPID_HandlesOwnReload: // == VSHPROPID_ReloadableProjectFile
242 case VSHPROPID_ParentHierarchy:
243 case VSHPROPID_ParentHierarchyItemid:
244 case VSHPROPID_ItemDocCookie:
245 case VSHPROPID_Expanded:
246 case VSHPROPID_ConfigurationProvider:
247 case VSHPROPID_ImplantHierarchy:
248 case VSHPROPID_OwnerKey:
249 case VSHPROPID_StartupServices:
250 case VSHPROPID_FirstVisibleChild:
251 case VSHPROPID_NextVisibleSibling:
252 case VSHPROPID_IsHiddenItem:
253 case VSHPROPID_IsNonMemberItem:
254 case VSHPROPID_IsNonLocalStorage:
255 case VSHPROPID_StorageType:
256 case VSHPROPID_ItemSubType:
257 case VSHPROPID_OverlayIconIndex:
258 case VSHPROPID_DefaultNamespace:
259 case VSHPROPID_IsNonSearchable:
260 case VSHPROPID_IsFindInFilesForegroundOnly:
261 case VSHPROPID_CanBuildFromMemory:
262 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
263 break;
264 case VSHPROPID_PreferredLanguageSID:
265 __if_exists(ItemInterface::GetPreferredLanguageSID)
267 return GetPreferredLanguageSID();
269 break;
270 // intentional fall through below
271 case VSHPROPID_ShowProjInSolutionPage:
272 case VSHPROPID_AllowEditInRunMode:
273 case VSHPROPID_IsNewUnsavedItem:
274 case VSHPROPID_ShowOnlyItemCaption:
275 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
276 break;
277 case VSHPROPID_ProjectIDGuid:
278 __if_exists(ItemInterface::GetProjectIDGuid)
280 return GetProjectIDGuid();
282 break;
283 // intentional fall through below
284 case VSHPROPID_DesignerVariableNaming:
285 case VSHPROPID_DesignerFunctionVisibility:
286 case VSHPROPID_HasEnumerationSideEffects:
287 case VSHPROPID_DefaultEnableBuildProjectCfg:
288 case VSHPROPID_DefaultEnableDeployProjectCfg:
289 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
290 break;
291 default:
292 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
295 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
296 return GUID_NULL;
299 virtual void SetGuidProperty(_In_ VSHPROPID propid, _In_ REFGUID rguid)
301 (rguid);
302 switch(propid)
304 // intentional fall through below
305 case VSHPROPID_Parent:
306 case VSHPROPID_FirstChild:
307 case VSHPROPID_NextSibling:
308 case VSHPROPID_Root:
309 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
310 break;
311 case VSHPROPID_TypeGuid:
312 break; // Property can't be set
313 // intentional fall through below
314 case VSHPROPID_SaveName:
315 case VSHPROPID_Caption:
316 case VSHPROPID_IconImgList:
317 case VSHPROPID_IconIndex:
318 case VSHPROPID_Expandable:
319 case VSHPROPID_ExpandByDefault:
320 case VSHPROPID_Name: // == VSHPROPID_ProjectName
321 case VSHPROPID_IconHandle:
322 case VSHPROPID_OpenFolderIconHandle:
323 case VSHPROPID_OpenFolderIconIndex:
324 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
325 break;
326 case VSHPROPID_CmdUIGuid:
327 break; // Property can't be set
328 // intentional fall through below
329 case VSHPROPID_SelContainer:
330 case VSHPROPID_BrowseObject:
331 case VSHPROPID_AltHierarchy:
332 case VSHPROPID_AltItemid:
333 case VSHPROPID_ProjectDir:
334 case VSHPROPID_SortPriority:
335 case VSHPROPID_UserContext:
336 case VSHPROPID_EditLabel:
337 case VSHPROPID_ExtObject:
338 case VSHPROPID_ExtSelectedItem:
339 case VSHPROPID_StateIconIndex:
340 case VSHPROPID_TypeName: // == VSHPROPID_ProjectType
341 case VSHPROPID_HandlesOwnReload: // == VSHPROPID_ReloadableProjectFile
342 case VSHPROPID_ParentHierarchy:
343 case VSHPROPID_ParentHierarchyItemid:
344 case VSHPROPID_ItemDocCookie:
345 case VSHPROPID_Expanded:
346 case VSHPROPID_ConfigurationProvider:
347 case VSHPROPID_ImplantHierarchy:
348 case VSHPROPID_OwnerKey:
349 case VSHPROPID_StartupServices:
350 case VSHPROPID_FirstVisibleChild:
351 case VSHPROPID_NextVisibleSibling:
352 case VSHPROPID_IsHiddenItem:
353 case VSHPROPID_IsNonMemberItem:
354 case VSHPROPID_IsNonLocalStorage:
355 case VSHPROPID_StorageType:
356 case VSHPROPID_ItemSubType:
357 case VSHPROPID_OverlayIconIndex:
358 case VSHPROPID_DefaultNamespace:
359 case VSHPROPID_IsNonSearchable:
360 case VSHPROPID_IsFindInFilesForegroundOnly:
361 case VSHPROPID_CanBuildFromMemory:
362 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
363 break;
364 case VSHPROPID_PreferredLanguageSID:
365 break; // Property can't be set
366 // intentional fall through below
367 case VSHPROPID_ShowProjInSolutionPage:
368 case VSHPROPID_AllowEditInRunMode:
369 case VSHPROPID_IsNewUnsavedItem:
370 case VSHPROPID_ShowOnlyItemCaption:
371 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
372 break;
373 case VSHPROPID_ProjectIDGuid:
374 break; // Property can't be set
375 // intentional fall through below
376 case VSHPROPID_DesignerVariableNaming:
377 case VSHPROPID_DesignerFunctionVisibility:
378 case VSHPROPID_HasEnumerationSideEffects:
379 case VSHPROPID_DefaultEnableBuildProjectCfg:
380 case VSHPROPID_DefaultEnableDeployProjectCfg:
381 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling GetProperty
382 break;
383 default:
384 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
387 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
390 virtual void GetProperty(_In_ VSHPROPID propid, _Out_ VARIANT* pVar)
392 switch(propid)
394 case VSHPROPID_Parent: // intentional fall through
395 case VSHPROPID_FirstChild:
396 GetRelativesVSITEMID(propid, pVar);
397 return;
398 case VSHPROPID_NextSibling: // intentional fall through
399 case VSHPROPID_Root:
400 VSL_ASSERT(false); // Should never get here, root should take care of this
401 break;
402 case VSHPROPID_TypeGuid:
403 break; // Should be calling GetPropertyGuid
404 case VSHPROPID_SaveName:
405 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
406 break;
407 case VSHPROPID_Caption:
408 __if_exists(ItemInterface::SupportsUI)
410 ATL::CComVariant var(GetCaption());
411 var.Detach(pVar);
412 return;
414 __if_not_exists(ItemInterface::SupportsUI)
416 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
418 case VSHPROPID_IconImgList:
419 VSL_ASSERT(false); // Should never get here, root should take care of this
420 break;
421 case VSHPROPID_IconIndex:
422 __if_exists(ItemInterface::SupportsUI)
424 ATL::CComVariant var(static_cast<long>(GetIconIndex()));
425 var.Detach(pVar);
426 return;
428 // intentional fall through
429 case VSHPROPID_Expandable:
430 __if_exists(ItemInterface::SupportsUI)
432 ATL::CComVariant var(IsExpandable());
433 var.Detach(pVar);
434 return;
436 // intentional fall through
437 case VSHPROPID_ExpandByDefault:
438 __if_exists(ItemInterface::SupportsUI)
440 ATL::CComVariant var(IsExpandedByDefault());
441 var.Detach(pVar);
442 return;
444 __if_not_exists(ItemInterface::SupportsUI)
446 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
448 break;
449 case VSHPROPID_Name: // == VSHPROPID_ProjectName
450 __if_exists(ItemInterface::GetName)
452 ATL::CComVariant var(GetName());
453 var.Detach(pVar);
454 return;
456 __if_not_exists(ItemInterface::GetName)
458 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
460 break;
461 case VSHPROPID_IconHandle:
462 __if_exists(ItemInterface::SupportsUI)
464 #pragma warning(push)
465 #pragma warning(disable : 4311) // 'reinterpret_cast' : pointer truncation from 'HICON' to 'long'
466 ATL::CComVariant var(reinterpret_cast<long>(GetIconHandle()));
467 #pragma warning(pop)
468 var.Detach(pVar);
469 return;
471 __if_not_exists(ItemInterface::SupportsUI)
473 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
475 break;
476 case VSHPROPID_OpenFolderIconHandle:
477 __if_exists(ItemInterface::SupportsUI)
479 #pragma warning(push)
480 #pragma warning(disable : 4311) // 'reinterpret_cast' : pointer truncation from 'HICON' to 'long'
481 ATL::CComVariant var(reinterpret_cast<long>(GetOpenFolderIconHandle()));
482 #pragma warning(pop)
483 var.Detach(pVar);
484 return;
486 __if_not_exists(ItemInterface::SupportsUI)
488 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
490 break;
491 case VSHPROPID_OpenFolderIconIndex:
492 __if_exists(ItemInterface::SupportsUI)
494 ATL::CComVariant var(static_cast<long>(GetOpenFolderIconIndex()));
495 var.Detach(pVar);
496 return;
498 __if_not_exists(ItemInterface::SupportsUI)
500 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
502 break;
503 case VSHPROPID_CmdUIGuid:
504 break; // Should be calling GetPropertyGuid
505 case VSHPROPID_SelContainer:
506 __if_exists(ItemInterface::GetISelectionContainer)
508 ISelectionContainer* pISelectionContainer = GetISelectionContainer();
509 // Visual Studio will try VSHPROPID_BrowseObject instead
510 VSL_CHECKPOINTER(pISelectionContainer, E_NOTIMPL);
511 ATL::CComVariant var(pISelectionContainer);
512 var.Detach(pVar);
513 return;
515 __if_not_exists(ItemInterface::GetISelectionContainer)
517 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
519 break;
520 case VSHPROPID_BrowseObject:
521 __if_exists(ItemInterface::SupportsUI)
523 IDispatch* pIDispatch = GetIDispatch();
524 #ifdef DEBUG
525 __if_not_exists(ItemInterface::GetISelectionContainer)
527 if(pIDispatch == NULL)
529 VSL_ASSERTEX(false, L"GetIDispatch is required to return not NULL if GetISelectionContainer is not supported!");
532 #endif // DEBUG
533 VSL_CHECKPOINTER(pIDispatch, E_NOTIMPL);
534 ATL::CComVariant var(pIDispatch);
535 var.Detach(pVar);
536 return;
538 // intentional fall through here and below
539 case VSHPROPID_AltHierarchy:
540 case VSHPROPID_AltItemid:
541 case VSHPROPID_ProjectDir:
542 case VSHPROPID_SortPriority:
543 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
544 break;
545 case VSHPROPID_UserContext:
546 __if_exists(ItemInterface::GetIVsUserContext)
548 IVsUserContext* pIVsUserContext = GetIVsUserContext();
549 VSL_CHECKPOINTER(pIVsUserContext, E_NOTIMPL);
550 ATL::CComVariant var(pIVsUserContext);
551 var.Detach(pVar);
552 return;
554 __if_not_exists(ItemInterface::GetIVsUserContext)
556 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
558 break;
559 case VSHPROPID_EditLabel:
560 __if_exists(ItemInterface::GetEditLabel)
562 ATL::CComVariant var(GetEditLabel());
563 var.Detach(pVar);
564 return;
566 // intentional fall through here and below
567 case VSHPROPID_ExtObject:
568 case VSHPROPID_ExtSelectedItem:
569 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
570 break;
571 case VSHPROPID_StateIconIndex:
572 __if_exists(ItemInterface::SupportsSourceControl)
574 ATL::CComVariant var(static_cast<long>(GetStateIconIndex()));
575 var.Detach(pVar);
576 return;
578 __if_not_exists(ItemInterface::SupportsSourceControl)
580 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
582 break;
583 // intentional fall through below
584 case VSHPROPID_TypeName: // == VSHPROPID_ProjectType
585 case VSHPROPID_HandlesOwnReload: // == VSHPROPID_ReloadableProjectFile
586 case VSHPROPID_ParentHierarchy: // FUTURE - handle this here or on the root?
587 case VSHPROPID_ParentHierarchyItemid: // FUTURE - handle this here or on the root?
588 case VSHPROPID_ItemDocCookie:
589 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
590 break;
591 case VSHPROPID_Expanded:
592 __if_exists(ItemInterface::SupportsUI)
594 ATL::CComVariant var(IsExpanded());
595 var.Detach(pVar);
596 return;
598 __if_not_exists(ItemInterface::SupportsUI)
600 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
602 break;
603 case VSHPROPID_ConfigurationProvider:
604 case VSHPROPID_ImplantHierarchy: // FUTURE - handle this here or on the root?
605 case VSHPROPID_OwnerKey: // FUTURE - handle this here or on the root?
606 case VSHPROPID_StartupServices:
607 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
608 break;
609 case VSHPROPID_FirstVisibleChild:
610 GetRelativesVSITEMID(propid, pVar);
611 return;
612 case VSHPROPID_NextVisibleSibling:
613 VSL_ASSERT(false); // Should never get here, root should take care of this
614 break;
615 case VSHPROPID_IsHiddenItem:
616 __if_exists(ItemInterface::SupportsUI)
618 ATL::CComVariant var(!IsVisible());
619 var.Detach(pVar);
620 return;
622 // intentional fall through here and below
623 case VSHPROPID_IsNonMemberItem:
624 case VSHPROPID_IsNonLocalStorage:
625 case VSHPROPID_StorageType:
626 case VSHPROPID_ItemSubType:
627 case VSHPROPID_OverlayIconIndex:
628 case VSHPROPID_DefaultNamespace:
629 case VSHPROPID_IsNonSearchable:
630 case VSHPROPID_IsFindInFilesForegroundOnly:
631 case VSHPROPID_CanBuildFromMemory:
632 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
633 break;
634 case VSHPROPID_PreferredLanguageSID:
635 break; // Should be calling GetPropertyGuid
636 // intentional fall through below
637 case VSHPROPID_ShowProjInSolutionPage:
638 case VSHPROPID_AllowEditInRunMode:
639 case VSHPROPID_IsNewUnsavedItem:
640 case VSHPROPID_ShowOnlyItemCaption:
641 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
642 break;
643 case VSHPROPID_ProjectIDGuid:
644 break; // Should be calling GetPropertyGuid
645 // intentional fall through below
646 case VSHPROPID_DesignerVariableNaming:
647 case VSHPROPID_DesignerFunctionVisibility:
648 case VSHPROPID_HasEnumerationSideEffects:
649 case VSHPROPID_DefaultEnableBuildProjectCfg:
650 case VSHPROPID_DefaultEnableDeployProjectCfg:
651 // __VSHPROPID2 - new for Visual Studio 8.0
652 case VSHPROPID_PropertyPagesCLSIDList:
653 case VSHPROPID_CfgPropertyPagesCLSIDList:
654 case VSHPROPID_ExtObjectCATID:
655 case VSHPROPID_BrowseObjectCATID:
656 case VSHPROPID_CfgBrowseObjectCATID:
657 case VSHPROPID_AddItemTemplatesGuid:
658 case VSHPROPID_ChildrenEnumerated:
659 case VSHPROPID_StatusBarClientText:
660 case VSHPROPID_DebuggeeProcessId:
661 case VSHPROPID_IsLinkFile:
662 case VSHPROPID_KeepAliveDocument:
663 case VSHPROPID_SupportsProjectDesigner:
664 case VSHPROPID_IntellisenseUnknown:
665 case VSHPROPID_IsUpgradeRequired:
666 case VSHPROPID_DesignerHiddenCodeGeneration:
667 case VSHPROPID_SuppressOutOfDateMessageOnBuild:
668 case VSHPROPID_Container:
669 case VSHPROPID_UseInnerHierarchyIconList:
670 case VSHPROPID_EnableDataSourceWindow:
671 case VSHPROPID_AppTitleBarTopHierarchyName:
672 case VSHPROPID_DebuggerSourcePaths:
673 case VSHPROPID_CategoryGuid:
674 case VSHPROPID_DisableApplicationSettings:
675 case VSHPROPID_ProjectDesignerEditor:
676 case VSHPROPID_PriorityPropertyPagesCLSIDList:
677 case VSHPROPID_NoDefaultNestedHierSorting:
678 case VSHPROPID_ExcludeFromExportItemTemplate:
679 case VSHPROPID_SupportedMyApplicationTypes:
680 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
681 break;
682 default:
683 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
686 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED);
689 virtual void SetProperty(_In_ VSHPROPID propid, _In_ VARIANT& rVar)
691 (rVar);
692 switch(propid)
694 // Intentional fall through below
695 case VSHPROPID_Parent:
696 case VSHPROPID_FirstChild:
697 case VSHPROPID_NextSibling:
698 case VSHPROPID_Root:
699 break; // Property can't be set
700 case VSHPROPID_TypeGuid:
701 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling SetPropertyGuid
702 break;
703 // intentional fall through below
704 case VSHPROPID_SaveName:
705 case VSHPROPID_Caption:
706 case VSHPROPID_IconImgList:
707 case VSHPROPID_IconIndex:
708 case VSHPROPID_Expandable:
709 case VSHPROPID_ExpandByDefault:
710 case VSHPROPID_Name: // == VSHPROPID_ProjectName
711 case VSHPROPID_IconHandle:
712 case VSHPROPID_OpenFolderIconHandle:
713 case VSHPROPID_OpenFolderIconIndex:
714 break; // Property can't be set
715 case VSHPROPID_CmdUIGuid:
716 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling SetPropertyGuid
717 break;
718 // intentional fall through below
719 case VSHPROPID_SelContainer:
720 case VSHPROPID_BrowseObject:
721 case VSHPROPID_AltHierarchy:
722 case VSHPROPID_AltItemid:
723 case VSHPROPID_ProjectDir:
724 case VSHPROPID_SortPriority:
725 case VSHPROPID_UserContext:
726 break; // Property can't be set
727 case VSHPROPID_EditLabel:
728 __if_exists(ItemInterface::SetEditLabel)
730 VSL_CHECKBOOLEAN(rVar.vt == VT_BSTR, DISP_E_BADVARTYPE);
731 SetEditLabel(rVar.bstrVal);
732 return;
734 break;
735 // intentional fall through below
736 case VSHPROPID_ExtObject:
737 case VSHPROPID_ExtSelectedItem:
738 case VSHPROPID_StateIconIndex:
739 case VSHPROPID_TypeName: // == VSHPROPID_ProjectType
740 case VSHPROPID_HandlesOwnReload: // == VSHPROPID_ReloadableProjectFile
741 case VSHPROPID_ParentHierarchy: // FUTURE - handle this here or on the root?
742 case VSHPROPID_ParentHierarchyItemid: // FUTURE - handle this here or on the root?
743 case VSHPROPID_ItemDocCookie:
744 break; // Property can't be set
745 case VSHPROPID_Expanded:
746 __if_exists(ItemInterface::SupportsUI)
748 VSL_CHECKBOOLEAN(rVar.vt == VT_BOOL, DISP_E_BADVARTYPE);
749 SetExpanded(rVar.boolVal != VARIANT_FALSE);
750 return;
752 // else property can't be set
753 break;
754 case VSHPROPID_ConfigurationProvider:
755 case VSHPROPID_ImplantHierarchy:
756 case VSHPROPID_OwnerKey: // FUTURE - handle this here or on the root?
757 case VSHPROPID_StartupServices:
758 case VSHPROPID_FirstVisibleChild:
759 case VSHPROPID_NextVisibleSibling:
760 case VSHPROPID_IsHiddenItem:
761 case VSHPROPID_IsNonMemberItem:
762 case VSHPROPID_IsNonLocalStorage:
763 case VSHPROPID_StorageType:
764 case VSHPROPID_ItemSubType:
765 case VSHPROPID_OverlayIconIndex:
766 case VSHPROPID_DefaultNamespace:
767 case VSHPROPID_IsNonSearchable:
768 case VSHPROPID_IsFindInFilesForegroundOnly:
769 case VSHPROPID_CanBuildFromMemory:
770 break; // Property can't be set
771 case VSHPROPID_PreferredLanguageSID:
772 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling SetPropertyGuid
773 break;
774 // intentional fall through below
775 case VSHPROPID_ShowProjInSolutionPage:
776 case VSHPROPID_AllowEditInRunMode:
777 case VSHPROPID_IsNewUnsavedItem:
778 case VSHPROPID_ShowOnlyItemCaption:
779 break; // Property can't be set
780 case VSHPROPID_ProjectIDGuid:
781 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED); // Should be calling SetPropertyGuid
782 break;
783 // intentional fall through below
784 case VSHPROPID_DesignerVariableNaming:
785 case VSHPROPID_DesignerFunctionVisibility:
786 case VSHPROPID_HasEnumerationSideEffects:
787 case VSHPROPID_DefaultEnableBuildProjectCfg:
788 case VSHPROPID_DefaultEnableDeployProjectCfg:
789 break; // Property can't be set
790 default:
791 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
794 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
797 virtual VSITEMID GetVSITEMID() const
799 return reinterpret_cast<VSITEMID>(static_cast<HierarchyNode::Item>(const_cast<VsHierarchyItemBase*>(this)));
802 virtual IVsHierarchyEvents* GetIVsHierarchyEvents()
804 return GetRoot()->GetIVsHierarchyEvents();
807 protected:
809 void FirePropertyChanged(VSHPROPID propid)
811 VSL_CHECKHRESULT(GetIVsHierarchyEvents()->OnPropertyChanged(GetVSITEMID(), propid, 0));
814 void Delete()
816 m_pNode->GetParent()->RemoveDescendant(m_pNode);
817 // instance is invalid now
820 HierarchyNode* const m_pNode;
822 private:
824 IVsHierarchyItem* GetRoot()
826 HierarchyNode* pNodeParent = m_pNode;
827 HierarchyNode* pNode = m_pNode;
828 while(NULL != (pNode = pNode->GetParent()))
830 pNodeParent = pNode;
832 return **pNodeParent;
835 void GetRelativesVSITEMID(_In_ VSHPROPID propid, _Out_ VARIANT* pVar) const
837 VSITEMID requestedId = VSITEMID_NIL;
839 switch(propid)
841 case VSHPROPID_Parent:
842 requestedId = (**(m_pNode->GetParent()))->GetVSITEMID();
843 break;
844 case VSHPROPID_FirstChild:
845 requestedId = (***(GetDescendantContainer().begin()))->GetVSITEMID();
846 break;
847 case VSHPROPID_FirstVisibleChild:
849 __if_exists(ItemInterface::SupportsUI)
851 HierarchyNode::DescendantContainer& rContainer = GetDescendantContainer();
852 for(HierarchyNode::iterator i = rContainer.begin(); i != rContainer.end(); ++i)
854 if((***(i))->IsVisible())
856 requestedId = (***(i))->GetVSITEMID();
857 break;
861 __if_not_exists(ItemInterface::SupportsUI)
863 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
866 break;
867 default:
868 VSL_ASSERT(false); // PARANOID - should never get here
871 ATL::CComVariant var(static_cast<__int32>(requestedId), VT_I4);
872 var.Detach(pVar);
875 typename HierarchyNode::DescendantContainer& GetDescendantContainer() const
877 HierarchyNode::DescendantContainer& rContainer = m_pNode->GetDescendantContainer();
878 VSL_CHECKBOOLEAN(!rContainer.empty(), E_INVALIDARG);
879 return rContainer;
882 #pragma warning(pop)
884 template <class Base_T = VsHierarchyItemBase<IVsUIHierarchyItem> >
885 class VsUIHierarchyItemBase :
886 public Base_T
889 VSL_DECLARE_NONINSTANTIABLE_BASE_CLASS(VsUIHierarchyItemBase)
891 protected:
893 typedef Base_T BaseClass; // Note using the name Base causes problems with the Base template parameter for CComObject
895 VsUIHierarchyItemBase(typename HierarchyNode::Item& item):
896 Base_T(item),
897 m_bExpanded(false)
901 public:
902 VsUIHierarchyItemBase(Base_T& rParent):
903 Base_T(rParent),
904 m_bExpanded(false)
908 #ifdef VSL_TEST_HIERARCHY_METHODS_CALLED
909 virtual ISelectionContainer* GetISelectionContainer()
911 return NULL;
914 virtual IVsUserContext* GetIVsUserContext()
916 return NULL;
918 #endif // VSL_TEST_HIERARCHY_METHODS_CALLED
920 virtual bool IsVisible() const
922 return true;
925 virtual UINT GetIconIndex() const
927 // indicates that Visual Studio should ask for the icon handle instead
928 VSL_CREATE_ERROR_HRESULT(DISP_E_MEMBERNOTFOUND);
929 return 0;
932 virtual HICON GetIconHandle() const
934 // If the hierarchy object doesn't support IVsProject then VS can not get the document path
935 // in order to try to get the file's system icon, so this is the last resort, as it is called after GetIconIndex
936 __if_not_exists(ItemInterface::SupportsProject)
938 VSL_ASSERTEX(false, L"No project UI hierarchy item has no valid icon index and no icon handle, so the item can not be displayed");
940 // indicates that Visual Studio should ask IVsProject to get a file path and use that file's associated icon instead
941 VSL_CREATE_ERROR_HRESULT(DISP_E_MEMBERNOTFOUND);
942 return NULL;
945 virtual HICON GetOpenFolderIconHandle() const
947 return GetIconHandle();
950 virtual UINT GetOpenFolderIconIndex() const
952 return GetIconIndex();
955 virtual bool IsExpandable() const
957 return m_pNode->HasDescendants();
960 virtual bool IsExpandedByDefault() const
962 return false;
965 virtual bool IsExpanded() const
967 return m_bExpanded;
970 virtual void SetExpanded(bool bExpanded)
972 m_bExpanded = bExpanded;
975 private:
977 bool m_bExpanded;
980 template <
981 class BaseImpl_T = VsHierarchyItemBase<>,
982 class RootInterface_T = IVsHierarchyRootItem<BaseImpl_T::ItemInterface> >
983 class VsHierarchyRootItemBase :
984 public BaseImpl_T,
985 public RootInterface_T
987 public:
988 typedef typename BaseImpl_T BaseImpl;
989 typedef typename BaseImpl::ItemInterface ItemInterface;
991 VsHierarchyRootItemBase(ItemInterface* pInterface):
992 BaseImpl_T(pInterface),
993 m_pSelection(NULL)
997 protected:
998 ~VsHierarchyRootItemBase()
1002 public:
1003 void Dispose()
1005 // The root node will delete each of it's children, and they will delete their children, and so on...
1006 // Destruction of the node will destory the item it contains, including this instance, so this
1007 // instance is invalid after this delete.
1008 delete m_pNode;
1011 virtual VSITEMID GetVSITEMID() const
1013 return VSITEMID_ROOT;
1016 virtual IVsHierarchyEvents* GetIVsHierarchyEvents()
1018 // Derived class needs to implement this properly
1019 VSL_CREATE_ERROR_HRESULT(E_UNEXPECTED);
1020 return NULL;
1023 virtual ItemInterface& GetItem(_In_ VSITEMID itemid)
1025 VSL_CHECKBOOLEAN(itemid != VSITEMID_NIL, E_INVALIDARG);
1027 if(VSITEMID_ROOT == itemid)
1029 return *this;
1032 if(VSITEMID_SELECTION == itemid)
1034 VSL_CHECKPOINTER(m_pSelection, E_UNEXPECTED);
1035 return *m_pSelection;
1038 BaseImpl_T::HierarchyNode::ItemContainer* pItem = m_pNode->FindItemContainer(ItemIdToItem(itemid));
1039 VSL_CHECKPOINTER(pItem, E_INVALIDARG);
1040 return **pItem;
1043 virtual const GUID& GetGuidProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid) const
1045 return GetItem(itemid).GetGuidProperty(propid);
1048 virtual void SetGuidProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _In_ REFGUID rguid)
1050 GetItem(itemid).SetGuidProperty(propid, rguid);
1053 virtual void GetProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _Out_ VARIANT* pVar) const
1055 VSITEMID requestedId = VSITEMID_ROOT;
1057 switch(propid)
1059 case VSHPROPID_Root:
1060 break;
1061 case VSHPROPID_NextSibling:
1062 requestedId = ItemToItemId(GetNextSibling(itemid));
1063 break;
1064 case VSHPROPID_NextVisibleSibling:
1065 requestedId = ItemToItemId(GetNextVisibleSibling(itemid));
1066 break;
1067 case VSHPROPID_IconImgList:
1068 __if_exists(ItemInterface::SupportsUI)
1070 // VS only get's the image list from the root item, which means that it is global
1071 // for the entire hierarchy.
1072 #pragma warning(push)
1073 #pragma warning(disable : 4311) // 'reinterpret_cast' : pointer truncation from 'HIMAGELIST' to 'long'
1074 ATL::CComVariant var(reinterpret_cast<long>(static_cast<HIMAGELIST>(const_cast<VsHierarchyRootItemBase*>(this)->GetIconImageList())));
1075 #pragma warning(pop)
1076 var.Detach(pVar);
1077 return;
1079 default:
1080 GetItem(itemid).GetProperty(propid, pVar);
1081 return;
1084 ATL::CComVariant var(static_cast<__int32>(requestedId), VT_I4);
1085 var.Detach(pVar);
1088 virtual void SetProperty(_In_ VSITEMID itemid, _In_ VSHPROPID propid, _In_ VARIANT& rVar)
1090 GetItem(itemid).SetProperty(propid, rVar);
1093 virtual ImageListWin32Control& GetIconImageList()
1095 // indicates that Visual Studio will need to use icon handle for each item
1096 // of if no icon is provided, then attepmt to use IVsProject to get a file path
1097 // and use that file's associated icon
1098 VSL_CREATE_ERROR_HRESULT(DISP_E_MEMBERNOTFOUND);
1099 #pragma warning(push)
1100 #pragma warning(disable : 4239 4172)
1101 return ImageListWin32Control();
1102 #pragma warning(pop)
1105 protected:
1107 void SetSelection(ItemInterface* pSelection)
1109 m_pSelection = pSelection;
1112 private:
1113 ItemInterface& GetItem(_In_ VSITEMID itemid) const
1115 return const_cast<VsHierarchyRootItemBase*>(this)->GetItem(itemid);
1118 typename BaseImpl_T::HierarchyNode::Item ItemIdToItem(_In_ VSITEMID itemid) const
1120 return reinterpret_cast<BaseImpl_T::HierarchyNode::Item>(itemid);
1123 VSITEMID ItemToItemId(_In_ const typename HierarchyNode::Item& item) const
1125 return item != NULL ? item->GetVSITEMID() : VSITEMID_NIL;
1128 VSITEMID TransformVSITEMIDForSibilingSearch(_In_ VSITEMID itemid) const
1130 if(VSITEMID_ROOT == itemid)
1132 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
1135 if(VSITEMID_SELECTION == itemid)
1137 if(m_pSelection == static_cast<const ItemInterface* const>(this))
1139 VSL_CREATE_ERROR_HRESULT(E_INVALIDARG);
1141 return ItemToItemId(m_pSelection);
1144 return itemid;
1147 ItemInterface* GetNextSibling(_In_ VSITEMID itemid) const
1149 BaseImpl_T::HierarchyNode::FindInfo findInfo = {ItemIdToItem(TransformVSITEMIDForSibilingSearch(itemid))};
1150 VSL_CHECKBOOLEAN(m_pNode->FindIterator(findInfo), E_INVALIDARG);
1151 if((++findInfo.rFound) != findInfo.pContainer->end())
1153 return ***(findInfo.rFound);
1155 return NULL;
1158 ItemInterface* GetNextVisibleSibling(_In_ VSITEMID itemid) const
1160 __if_exists(ItemInterface::SupportsUI)
1162 BaseImpl_T::HierarchyNode::FindInfo findInfo = {ItemIdToItem(TransformVSITEMIDForSibilingSearch(itemid))};
1163 VSL_CHECKBOOLEAN(m_pNode->FindIterator(findInfo), E_INVALIDARG);
1164 for(++findInfo.rFound; findInfo.rFound != findInfo.pContainer->end(); ++findInfo.rFound)
1166 if((***findInfo.rFound)->IsVisible())
1168 return ***(findInfo.rFound);
1172 __if_not_exists(ItemInterface::SupportsUI)
1174 VSL_CREATE_ERROR_HRESULT(E_NOTIMPL);
1176 return NULL;
1179 ItemInterface* m_pSelection;
1182 class IVsHierarchyEventsDelegate :
1183 public IVsHierarchyEvents
1185 public:
1187 // This isn't a real COM object
1188 VSL_DEFINE_IUNKNOWN_NOTIMPL
1190 virtual HRESULT STDMETHODCALLTYPE OnItemAdded(
1191 /* [in] */ VSITEMID itemidParent,
1192 /* [in] */ VSITEMID itemidSiblingPrev,
1193 /* [in] */ VSITEMID itemidAdded)
1195 return m_dOnItemAdded(itemidParent, itemidSiblingPrev, itemidAdded);
1198 virtual HRESULT STDMETHODCALLTYPE OnItemsAppended(
1199 /* [in] */ VSITEMID itemidParent)
1201 return m_dOnItemsAppended(itemidParent);
1204 virtual HRESULT STDMETHODCALLTYPE OnItemDeleted(
1205 /* [in] */ VSITEMID itemid)
1207 return m_dOnItemDeleted(itemid);
1210 virtual HRESULT STDMETHODCALLTYPE OnPropertyChanged(
1211 /* [in] */ VSITEMID itemid,
1212 /* [in] */ VSHPROPID propid,
1213 /* [in] */ DWORD flags)
1215 return m_dOnPropertyChanged(itemid, propid, flags);
1218 virtual HRESULT STDMETHODCALLTYPE OnInvalidateItems(
1219 /* [in] */ VSITEMID itemidParent)
1221 return m_dOnInvalidateItems(itemidParent);
1224 virtual /* [local] */ HRESULT STDMETHODCALLTYPE OnInvalidateIcon(
1225 /* [in] */ HICON hicon)
1227 return m_dOnInvalidateIcon(hicon);
1230 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (VSITEMID, VSITEMID, VSITEMID)> OnItemAddedFunctor;
1231 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (VSITEMID)> OnItemsAppendedFunctor;
1232 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (VSITEMID)> OnItemDeletedFunctor;
1233 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (VSITEMID, VSHPROPID, DWORD)> OnPropertyChangedFunctor;
1234 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (VSITEMID)> OnInvalidateItemsFunctor;
1235 typedef MemberFunctionPointerFunctor<IVsHierarchyEvents, CallingConventionStandard, HRESULT (HICON)> OnInvalidateIconFunctor;
1237 struct IVsHierarchyEventsFunctors
1239 OnItemAddedFunctor m_OnItemAddedFunctor;
1240 OnItemsAppendedFunctor m_OnItemsAppendedFunctor;
1241 OnItemDeletedFunctor m_OnItemDeletedFunctor;
1242 OnPropertyChangedFunctor m_OnPropertyChangedFunctor;
1243 OnInvalidateItemsFunctor m_OnInvalidateItemsFunctor;
1244 OnInvalidateIconFunctor m_OnInvalidateIconFunctor;
1246 IVsHierarchyEventsFunctors(
1247 IVsHierarchyEvents* pIVsHierarchyEvents):
1248 m_OnItemAddedFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnItemAdded),
1249 m_OnItemsAppendedFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnItemsAppended),
1250 m_OnItemDeletedFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnItemDeleted),
1251 m_OnPropertyChangedFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnPropertyChanged),
1252 m_OnInvalidateItemsFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnInvalidateItems),
1253 m_OnInvalidateIconFunctor(pIVsHierarchyEvents, &IVsHierarchyEvents::OnInvalidateIcon)
1258 void operator+=(IVsHierarchyEventsFunctors& rFunctors)
1260 m_dOnItemAdded += &(rFunctors.m_OnItemAddedFunctor);
1261 m_dOnItemsAppended += &(rFunctors.m_OnItemsAppendedFunctor);
1262 m_dOnItemDeleted += &(rFunctors.m_OnItemDeletedFunctor);
1263 m_dOnPropertyChanged += &(rFunctors.m_OnPropertyChangedFunctor);
1264 m_dOnInvalidateItems += &(rFunctors.m_OnInvalidateItemsFunctor);
1265 m_dOnInvalidateIcon += &(rFunctors.m_OnInvalidateIconFunctor);
1268 void operator-=(IVsHierarchyEventsFunctors& rFunctors)
1270 m_dOnItemAdded -= &(rFunctors.m_OnItemAddedFunctor);
1271 m_dOnItemsAppended -= &(rFunctors.m_OnItemsAppendedFunctor);
1272 m_dOnItemDeleted -= &(rFunctors.m_OnItemDeletedFunctor);
1273 m_dOnPropertyChanged -= &(rFunctors.m_OnPropertyChangedFunctor);
1274 m_dOnInvalidateItems -= &(rFunctors.m_OnInvalidateItemsFunctor);
1275 m_dOnInvalidateIcon -= &(rFunctors.m_OnInvalidateIconFunctor);
1278 private:
1279 Delegate<HRESULT (VSITEMID, VSITEMID, VSITEMID)> m_dOnItemAdded;
1280 Delegate<HRESULT (VSITEMID)> m_dOnItemsAppended;
1281 Delegate<HRESULT (VSITEMID)> m_dOnItemDeleted;
1282 Delegate<HRESULT (VSITEMID, VSHPROPID, DWORD)> m_dOnPropertyChanged;
1283 Delegate<HRESULT (VSITEMID)> m_dOnInvalidateItems;
1284 Delegate<HRESULT (HICON)> m_dOnInvalidateIcon;
1287 template <
1288 class DerivedClass_T,
1289 class HierarchyRootItem_T,
1290 class Base_T = IVsHierarchy,
1291 class VsSiteCache_T = VsSiteCacheLocal >
1292 class IVsHierarchyImpl :
1293 public VsSiteBaseImpl<DerivedClass_T, IVsHierarchyImpl<DerivedClass_T, HierarchyRootItem_T, Base_T, VsSiteCache_T>, Base_T, VsSiteCache_T>
1296 private:
1298 HierarchyRootItem_T* CreateRootItemInstance()
1300 HierarchyRootItem_T* pRootItem = NULL;
1301 VSL_CHECKHRESULT(HierarchyRootItem_T::CreateInstance(&pRootItem));
1302 VSL_CHECKPOINTER(pRootItem, E_FAIL);
1303 #pragma warning(push) // compiler doesn't get that the above line will throw if pValidValues is NULL
1304 #pragma warning(disable : 6011) // Dereferencing NULL pointer 'pRootItem'
1305 __if_exists(HierarchyRootItem_T::AddRef)
1307 pRootItem->AddRef();
1309 return pRootItem;
1310 #pragma warning(pop)
1313 protected:
1316 IVsHierarchyImpl():
1317 m_pRoot(CreateRootItemInstance()),
1318 m_LastCookie(0)
1322 ~IVsHierarchyImpl()
1324 m_pRoot->Dispose();
1327 public:
1329 typedef HierarchyRootItem_T HierarchyRootItem;
1330 typedef typename HierarchyRootItem::ItemInterface ItemInterface;
1332 STDMETHOD(GetGuidProperty)(
1333 _In_ VSITEMID itemid,
1334 _In_ VSHPROPID propid,
1335 _Out_ GUID *pguid)
1337 VSL_STDMETHODTRY{
1339 EnsureValidVSHPROPID(propid);
1340 VSL_CHECKPOINTER(pguid, E_INVALIDARG);
1342 *pguid = GetRootItem().GetGuidProperty(itemid, propid);
1344 }VSL_STDMETHODCATCH()
1346 return VSL_GET_STDMETHOD_HRESULT();
1349 STDMETHOD(SetGuidProperty)(
1350 _In_ VSITEMID itemid,
1351 _In_ VSHPROPID propid,
1352 _In_ REFGUID rguid)
1354 VSL_STDMETHODTRY{
1356 EnsureValidVSHPROPID(propid);
1358 GetRootItem().SetGuidProperty(itemid, propid, rguid);
1360 }VSL_STDMETHODCATCH()
1362 return VSL_GET_STDMETHOD_HRESULT();
1365 STDMETHOD(GetProperty)(
1366 _In_ VSITEMID itemid,
1367 _In_ VSHPROPID propid,
1368 _Out_ VARIANT *pvar)
1370 VSL_STDMETHODTRY{
1372 EnsureValidVSHPROPID(propid);
1373 VSL_CHECKPOINTER(pvar, E_INVALIDARG);
1374 pvar->vt = VT_EMPTY;
1376 GetRootItem().GetProperty(itemid, propid, pvar);
1378 }VSL_STDMETHODCATCH()
1380 return VSL_GET_STDMETHOD_HRESULT();
1383 STDMETHOD(SetProperty)(
1384 _In_ VSITEMID itemid,
1385 _In_ VSHPROPID propid,
1386 _In_ VARIANT var)
1388 VSL_STDMETHODTRY{
1390 EnsureValidVSHPROPID(propid);
1392 GetRootItem().SetProperty(itemid, propid, var);
1394 }VSL_STDMETHODCATCH()
1396 return VSL_GET_STDMETHOD_HRESULT();
1399 STDMETHOD(GetNestedHierarchy)(
1400 _In_ VSITEMID itemid,
1401 _In_ REFIID iidHierarchyNested,
1402 _Out_ void **ppHierarchyNested,
1403 _Out_ VSITEMID *pitemidNested)
1405 #if 1
1406 VSL_TRACE(_T("IVsHierarchyImpl::GetNestedHierarchy is not implemented\n"));
1408 (itemid, iidHierarchyNested, ppHierarchyNested, pitemidNested);
1410 return E_NOTIMPL;
1411 #else // FUTURE - support IVsHierarchyImpl::GetNestedHierarchy
1412 VSL_STDMETHODTRY{
1414 VSL_CHECKPOINTER(ppHierarchyNested, E_INVALIDARG);
1415 VSL_CHECKPOINTER(pitemidNested, E_INVALIDARG);
1417 (iidHierarchyNested);
1419 }VSL_STDMETHODCATCH()
1421 return VSL_GET_STDMETHOD_HRESULT();
1422 #endif
1425 STDMETHOD(GetCanonicalName)(
1426 _In_ VSITEMID itemid,
1427 _Out_ BSTR *pbstrName)
1429 VSL_STDMETHODTRY_EX(E_NOTIMPL){
1431 VSL_CHECKPOINTER(pbstrName, E_INVALIDARG);
1433 __if_exists(ItemInterface::GetCanonicalName)
1435 VSL_CHECKHRESULT(const_cast<ATL::CComBSTR&>(GetRootItem().GetItem(itemid).GetCanonicalName()).CopyTo(pbstrName));
1437 __if_not_exists(ItemInterface::GetCanonicalName)
1439 (itemid);
1442 }VSL_STDMETHODCATCH()
1444 return VSL_GET_STDMETHOD_HRESULT();
1447 STDMETHOD(ParseCanonicalName)(
1448 _In_ LPCOLESTR pszName,
1449 _Out_ VSITEMID *pitemid)
1451 VSL_STDMETHODTRY_EX(E_NOTIMPL){
1453 VSL_CHECKPOINTER(pszName, E_INVALIDARG);
1454 VSL_CHECKBOOLEAN(pszName[0] != L'\0', E_INVALIDARG);
1455 VSL_CHECKPOINTER(pitemid, E_INVALIDARG);
1457 __if_exists(ItemInterface::ParseCanonicalName)
1459 *pitemid = GetRootItem().ParseCanonicalName(pszName);
1462 }VSL_STDMETHODCATCH()
1464 return VSL_GET_STDMETHOD_HRESULT();
1467 STDMETHOD(Unused0)()
1469 VSL_TRACE(_T("IVsHierarchyImpl::Unused0 is not implemented\n"));
1471 return E_NOTIMPL;
1474 STDMETHOD(AdviseHierarchyEvents)(
1475 _In_ IVsHierarchyEvents *pEventSink,
1476 _Out_ VSCOOKIE *pdwCookie)
1478 VSL_STDMETHODTRY{
1480 VSL_CHECKPOINTER(pEventSink, E_INVALIDARG);
1481 VSL_CHECKPOINTER(pdwCookie, E_INVALIDARG);
1483 VSL_CHECKBOOLEAN(m_LastCookie < 0xFFFFFFFF, E_FAIL);
1485 m_CookieEventList.push_front(CookieEventPair(++m_LastCookie, pEventSink));
1486 m_IVsHierarchyEventsDelegate += (*(m_CookieEventList.begin())).second;
1487 *pdwCookie = m_LastCookie;
1489 }VSL_STDMETHODCATCH()
1491 return VSL_GET_STDMETHOD_HRESULT();
1494 STDMETHOD(UnadviseHierarchyEvents)(
1495 _In_ VSCOOKIE dwCookie)
1497 VSL_STDMETHODTRY{
1499 class RemoveCookieEvent
1501 public:
1502 RemoveCookieEvent(VSCOOKIE cookie, IVsHierarchyEventsDelegate& rIVsHierarchyEventsDelegate):
1503 m_cookie(cookie),
1504 m_rIVsHierarchyEventsDelegate(rIVsHierarchyEventsDelegate)
1507 bool operator()(CookieEventPair& rToCheck)
1509 if(rToCheck.first == m_cookie)
1511 m_rIVsHierarchyEventsDelegate -= rToCheck.second;
1512 return true;
1514 return false;
1516 void operator=(const RemoveCookieEvent& rToCopy)
1518 m_cookie = rToCopy.m_cookie;
1519 m_rIVsHierarchyEventsDelegate = rToCopy.m_rIVsHierarchyEventsDelegate;
1521 private:
1522 VSCOOKIE m_cookie;
1523 IVsHierarchyEventsDelegate& m_rIVsHierarchyEventsDelegate;
1526 // No verification that cookie is valid, just removal or not.
1527 m_CookieEventList.remove_if(RemoveCookieEvent(dwCookie, m_IVsHierarchyEventsDelegate));
1529 if(m_CookieEventList.empty())
1531 // PARANOID - theoretically, over the long haul, m_LastCookie could wrap,
1532 // so zero it when the list is empty
1533 m_LastCookie = 0;
1536 }VSL_STDMETHODCATCH()
1538 return VSL_GET_STDMETHOD_HRESULT();
1541 STDMETHOD(Unused1)()
1543 VSL_TRACE(_T("IVsHierarchyImpl::Unused1 is not implemented\n"));
1545 return E_NOTIMPL;
1548 STDMETHOD(Unused2)()
1550 VSL_TRACE(_T("IVsHierarchyImpl::Unused2 is not implemented\n"));
1552 return E_NOTIMPL;
1555 STDMETHOD(Unused3)()
1557 VSL_TRACE(_T("IVsHierarchyImpl::Unused3 is not implemented\n"));
1559 return E_NOTIMPL;
1562 STDMETHOD(Unused4)()
1564 VSL_TRACE(_T("IVsHierarchyImpl::Unused4 is not implemented\n"));
1566 return E_NOTIMPL;
1569 HierarchyRootItem& GetRootItem()
1571 return *m_pRoot;
1574 IVsHierarchyEvents* GetIVsHierarchyEvents()
1576 return &m_IVsHierarchyEventsDelegate;
1579 protected:
1581 HierarchyRootItem* m_pRoot;
1583 private:
1585 void EnsureValidVSHPROPID(_In_ VSHPROPID propid)
1587 VSL_CHECKBOOLEAN(propid >= VSHPROPID_FIRST2 && propid <= VSHPROPID_LAST, E_INVALIDARG);
1590 typedef std::pair<VSCOOKIE, IVsHierarchyEventsDelegate::IVsHierarchyEventsFunctors> CookieEventPair;
1592 std::list<CookieEventPair> m_CookieEventList;
1593 VSCOOKIE m_LastCookie;
1594 IVsHierarchyEventsDelegate m_IVsHierarchyEventsDelegate;
1597 template <
1598 class DerivedClass_T,
1599 class HierarchyRootItem_T,
1600 class Base_T = IVsHierarchyImpl<DerivedClass_T, HierarchyRootItem_T, IVsUIHierarchy> >
1601 class IVsUIHierarchyImpl :
1602 public Base_T
1604 public:
1605 STDMETHOD(QueryStatusCommand)(
1606 _In_ VSITEMID itemid,
1607 _In_ const GUID *pguidCmdGroup,
1608 _In_ ULONG cCmds,
1609 _Inout_cap_(cCmds) OLECMD prgCmds[ ],
1610 _Inout_opt_ OLECMDTEXT *pCmdText)
1612 VSL_STDMETHODTRY{
1614 CComPtr<IOleCommandTarget> pTarget = GetRootItem().GetItem(itemid).GetIOleCommandTarget();
1616 if(!pTarget)
1618 return OLECMDERR_E_NOTSUPPORTED;
1621 return pTarget->QueryStatus(pguidCmdGroup, cCmds, prgCmds, pCmdText);
1623 }VSL_STDMETHODCATCH()
1625 return VSL_GET_STDMETHOD_HRESULT();
1628 STDMETHOD(ExecCommand)(
1629 _In_ VSITEMID itemid,
1630 _In_ const GUID *pguidCmdGroup,
1631 _In_ DWORD nCmdID,
1632 _In_ DWORD nCmdexecopt,
1633 _In_opt_ VARIANT *pvaIn,
1634 _Inout_opt_ VARIANT *pvaOut)
1636 VSL_STDMETHODTRY{
1638 CComPtr<IOleCommandTarget> pTarget = GetRootItem().GetItem(itemid).GetIOleCommandTarget();
1640 if(!pTarget)
1642 return OLECMDERR_E_NOTSUPPORTED;
1645 return pTarget->Exec(pguidCmdGroup, nCmdID, nCmdexecopt, pvaIn, pvaOut);
1647 }VSL_STDMETHODCATCH()
1649 return VSL_GET_STDMETHOD_HRESULT();
1653 } // namespace VSL
1655 #endif // VSLHIERARCHY_H_10C49CA1_2F46_11D3_A504_00C04F5E0BA5