33

I have two similar problems:

a) I have a solution which includes several projects and I want to be able easily switch project location by setting some environment variable/macro. As example this project can be located in \SolutionDir\Dir1\ or \SolutionDir\Dir2\ So, I want to specify that it should be located in \SolutionDir\$(Var) and just set the variable.

Is there any build in Visual Studio way to do it?

I know currently only two solutions - edit .sln file manual/programmatically to find this project and set correct path.

I wasn't able to use environment variable in .sln file.

b) I have a project which includes resources (.rc and .h) files. I want to be able to set their location through other environment variable or macro.

Something like \ProjectDir\$(Var2)\resource.rc

I found some promising info on property sheets, but Visual studio doesn't expand macros when I am using them in File tag in the .vcproj.

Thank you for any ideas how to solve this problem.

Regards, Victor

  • interesting. But I can't figure out why you want to do this. There's probably a different way to solve the issue you are trying to address. – Tim May 08 '09 at 16:10
  • I want to setup the project to be easily switchable between branded versions of product for different OEM's. –  May 11 '09 at 20:11

6 Answers6

23

Just use the environment variable in the relevant field:

OutputDirectory="$(MyEnvVariableName)\Bin"

One trick is that you need to restart the Visual Studio IDE each time you change the variable.

There is an MSDN article precisely about this: How to: Use Environment Variables in a Build

Rom
  • 4,129
  • 23
  • 18
21

I think I have the same goal than you: I want to use environment variables to locate some projects in a solution file (.sln) and to use some environment variables to locate some files within my projects.

I found a way to do that and it works fine for me (with Visual Studio 2005): - edit the .sln file with a text editor and use environment variables with the following syntax %MyEnvironmentVariable% - edit the .vcproj files and replace the path to the desired files with some variables, with the following syntax $(MyEnvironmentVariable).

Hope it helps... Cyrille

  • 2
    This is just what I was looking for, didn't know that .sln uses %VAR% syntax, I've been using $(VAR) that works in .scproj. Thx! – watbywbarif May 30 '12 at 08:45
  • Be aware that introducing variables into a .sln file means that they cannot be used with MSBuild. See See https://connect.microsoft.com/VisualStudio/feedback/details/690318/msbuild-doesnt-parse-environment-variables-in-sln-files – cowlinator Nov 30 '17 at 01:11
  • The link by @cowlinator is dead but the issue remains, see [this issue](https://github.com/Microsoft/msbuild/issues/120) – BNT Nov 26 '18 at 12:02
2

The best way to achieve what you describe in b) is to use property sheets. Check out also this very similar question.

I found some promising info on property sheets, but Visual studio doesn't expand macros when I am using them in File tag in the .vcproj.

I am not sure what version of VS you use. VS2008 lets you define for example an include directory like this: "$(OpenCVInclude)\cxcore\include". I use it all the time. OpenCVInclude is a macro defined in a property sheet.

As for question a), I think there is no "clean" way to do what you want. As an alternative you could the configuration manager:

  • Include all the projects in the solution.
  • Name the project differently, for example based on the OEM.
  • For each project define release and debug configurations in the solution
  • In "Build->Configuration Manager" You can check or uncheck the "Build" column for each configuration. Check "build" for the relevant project.
Community
  • 1
  • 1
Dani van der Meer
  • 6,169
  • 3
  • 26
  • 45
1

I am not sure if you are building just C++ projects or if you are also building C#\VB projects, but one of the great things about Visual Studio is all of the projects are really just MSBuild projects. If you edit a project in a text editor you will see that at the end of the project it imports a .targets file. If you track down and find follow the imports you will find that almost all of the VS projects import Microsoft.Common.Targets. Microsoft.Common.Targets imports Custom.Before.Microsoft.Common.Targets. Using this import you can import your own targets file with your own custom actions.

I for example have a target file that has a common property defined across all projects in a solution and a custom post build event that processes at the end of each project building.

Using this extension method and by creating custom configurations in the solution besides just the standard release\debug, you should be able to create as complex of a build configuration as you need.

mageos
  • 1,216
  • 7
  • 15
0

One solution is to set some enviroment variables just before starting VS. In our projects we use a batch file which looks like this:

SET ROOT=D:/root
SET COMPILER_ROOT=C:/Program Files (x86)/Microsoft Visual Studio 12.0/Common7/IDE
start "Microsoft Visual Studio 12.0" /D"%COMPILER_ROOT%\" "%COMPILER_ROOT%/devenv.exe" "%ROOT%\trunk\OurSolution.sln"
Jacob
  • 21
  • 4
0

(a) Cyrille gives a decent solution to what you asked for. Another way is to keep your changeable settings in one common place. Note that this won't work for non-msbuild files like *.sln and *.vcproj (until VS 2010).

Project files: ... $(ChangeableDir)\foo.cs

Common.targets: ChangeThis ...

However, I don't think this is a great way to do things. If the differences between what you're building are large pieces of functionality, you should consider creating a branch in your source control system. OTOH, if the differences are minor -- eg hardcoded strings -- then this leads to your second question...

(b) The kind of resource management you describe is essentially the same problem faced by people localizing their project into different languages. Luckily, direct support is built into Visual Studio since 2005. Check out previous questions like: Localization in Visual Studio 2008

Community
  • 1
  • 1
Richard Berg
  • 20,629
  • 2
  • 66
  • 86