Add custom view for expression
2006-10-19 22:21 atempcode 阅读(736) 评论(0) 编辑 收藏 举报In VS2005, there are new features to display data in a specific format (read very visual) called Type Visualizer and Custom Viewer.
There are a lot of articals talking about the Type Visualizer like this, this and this. Since we are implementing a debug engine in our current project, I have a chance to implement the Custom View, approaching the same goal in a different way.
1. Implement the IDebugProperty3 for the property object. Especially the GetCustomViewerList and GetCustomViewerCount methods.
2. Regsiter the custom view using SetEEMetric.
3. Create a object implementing the IDebugCustomView interface. In the Display(...) method, you can do whatever you want to show the data to the users.
4. Set The flag DBG_ATTRIB_VALUE_CUSTOM_VIEWER in the dwAttrib field of the DEBUG_PROPERTY_INFO structure when IDebugProperty3::GetPropertyinfo called. This indicates the property has a custom view associated. Then VS will QueryInterface for the IDebugProperty3 interface.
The example MS gave demonstrate how VS get your custom view (not how you implement your cutom view):
IDebugCustomViewer *GetFirstCustomViewer(IDebugProperty2 *pProperty) { // This string is typically defined globally. For this example, it // is defined here. static const WCHAR strRegistrationRoot[] = L"Software\\Microsoft\\VisualStudio\\8.0Exp"; IDebugCustomViewer *pViewer = NULL; if (pProperty != NULL) { CComQIPtr<IDebugProperty3> pProperty3(pProperty); if (pProperty3 != NULL) { HRESULT hr; ULONG viewerCount = 0; hr = pProperty3->GetCustomViewerCount(&viewerCount); if (viewerCount > 0) { ULONG viewersFetched = 0; DEBUG_CUSTOM_VIEWER viewerInfo = { 0 }; hr = pProperty3->GetCustomViewerList(0, 1, &viewerInfo, &viewersFetched); if (viewersFetched == 1) { CLSID clsidViewer = { 0 }; CComPtr<IDebugCustomViewer> spCustomViewer; // Get the viewer's CLSID from the registry. ::GetEEMetric(viewerInfo.guidLang, viewerInfo.guidVendor, viewerInfo.bstrMetric, &clsidViewer, strRegistrationRoot); if (!IsEqualGUID(clsidViewer,GUID_NULL)) { // Instantiate the custom viewer. spCustomViewer.CoCreateInstance(clsidViewer); if (spCustomViewer != NULL) { pViewer = spCustomViewer.Detach(); } } } } } } return(pViewer); }
But an important point was missed: before QueryInterface for the IDebugProperty3 interface, VS will call GetPropertyinfo to see if the flag DBG_ATTRIB_VALUE_CUSTOM_VIEWER in the dwAttrib field is set. If not, it will just goes away. This costs me an afternoon to find out.