Microsoft Visual C++ NuGet

From WxWiki
Revision as of 11:45, 26 February 2015 by Andrew.Smart (talk | contribs) (Clarity in a sentence.)
Jump to navigation Jump to search
This article applies to the following versions
wxWidgets Visual C++
Any 2010 Any Edition (but Express is difficult)
Any 2012 Any Edition
Any 2013 Any Edition
*Any Visual Studio Edition that NuGet supports will work

A workaround for MSVC 2010 Express is demonstrated at the end.

The developer must obtain wxWidgets via one of the following:

  1. Source code (most secure, but will take some time to build)
  2. wxPack (includes prebuilt binaries and other goodies)
  3. Prebuilt binaries

A video tutorial playlist illustrating how to obtain wxWidgets via each of the above options, installing the NuGet Package, linking to wxWidgets, creating a GUI with wxFormBuilder, and more is available here[1].

This package is a helper for setting up a C++ project to use wxWidgets. This technique allows each developer working on a project to link to wxWidgets how they want to (from source, from prebuilt, statically/dynamically, etc). This package does not check out or redistribute the wxWidgets library.

NuGet could redistribute prebuilt binaries or even check out the latest stable tag of
wxWidgets and build it for you; but the author of the package feels *not* distributing
prebuilt binaries or the source with the package handles all use-cases best.

This guide (installing the NuGet package) can be completed in 3 easy steps.

Three easy steps

(1) Install the NuGet Package Manager via the Visual Studio Extension Manager

The package manager may already be installed depending on your version/edition of Visual Studio. It can be installed from within Visual Studio, by searching for "NuGet" within Visual Studio's Extension Manager (Tools->Extensions and Updates...). Detailed instructions can be found here[2].

(2) Install the wxWidgetsTemplate NuGet Package via the NuGet Package Manager

This step is is also done from within Visual Studio, and can be done in one of two ways:

  1. Either: Search for and install the wxWidgetsTemplate from within the Manage NuGet Packages pane (Tools->Library Package Manager->Manage NuGet Packages for Solution...):
    ManageNuGetPackages.png
  2. Or: Enter the command Install-Package wxWidgetsTemplate within the Package Manager Console (If hidden, select View->Other Windows->Package Manager Console):
    InstallwxWidgetsTemplatePackageManagerConsole.png

(3) Customize the target wxWidgets library options

ConfigurewxWidgetsTemplate.png
In the image above, bold elements were modified from the default.
In the image above, the wxWidgets properties page may either appear in Common Properties or Configuration Properties depending on
your version of Visual Studio.
You may need to reload the project in order for these properties to show up, and for the included files to be properly parsed.

Open your project's properties (for any project that links to wxWidgets libraries). Here is a description of each of the options, the meaning of which depends on if you have the source code or downloaded prebuilt binaries:

Property Link to wxWidgets source code Link to downloaded prebuilt binaries
wxWidgets path This field will automatically be populated with $(WXWIN) if you had defined the WXWIN environmental variable. Should point to your working copy of the wxWidgets library. This field will automatically be populated with $(WXWIN) if you had defined the WXWIN environmental variable. Should point to the root of where you had extracted the prebuilt binaries (e.g. C:/wxWidgets of C:/wxWidgets/lib/vc120_x64_dll/wxbase30ud_xml_vc120_x64.dll).
SHARED Determines if your project dynamically links or statically links to wxWidgets. Set this to dynamically link to wxWidgets. You may only dynamically link to wxWidgets as static builds are not distributed.
wxTOOLKIT_PREFIX See documentation[3]. If you're not using msw then change this so that the appropriate libraries will be linked to. If you want to try the wxUniversal port set this to 'mswuniv'. Leave the default setting; only msw is prebuilt.
wxMSVC_VERSION Safe to leave this blank, unless you intend to use multiple builds of wxWidgets with multiple versions of the MSVC compiler. You must set this to what you had downloaded and are targeting (e.g. if you downloaded wxMSW-3.0.2_vc120_x64_ReleaseDLL.7z set this to 120).
Print MSBuild Variables during compile? Think of this as a verbosity flag. If you encounter problems turn this on, and inspect the Output pane of visual studio to diagnose the problem(s). This isn't supported by MSVC2010 Express.
Build wxWidgets library? Will check to see that wxWidgets is built and up to date before building your project. If the target wxWidgets build isn't built, it will build it for you. Turn this off to speed up compilation time (as it would skip this check). N/A
Additional build options If building wxWidgets, these options will be passed to the make build. Most of these properties are translated into build options, this property is how you can pass on other build options. 'clean' is useful. Other options are defined in the readmes. N/A

When you build your project, Visual Studio may automatically build wxWidgets, define the necessary preprocessor directives, and link to the appropriate libraries before building your code. If dynamically linking to wxWidgets, the package will set up hard links to the *.dll's within the output folder; this saves space and allows you to run the executable within that working directory (by double clicking on it).

The package will automatically create and use a precompiled header file exclusively for wxWidgets (See CreatePrecompiledHeaderFileProcess.cpp within the package for more information). Note this PCH wasn't designed to be modifiable as modifications would be removed if the NuGet package is updated. It is a shim to be honest- this shim more than halves compilation time as wxWidgets is large. I suggest you use your own PCH if you want to optimize compilation time on other code in your project as well. When using your own PCH such as stdafx.h you'll need to define that manually in the project property pages.

If you have any bugfixes or bug reports for this NuGet package, please submit them on GitHub[4].

Notes on use with prebuilt binaries

Downloading wxPack will probably already set all the prebuilt binaries up for you.

If prebuilt binaries are downloaded manually, the headers must be downloaded as well. Both must be extracted into the same folder (e.g. C:\dev\wxWidgets), such that .\include (headers) and .\lib (prebuilt binaries) exist in that folder.

As an example using MSVC2010 targeting 32-bit, download from here[5]:

  1. ./wxWidgets-3.0.2_headers.7z
  2. ./binaries/wxMSW-3.0.2_vc100_Dev.7z
  3. ./binaries/wxMSW-3.0.2_vc100_ReleaseDLL.7z
vc100 is for MSVC2010. The msi's install to %WINDOWS%/system32 by default so I don't suggest those.
The msi's are more useful as a redistributable of wxWidgets which can be packaged with your project's installer.

These 7z archives after extraction should appear as shown (with both the debug and non-debug DLLs as annotated by the d in the filename, and the vc100_dll may differ depending on what you are targeting):

ExpectedContents.jpg

MSVC 2010 Express doesn't define _UNICODE by default (others do), but the wxWidgets prebuilt binary expects it to be defined as wxWidgets is built supporting Unicode by default. To define _UNICODE for your project, set this property as shown in the image below:

UnicodeCharacterSet.png

Notes on source code management (SCM)

This is a good way of declaring dependencies for your project, as Microsoft Visual Studio will prompt any other developer who opens your C++ project to download any NuGet packages they are missing. e.g. You can add boost, aspell, libssh2, wxWidgets, glew, freeglut, libxml2, SDL, cpprestsdk, protobuf and etcetera as dependencies which are automatically downloaded by the NuGet package manager. These can be found by searching for the 'native' tag[6] (most NuGet packages are portable .NET libraries, and some shouldn't be using the native tag). Using NuGet packages to distribute libraries is useful!

If you use Source Code Management, commit <SolutionDir>/.nuget/packages.config, <SolutionDir>/packages/repositories.config, and <ProjectDir>/packages.config. These contain the links to the NuGet packages; do not version the packages themselves[7]. Other developers opening the project will be notified of the missing dependencies, the dependencies will be downloaded after they press the "Update" button on the prompt. In the event that any NuGet packages are updated by their authors, NuGet will pop up a notification (visually within the NuGet windows) that updates are available.

The options you choose in the properties page will be stored in a *.user file. Do not version this file in SCM, these are your options declaring how you link to wxWidgets and should not be forced on other developers (i.e. not everyone has wxWidgets installed on their system at C:\wxWidgets).

MSVC 2010 Express

The 2010 Express edition does not support NuGet; others editions (Ultimate, Pro) do. Of the 2010 Express products, NuGet only supports Microsoft Visual Web Developer 2010 Express[8]. To get NuGet to install the package to our MSVC 2010 Express project, we must trick that other express product into changing out MSVC project:

  1. Install Microsoft Visual Web Developer 2010 Express.
  2. Install the NuGet Package Manager into that Express product[9]
  3. Rename the project filename from .vcxproj to .csproj (this must be done as Web Express won't open VC++ projects, but will open C# projects).
  4. Open the project's solution file (.sln) with notepad, and rename the .vcxproj to .csproj.
  5. Open the solution with Microsoft Visual Web Developer 2010 Express.
  6. Add the NuGet project.
  7. Close everything, and revert what you had renamed (.csproj -> .vcxproj).

NuGet also mentions a command line client, but that won't do every necessary change. Using Web Developer 2010 Express works.