text: #ifndef __SNAPEXT_H_
  #define __SNAPEXT_H_
  #include "resource.h"
  #include <atlsnap.h>
  #include "vssprop.h"
  
  class CVSSUIExtData1 : public CSnapInItemImpl<CVSSUIExtData1, TRUE>
  {
  public:
  	static const GUID* m_NODETYPE;
  	static const OLECHAR* m_SZNODETYPE;
  	static const OLECHAR* m_SZDISPLAY_NAME;
  	static const CLSID* m_SNAPIN_CLASSID;
  
  	BEGIN_SNAPINCOMMAND_MAP(CVSSUIExtData1, FALSE)
  	END_SNAPINCOMMAND_MAP()
  
  //	SNAPINMENUID(IDR_VSSUI_MENU)
  
  	CVSSUIExtData1()
  	{
  		memset(&m_scopeDataItem, 0, sizeof(SCOPEDATAITEM));
  		memset(&m_resultDataItem, 0, sizeof(RESULTDATAITEM));
  	}
  
  	~CVSSUIExtData1()
  	{
  	}
  
  	IDataObject* m_pDataObject;
  	virtual void InitDataClass(IDataObject* pDataObject, CSnapInItem* pDefault)
  	{
  		m_pDataObject = pDataObject;
  		// The default code stores off the pointer to the Dataobject the class is wrapping
  		// at the time. 
  		// Alternatively you could convert the dataobject to the internal format
  		// it represents and store that information
  	}
  
  	CSnapInItem* GetExtNodeObject(IDataObject* pDataObject, CSnapInItem* pDefault)
  	{
  		// Modify to return a different CSnapInItem* pointer.
  		return pDefault;
  	}
  };
  
  class CVSSUIExtData2 : public CSnapInItemImpl<CVSSUIExtData2, TRUE>
  {
  public:
  	static const GUID* m_NODETYPE;
  	static const OLECHAR* m_SZNODETYPE;
  	static const OLECHAR* m_SZDISPLAY_NAME;
  	static const CLSID* m_SNAPIN_CLASSID;
  
  	BEGIN_SNAPINCOMMAND_MAP(CVSSUIExtData2, FALSE)
  	END_SNAPINCOMMAND_MAP()
  
  //	SNAPINMENUID(IDR_VSSUI_MENU)  // use the same context menu
  
  	CVSSUIExtData2()
  	{
  		memset(&m_scopeDataItem, 0, sizeof(SCOPEDATAITEM));
  		memset(&m_resultDataItem, 0, sizeof(RESULTDATAITEM));
  	}
  
  	~CVSSUIExtData2()
  	{
  	}
  
  	IDataObject* m_pDataObject;
  	virtual void InitDataClass(IDataObject* pDataObject, CSnapInItem* pDefault)
  	{
  		m_pDataObject = pDataObject;
  		// The default code stores off the pointer to the Dataobject the class is wrapping
  		// at the time. 
  		// Alternatively you could convert the dataobject to the internal format
  		// it represents and store that information
  	}
  
  	CSnapInItem* GetExtNodeObject(IDataObject* pDataObject, CSnapInItem* pDefault)
  	{
  		// Modify to return a different CSnapInItem* pointer.
  		return pDefault;
  	}
  };
  
  class CVSSUI :
      public CComObjectRootEx<CComSingleThreadModel>,
      public CSnapInObjectRoot<0, CVSSUI>,
  	public IExtendContextMenuImpl<CVSSUI>,
  //    public IExtendPropertySheetImpl<CVSSUI>,
  	public CComCoClass<CVSSUI, &CLSID_VSSUI>
  {
  public:
  	CVSSUI();
  	~CVSSUI();
  
  EXTENSION_SNAPIN_DATACLASS(CVSSUIExtData1)
  EXTENSION_SNAPIN_DATACLASS(CVSSUIExtData2)
  
  BEGIN_EXTENSION_SNAPIN_NODEINFO_MAP(CVSSUI)
  	EXTENSION_SNAPIN_NODEINFO_ENTRY(CVSSUIExtData1)
  	EXTENSION_SNAPIN_NODEINFO_ENTRY(CVSSUIExtData2)
  END_EXTENSION_SNAPIN_NODEINFO_MAP()
  
  BEGIN_COM_MAP(CVSSUI)
      COM_INTERFACE_ENTRY(IExtendContextMenu)
  //    COM_INTERFACE_ENTRY(IExtendPropertySheet)
  END_COM_MAP()
  
  DECLARE_REGISTRY_RESOURCEID(IDR_VSSUI)
  
  DECLARE_NOT_AGGREGATABLE(CVSSUI)
  
  
  	static void WINAPI ObjectMain(bool bStarting)
  	{
  		if (bStarting)
  			CSnapInItem::Init();
  	}
  
      ///////////////////////////////
      // Interface IExtendContextMenu
      ///////////////////////////////
  
      //
      // overwrite AddMenuItems() such that we only add the menu item
      // when targeted machine belongs to postW2K server SKUs.
      //
      virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE AddMenuItems(
      /* [in] */ LPDATAOBJECT piDataObject,
      /* [in] */ LPCONTEXTMENUCALLBACK piCallback,
      /* [out][in] */ long *pInsertionAllowed);
  
      virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE Command(
      /* [in] */ long lCommandID,
      /* [in] */ LPDATAOBJECT piDataObject);
  
      ///////////////////////////////
      // Interface IExtendPropertySheet
      ///////////////////////////////
  //    virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE CreatePropertyPages( 
  //        /* [in] */ LPPROPERTYSHEETCALLBACK lpProvider,
  //        /* [in] */ LONG_PTR handle,
  //        /* [in] */ LPDATAOBJECT lpIDataObject);
      
  //    virtual /* [helpstring] */ HRESULT STDMETHODCALLTYPE QueryPagesFor( 
  //    /* [in] */ LPDATAOBJECT lpDataObject) { return S_OK; }
  
      HRESULT InvokePropSheet(LPDATAOBJECT piDataObject);
      
  private:
      CVSSProp* m_pPage;
  };
  
  HRESULT ExtractData(
      IDataObject* piDataObject,
      CLIPFORMAT   cfClipFormat,
      BYTE*        pbData,
      DWORD        cbData 
      );
  
  #endif
  