Top Banner

Click here to load reader

VSL Deep Dive

Jan 31, 2016




VSL Deep Dive. Josh Heitzman - Senior Software Design Engineer. VSL is…. Acronym for “Visual Studio Library” Modern C++ library targeting the Visual Studio Platform. Styled after ATL and WTL. Comprised only of header files. No binaries. - PowerPoint PPT Presentation

  • VSL Deep DiveJosh Heitzman - Senior Software Design Engineer

  • VSL isAcronym for Visual Studio LibraryModern C++ library targeting the Visual Studio Platform.Styled after ATL and WTL.Comprised only of header files. No binaries.Extensible and customizable (macros can be overriden to change core behavior).Not a framework like MFC, MPF, .Net Framework, etc..Not a complete offering for the entire VS Platform

  • VSL Effect

  • Resources\VisualStudioIntegration\Common\Source\CPP\VSLVSLArchitecture.htm class diagramsInclude VSL header filesMockInterfaces Windows and Visual Studio Platform Interface mocksUnitTest\VSLUnitTest.sln solution with all of the VSL unit tests.

    Questions/Issues: post title with VSL



  • VSL Design PrinciplesMinimize couplingAvoid feature creepExploit the C++ language and the Microsoft Visual C++ compilerFacilitate unit testingRe-use without obstructionResponsive to requests

  • Minimize couplingNarrowly scoping the functionality of classes:Implement one interfaceWrap one VS ServiceWrap one related set of Win32 APIs

    Use of C++ templates to reduce hard dependencies between classes.templateclass IVsWindowPaneImpl : public IVsWindowPane

    template class IExtensibleObjectImpl : public IExtensibleObject

  • Avoid feature creepOnly the functionality required for the task at hand is implemented.

    Avoid investing resources in features that may not be needed.class VsOutputWindowUtilities{ void OutputMessage( const wchar_t* const szMessage); void OutputMessageWithPreAndPostBarsOfEquals( const wchar_t* const szMessage);};

  • Exploit the C++ language and the Visual C++ compilerWhen possible, fail at compile time rather then runtimeMake use of C++ exceptionsUse C++ templates and when necessary C pre-processor macros to minimize code redundancy and maximize reuseUse of an extended version of the Resource Allocation Is Initialization paradigmtemplate class StaticArray{ C_ASSERT( NumberOfElements_T > 0);__if_exists(Derived_T::GetViewObject){__if_exists(Derived_T:: GetLocalRegistryCLSIDViewObject) { // Can't speceify both an object and // a clsid C_ASSERT(0); } pViewObject = rDerived.GetViewObject();}

  • Resource Allocation Is Initialization (RAII)RAII is used with all resources to ensure their lifetime is properly managed in the face of exceptions.template class Resource{ ResourceType m_Resource; Resource(): m_Resource(Values::GetNullValue()) {} Resource(ResourceType resource): m_Resource(resource) {} ~Resource() { Free(); } void Free(); ResourceType Detach(); operator CastType() const;};

  • eXtendened Resource Allocation Is Initialization (XRAII)RAII is extended to any set of calls that need balancing.class Suspend{ Suspend(This& rThis): m_rThis(rThis) { m_rThis.SendMessage(WM_SETREDRAW, FALSE, 0); m_dwMaskToRestore = static_cast(m_rThis.SendMessage( EM_SETEVENTMASK, 0, ENM_NONE)); } ~SuspendDrawAndNotifications() { m_rThis.SendMessage( EM_SETEVENTMASK, 0, m_dwMaskToRestore); m_rThis.SendMessage(WM_SETREDRAW, TRUE, 0); } This& m_rThis; DWORD m_dwMaskToRestore;};

  • Facilitate unit testingMocks for nearly all VS Platform interfacesMocks for many Windows Platform interfacesWrapper classes around some sets of Win32 APIsMocks for those classesCursorCursorMockFileFileMockKeyboardKeyboardMockWindowWindowMock

  • Re-use without obstructionMany classes take template parametersAllows you to provide your own custom implementation for a dependencySome template defaults will be correct for 99% of cases

    A couple of classes using policy based designa smart pointer and a smart resource

    Optional statically bound call backs into a derived classThis is accomplished via __if_exists and __if_notexists

    Numerous macros that can be overridden

  • Responsive to requestsVS SDK release cycle is shortCTP monthlyRTW every 4 months

    Designs are never perfect the first timeEven more so when on short cycle

    Breaking changes will be made as the demand arisesShort cycle means there wont be a lot of BCs with any given release

  • VSL provides help withError and exception handlingUnit testingFunctors and delegatesComparing various thingsManaging resourcesThe basics necessary to create a VS PackageCommand handlingVS Service consumptionCreating a VS Window that hosts a dialog or Win32 controlCreating a VS Document / VS EditorAutomation and VS Macro recordingVS Hierarchies

  • Error and exception handlingError handling macros that convert errors to exceptions

    Exception handling macros that catch and convert exceptions to HRESULTs

    VSL_BEGIN_MSG_MAP message map that catches exceptions

    Header files:VSLErrorHandlers.hVSLExceptionHandlers.hVSL_STDMETHODTRY{




  • Unit testingUnit testing frameworkMocks for nearly all VS Platform interfacesMocks for many Windows Platform interfacesMocks for wrapper classes around some sets of Win32 APIsIncluding some of ATL::CWindow

    Header files:VSLUnitTest.hclass UnitTest : public UnitTestBase{ UnitTest( const char* const szTestName): UnitTestBase(szTestName) { UTCHK(false); }};

    int _cdecl _tmain(int, _TCHAR*){ UTRUN(UnitTest); return VSL::FailureCounter::Get();}

  • Functors and delegatesClasses:FunctorFunctionPointerFunctorMemberFunctionPointerFunctorDelegate

    Header Files:VSLCommon.hFunctionPointerFunctor functor(&OnEvent1);

    Delegate event1;

    event1 += functor;event1();event1 -= functor();

  • Comparing various thingsImplemented primarily for the interface mocksIsStringLessThen can be used with STL algorithms

    Header files:VSLComparison.h

  • Managing resourcesPolicy based resource managers:PointerResource

    Header files:VSLCommon.hVSLFont.htypedef Pointer CoTaskMemPointer;

    CoTaskMemPointer pBuffer = ::CoTaskMemAlloc(iBufferByteSize);

    CHKPTR(static_cast(pBuffer), E_OUTOFMEMORY);

    CHK(0 == ::memcpy_s(pBuffer, iBufferByteSize, GetFileName(), iBufferByteSize), E_FAIL);

    *ppszFilename = static_cast(pBuffer.Detach());

  • The basics necessary to create a VS PackageClasses:IVsPackageImplIVsInstalledProductImpl

    Registry map macros

    Header files:VSLPackage.hclass Package : public IVsPackageImpl< Package, &CLSID_Package>, public IVsInstalledProductImpl< IDS_PRODUCT_NAME, IDS_PRODUCT_IDENTIFIER, IDS_PRODUCT_DETAILS, IDI_ LOGO>{VSL_BEGIN_REGISTRY_MAP(IDR_PACKAGE_RGS)...VSL_END_REGISTRY_MAP()

  • VsSiteCacheCan be local or global

    IVsPackageImpl uses the global VsSiteCache by defaultOnce a package is sited anything can then use the global cache by creating an instance of VsSiteCacheGlobal or utilizing the static methods of VsIServiceProviderUtilities directly or via the macros:VSQS - VsIServiceProviderUtilities::QueryServiceVSQCS - VsIServiceProviderUtilities::QueryCachedService

    IVsPaneWindow uses the local VsSiteCache by defaultOnce window is sited can correctly get context sensitive services like SID_STrackSelection and SID_SVsWindowFrame

  • Command handlingClasses:IOleCommandTargetImplCommand map macrosVsFontCommandHandling

    Header files:VSLCommandTarget.h

    Samples:Menus and CommandsServicesTool WindowSingle View Editorclass MenuAndCommandsPackage : ... public IOleCommandTargetImpl< MenuAndCommandsPackage>,...VSL_BEGIN_COMMAND_MAP() VSL_COMMAND_MAP_ENTRY( GUID_MenuAndCommandsCmdSet, cmdidMyCommand, NULL, &MenuCommandCallback) VSL_COMMAND_MAP_ENTRY_WITH_FLAGS( GUID_MenuAndCommandsCmdSet, cmdidDynVisibility2, NULL, &MenuVisibilityCallback, OLECMDF_SUPPORTED | OLECMDF_ENABLED | OLECMDF_INVISIBLE)VSL_END_VSCOMMAND_MAP()...

  • VS Service consumptionWrapped VS Services:VsOutputWindowUtilitiesProfferServiceUtilitiesOleComponentUIManagerUtilities

    Can use global or local VsSiteCache.OleComponentUIManagerUtilities::ShowMessage( L"Title", L"Message");Header files:VSLPackage.h

    Samples:Menus and CommandServicesTool WindowSingle View Editor

  • Creating a VS Window that hosts a dialogClasses:IVsWindowPaneImplWindowVsWindowPaneFromResource

    Header files:VSLWindows.hclass Form : public VsWindowPaneFromResource< Form, MAKEINTRESOURCE(IDD_DLG)>

  • Creating a VS Window that hosts a Win32 controlClasses:IVsWindowPaneImplWindowListViewWin32ControlRichEditWin32ControlWin32ControlContainer

    Header files:VSLControls.hVSLWindows.hclass Document : public Win32ControlContainer< RichEditWin32Control >

    class Report : public Win32ControlContainer< ListViewWin32Control< ReportViewTraits< false, false> > >

  • Fully integrating a VS WindowClassesVsWindowFrameEventSinkISelectionContainerImplISelectionContainerSingleItemImpl

    Header filesVSLWindows.hclass WindowPane : public IVsWindowPaneImpl, public VsWindowFrameEventSink, public ISomeInterface, public ISelectionContainerSingleItemImpl< WindowPane, ISomeInterface>

  • Creating a VS Document / VS EditorClasses:IVsEditorFactoryImplIVsFindTargetImplSingleViewFindInFilesOutputWindowIntegrationImplFileDocumentPersistanceBase

    Header Files:VSLFile.hVSLFindAndReplace.hVSLWindow.h

    Samples:Single View Editor

  • Automation and VS Macro recordingClass

Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.