Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
HomeAnnouncementsFree MagazinesWhite PapersSubmit Content
Discussion GroupsASP.NETWindows FormsLanguages.NET FrameworkVisual Studio.NET
Articles.NET FrameworkASP.NETToolsWindows Forms
.NET DirectoryOpen Source ProjectsUser GroupsWeb Resources
Related Topics
Visual Basic 6SQL ServerMS AccessOther DB ProductsMS Server ProductsMore Topics ...

.NET Forum / Visual Studio.NET / Extensibility / February 2005

Tip: Looking for answers? Try searching our database.

VSIP C++ Dialog

Thread view: 
Enable EMail Alerts  Start New Thread
Thread rating: 
Ash - 18 Feb 2005 13:44 GMT
Hello all,

I am a complete newbie with VSIP.

I want to create a number of my own tool windows in the IDE that will
display debug information for C++ class libraries during a debug
session.

I have read through a number of the provided samples in unmanaged C++,
but all of them, as far as I can tell, use either system GUI objects
or VB ActiveX controls to do the actual display.

I would like to create my own GUI components in C++ but I have no
experience of creating my own GUI components in ATL, MFC or whatever.

At the end of the day, I will be displaying the contents of C++
classes in different ways, so it makes sense to me to keep my project
in C++ (plus I already know the language quite well). I don't have C#
and I don't think that VB6 offers me the set of controls that I need
(e.g. tree view control).

Does anyone have (or can anyone knock up) a simple VSIP example that
shows creating a tool window in C++ (using ATL) and talking to it from
the GUI? While I am here, any example code that talks to the C++
debugger would be nice too ;-)

This may sound quite lazy of me, but I am already finding this VSIP
stuff quite confusing! A quick example would really accelerate my
project.

Many thanks

Ashley
"Ed Dore [MSFT]" - 18 Feb 2005 22:28 GMT
Hi Ashley,

Your best bet would be to review the ToolWn Sample that ships with the VSIP
SDK. Then use the VSIP Package Wizard (in the New Project's dialog, under
"Other Projects\Extensibility Projects) to create a new VSIP package.
There's an option to create a package that implements a toolwindow.

By default, the wizard throws some code into the package's CreateTool
function, that calls IVsUIShell::CreateToolWindow with the CLSID of an OLE
ActiveX Document.

ToolWindows can host an activex control, an activex document, or you can
implement your own native dialog window by implementing IVsWindowPane. I've
done the latter more than a few times.

Ultimately, I've found that it's pretty easy to use the ATL Wizard support
to add an ATL dialog to your project, and then convert it into a COM object
that derives from IVsWindowPane and IOleCommandTarget. For example:

class CAddRefTestDlg :
    public CDialogImpl<CAddRefTestDlg>,
    public CComObjectRootEx<CComSingleThreadModel>,
    public IVsWindowPane,
    public IOleCommandTarget
{
public:
    CAddRefTestDlg()
    {
    }

    ~CAddRefTestDlg()
    {
    }

DECLARE_NOT_AGGREGATABLE(CAddRefTestDlg)
DECLARE_PROTECT_FINAL_CONSTRUCT()

BEGIN_COM_MAP(CAddRefTestDlg)
    COM_INTERFACE_ENTRY(IVsWindowPane)
    COM_INTERFACE_ENTRY(IOleCommandTarget)
END_COM_MAP()

BEGIN_MSG_MAP(CAddRefTestDlg)
    MESSAGE_HANDLER(WM_INITDIALOG, OnInitDialog)
    MESSAGE_HANDLER(WM_CLOSE, OnClose)
    MESSAGE_HANDLER(WM_RBUTTONUP, OnRButtonUp)
END_MSG_MAP()

    enum { IDD = IDD_ADDREFTESTDLG };

    // dialog methods
    LRESULT OnInitDialog(UINT, WPARAM, LPARAM, BOOL&);
    LRESULT OnClose(UINT, WPARAM, LPARAM, BOOL&);
    LRESULT OnRButtonUp(UINT, WPARAM, LPARAM, BOOL&);

    // IVsWindowPane methods
              STDMETHOD(SetSite)(IServiceProvider* pSP);
              STDMETHOD(CreatePaneWindow)(HWND hwndParent, int x, int y,
int cx, int cy, HWND* phwnd);
              STDMETHOD(GetDefaultSize)(SIZE* pSize);
              STDMETHOD(ClosePane)(void);
              STDMETHOD(LoadViewState)(IStream* pStream);
              STDMETHOD(SaveViewState)(IStream* pStream);
              STDMETHOD(TranslateAccelerator)(LPMSG lpmsg);

    // IOleCommandTarget methods
              STDMETHOD(QueryStatus)(const GUID* pguidCmdGroup,ULONG
cCmds,OLECMD prgCmds[],OLECMDTEXT* pCmdText);
              STDMETHOD(Exec)(const GUID* pguidCmdGroup, DWORD nCmdID,
DWORD nCmdExecOpt, VARIANT* pvaIn, VARIANT* pvaOut);

public:
    CComPtr<IServiceProvider> m_srpSiteSP;
    CComPtr<IVsWindowFrame> m_srpWindowFrame;
};

Then to use the above class as your toolwindow, you just modify the
CreateTool implementation to look something like the following:

STDMETHODIMP CAddRefTestPackage::CreateTool(/*[in]*/ REFGUID rguid)
{
   ATLTRACE(_T("CAddRefTestPackage::CreateTool\n"));
   _ASSERTE(!m_fZombie);

   USES_CONVERSION;
    CComPtr<IVsUIShell>    srpUIShell = NULL;
    CComObject<CAddRefTestDlg>* spSimpToolWindow = NULL;

   if (m_fZombie)
       return E_UNEXPECTED;

    if (rguid == GUID_guidPersistanceSlot)
   {
         // now get the IVsUIShell interface so we can create a tool window
       //
       HRESULT hr = _Module.QueryService(SID_SVsUIShell, IID_IVsUIShell,
(void **)&srpUIShell);

       if (SUCCEEDED(hr))
       {
            hr = CComObject<CAddRefTestDlg>::CreateInstance(&spSimpToolWindow);
       
            if (SUCCEEDED(hr))
            {
                TCHAR szTitle[128];

                if (! ::LoadString(_Module.GetResourceInstance(), IDS_WINDOW_TITLE,
szTitle, countof(szTitle)))
                    return HRESULT_FROM_WIN32(::GetLastError());

                CComQIPtr<IVsWindowPane> srpWindowPane(spSimpToolWindow);
                hr = srpUIShell->CreateToolWindow(CTW_fInitNew|CTW_fForceCreate, 0,
srpWindowPane,
                    GUID_NULL, GUID_guidPersistanceSlot, GUID_NULL, NULL, T2OLE(szTitle),
                    NULL, &m_srpToolWinFrame);

                if (FAILED(hr))
                    _Module.SetErrorInfo(hr, IDS_E_CANTCREATETOOL, 0);
                else
                {
                    spSimpToolWindow->m_srpWindowFrame = m_srpToolWinFrame;

                    // Set the bitmap for the frame to be the same as the one used for the
menu item
                    CComVariant srpvt;
                    srpvt.intVal = IDB_MENU_IMAGES;
                    m_srpToolWinFrame->SetProperty(VSFPROPID_BitmapResource, srpvt);
                    srpvt.intVal = 1;
                    m_srpToolWinFrame->SetProperty(VSFPROPID_BitmapIndex, srpvt);
                }
                return hr;
            }
        }
   }

    return E_INVALIDARG;
}

Note, the difference between the wizard generated code and my code above.
In my code, you create an instance of your dialog object using:

    hr = CComObject<CAddRefTestDlg>::CreateInstance(&spSimpToolWindow);

Then you retrieve it's IVsWindowPane interface and pass this to the
IVsUIShell::CreateToolWindow function, instead of that clsid param.

Sincerely,
Ed Dore [MSFT]

This post is 'AS IS' with no warranties and confers no rights.

Rate this thread:







Free Magazines

Get these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...

Oracle MagazineNetwork ComputingComputer WorldBio-IT WorldeWeekInformation WeekInfosecurity
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2008 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.