VS: add VS_CSHARP_<tagname> sourcefile property

This commit is contained in:
Michael Stürmer 2017-02-23 16:48:16 +01:00 committed by Brad King
parent 6cbad490c2
commit 9588d0a2e2
5 changed files with 67 additions and 56 deletions

View File

@ -366,6 +366,7 @@ Properties on Source Files
/prop_sf/SKIP_AUTOUIC
/prop_sf/SYMBOLIC
/prop_sf/VS_COPY_TO_OUT_DIR
/prop_sf/VS_CSHARP_tagname
/prop_sf/VS_DEPLOYMENT_CONTENT
/prop_sf/VS_DEPLOYMENT_LOCATION
/prop_sf/VS_INCLUDE_IN_VSIX

View File

@ -0,0 +1,19 @@
VS_CSHARP_<tagname>
-------------------
Visual Studio and CSharp source-file-specific configuration.
Tell the Visual Studio generator to set the source file tag
``<tagname>`` to a given value in the generated Visual Studio CSharp
project. Ignored on other generators and languages. This property
can be used to define dependencies between source files or set any
other Visual Studio specific parameters.
Example usage:
.. code-block:: cmake
set_source_files_property(<filename>
PROPERTIES
VS_CSHARP_DependentUpon <other file>
VS_CSHARP_SubType "Form")

View File

@ -34,15 +34,6 @@ C#
Visual Studio (``VS_*``) are worth a look (for setting toolset
versions, root namespaces, assembly icons, ...).
* Auto-linking in ``.csproj`` files: In C#/.NET development with
Visual Studio there are a number of visual editors used which
generate code. Both the generated files and the ones edited
with the UI are connected in the ``.csproj`` file using
``<DependentUpon>`` tags. If CMake finds within a C# project
any source file with extension ``.Designer.cs`` or ``.xaml.cs``,
it checks sibling files with extension ``.xaml``, ``.settings``,
``.resx`` or ``.cs`` and establishes the dependency connection.
CUDA
^^^^

View File

@ -86,6 +86,7 @@ public:
// Get the properties
cmPropertyMap& GetProperties() { return this->Properties; }
const cmPropertyMap& GetProperties() const { return this->Properties; }
/**
* Check whether the given source file location could refer to this

View File

@ -680,20 +680,40 @@ void cmVisualStudio10TargetGenerator::WriteEmbeddedResourceGroup()
if (const char* g = (*oi)->GetProperty("VS_RESOURCE_GENERATOR")) {
generator = g;
}
this->WriteString("<Generator>", 3);
(*this->BuildFileStream) << cmVS10EscapeXML(generator)
<< "</Generator>\n";
if (designerResource.find(srcDir) == 0) {
designerResource = designerResource.substr(srcDir.length() + 1);
} else if (designerResource.find(binDir) == 0) {
designerResource = designerResource.substr(binDir.length() + 1);
} else {
designerResource =
cmsys::SystemTools::GetFilenameName(designerResource);
if (!generator.empty()) {
this->WriteString("<Generator>", 3);
(*this->BuildFileStream) << cmVS10EscapeXML(generator)
<< "</Generator>\n";
if (designerResource.find(srcDir) == 0) {
designerResource = designerResource.substr(srcDir.length() + 1);
} else if (designerResource.find(binDir) == 0) {
designerResource = designerResource.substr(binDir.length() + 1);
} else {
designerResource =
cmsys::SystemTools::GetFilenameName(designerResource);
}
this->ConvertToWindowsSlash(designerResource);
this->WriteString("<LastGenOutput>", 3);
(*this->BuildFileStream) << designerResource
<< "</LastGenOutput>\n";
}
}
const cmPropertyMap& props = (*oi)->GetProperties();
for (cmPropertyMap::const_iterator p = props.begin(); p != props.end();
++p) {
static const std::string propNamePrefix = "VS_CSHARP_";
if (p->first.find(propNamePrefix.c_str()) == 0) {
std::string tagName = p->first.substr(propNamePrefix.length());
if (!tagName.empty()) {
std::string value = props.GetPropertyValue(p->first);
if (!value.empty()) {
this->WriteString("<", 3);
(*this->BuildFileStream) << tagName << ">";
(*this->BuildFileStream) << cmVS10EscapeXML(value);
(*this->BuildFileStream) << "</" << tagName << ">\n";
}
}
}
this->ConvertToWindowsSlash(designerResource);
this->WriteString("<LastGenOutput>", 3);
(*this->BuildFileStream) << designerResource << "</LastGenOutput>\n";
}
}
@ -1940,42 +1960,21 @@ bool cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags(
sourceFileTags["Link"] = link;
}
}
// check if file is a generated .Designer.cs or .xaml.cs file
// to add additional necessary tags
const std::string fileExtension =
cmsys::SystemTools::GetFilenameExtension(f);
if (fileExtension == ".Designer.cs" || fileExtension == ".xaml.cs") {
f = f.substr(0, f.length() - fileExtension.length());
if (sourceFileTags.find("Link") == sourceFileTags.end() &&
!this->InSourceBuild) {
// add link fallback
sourceFileTags["Link"] =
cmsys::SystemTools::GetFilenameName(f) + fileExtension;
}
std::vector<std::string> extensions;
extensions.push_back(".resx");
extensions.push_back(".settings");
extensions.push_back(".xaml");
extensions.push_back(".cs");
std::string dependencyExtension;
for (std::vector<std::string>::iterator i = extensions.begin();
i != extensions.end(); ++i) {
if (cmsys::SystemTools::FileExists(f + *i)) {
dependencyExtension = *i;
// There should never be more than one match. Otherwise
// one cannot tell on which match the file depends.
break;
const cmPropertyMap& props = sf.GetProperties();
for (cmPropertyMap::const_iterator p = props.begin(); p != props.end();
++p) {
static const std::string propNamePrefix = "VS_CSHARP_";
if (p->first.find(propNamePrefix.c_str()) == 0) {
std::string tagName = p->first.substr(propNamePrefix.length());
if (!tagName.empty()) {
const std::string val = props.GetPropertyValue(p->first);
if (!val.empty()) {
sourceFileTags[tagName] = val;
} else {
sourceFileTags.erase(tagName);
}
}
}
if (dependencyExtension == ".resx") {
sourceFileTags["DesignTime"] = "True";
sourceFileTags["AutoGen"] = "True";
} else if (dependencyExtension == ".settings") {
sourceFileTags["DesignTimeSharedInput"] = "True";
sourceFileTags["AutoGen"] = "True";
}
sourceFileTags["DependentUpon"] =
cmsys::SystemTools::GetFilenameName(f) + dependencyExtension;
}
// write source file specific tags
if (!sourceFileTags.empty()) {