Nice3point.Revit.Sdk
6.0.2
Prefix Reserved
<Sdk Name="Nice3point.Revit.Sdk" Version="6.0.2" />
#:sdk Nice3point.Revit.Sdk@6.0.2
Revit MSBuild SDK
MSBuild SDK for developing and publishing the add-ins for multiple Revit versions.
Table of contents
- Features
- Installation
- Preprocessor symbols
- Publishing
- Assembly repacking
- Manifest patching
- Implicit global usings
- Launch configuration
- Configuration
Features
- Add-ins development for multiple Revit API versions from a single codebase.
- Automatic Frameworks configuration. No need to manually set .NET versions for each Revit API version, the SDK does it for you.
- Easy Testing automatically copies your add-in to Revit folders for quick testing.
- Manifest patching automatically fixes .addin files to support breaking changes between Revit versions.
- Clean Project Files removes all the messy boilerplates from your .csproj configuration.
Installation
To use this SDK, you need to specify it in the Sdk attribute of the <Project> element in your .csproj file:
<Project Sdk="Nice3point.Revit.Sdk/<version>">
</Project>
Preprocessor symbols
Preprocessor symbols (#define constants) are used in conditional compilation to enable or exclude code based on the target Revit version.
This ensures compatibility across multiple Revit versions without code duplication.
The OR_GREATER symbols are cumulative and provide a cleaner way to handle version-specific API changes.
Each symbol indicates compatibility with the specified version and all newer versions.
| Current configuration | Project configurations | Generated define constants |
|---|---|---|
| Debug.R20 | Debug.R20, Debug.R21, Debug.R22 | REVIT2020, REVIT2020_OR_GREATER |
| Release.R21 | Release.R20, Release.R21, Release.R22 | REVIT2021, REVIT2020_OR_GREATER, REVIT2021_OR_GREATER |
| Release.2022 | Debug.2020, Release.2021, Release.2022 | REVIT2022, REVIT2020_OR_GREATER, REVIT2021_OR_GREATER, REVIT2022_OR_GREATER |
Usage:
#if REVIT2021_OR_GREATER
UnitUtils.ConvertFromInternalUnits(69, UnitTypeId.Millimeters);
#else
UnitUtils.ConvertFromInternalUnits(69, DisplayUnitType.DUT_MILLIMETERS);
#endif
To support removed APIs in newer versions of Revit, you can invert the constant:
#if !REVIT2023_OR_GREATER
var builtinCategory = (BuiltInCategory) category.Id.IntegerValue;
#endif
Constants are generated from the names of project configurations.
Supported formats: Release.R25, Release.2025, 2025 Release. Two or four digits. If your project configurations do not contain metadata about the version, you can specify it explicitly:
<PropertyGroup>
<RevitVersion>2025</RevitVersion>
</PropertyGroup>
Preprocessor symbols generating is enabled by default, to disable implicit defines, set the DisableImplicitRevitDefines property:
<PropertyGroup>
<DisableImplicitRevitDefines>true</DisableImplicitRevitDefines>
</PropertyGroup>
Publishing
Depending on your workflow, you can either deploy the files locally for immediate testing and debugging or publish them into a folder for further distribution.
Local deployment
To copy Revit add-in files to the %AppData%\Autodesk\Revit\Addins folder after building a project, you can enable the DeployAddin property.
Copying files helps attach the debugger to the add-in when Revit starts. This makes it easier to test the application or can be used for local development.
<PropertyGroup>
<DeployAddin>true</DeployAddin>
</PropertyGroup>
When DeployAddin is enabled, PublishAddin is enabled implicitly.
You can override target folders:
<PropertyGroup>
<AddinPublishDir>$(OutputPath)\publish</AddinPublishDir>
<AddinDeployDir>$(ProgramData)\Autodesk\Revit\Addins\$(RevitVersion)</AddinDeployDir>
</PropertyGroup>
Default: Disabled
Should only be enabled in projects containing the Revit manifest file (.addin).
Clean solution or Clean project commands will delete the deployed files.
Publishing for distribution
If your goal is to generate an installer or a bundle, enable the PublishAddin property.
This configuration publishes the compiled files into the bin\publish folder.
<PropertyGroup>
<PublishAddin>true</PublishAddin>
</PropertyGroup>
Default: Disabled
Publish extra content
By default, all project files and dependencies required for the add-in to run, including the .addin manifest, are copied.
If you need to include additional files, such as configuration or family files, include them in the Content item.
<ItemGroup>
<Content Include="Resources\Families\Window.rfa" CopyToPublishDirectory="Always"/>
<Content Include="Resources\Music\Click.wav" CopyToPublishDirectory="PreserveNewest"/>
<Content Include="Resources\Images\**" CopyToPublishDirectory="PreserveNewest"/>
</ItemGroup>
To enable copying Content files, set CopyToPublishDirectory="Always" or CopyToPublishDirectory="PreserveNewest"
The PublishDirectory property specifies which subfolder of the add-in the file should be copied to.
If it is not specified, the files will be copied to the root folder.
<ItemGroup>
<Content Include="Resources\Families\Window.rfa" PublishDirectory="Families" CopyToPublishDirectory="PreserveNewest"/>
<Content Include="Resources\Music\Click.wav" PublishDirectory="Music\Effects" CopyToPublishDirectory="PreserveNewest"/>
<Content Include="Resources\Images\**" PublishDirectory="Images" CopyToPublishDirectory="PreserveNewest"/>
<Content Include="Readme.md" CopyToPublishDirectory="PreserveNewest"/>
</ItemGroup>
Result:
📂bin\publish; %AppData%\Autodesk\Revit\Addins\2025
┣📜RevitAddIn.addin
┗📂RevitAddIn
┣📂Families
┃ ┗📜Family.rfa
┣📂Images
┃ ┣📜Image.png
┃ ┣📜Image2.png
┃ ┗📜Image3.jpg
┣📂Music
┃ ┗📂Effects
┃ ┗📜Click.wav
┣📜CommunityToolkit.Mvvm.dll
┣📜RevitAddIn.dll
┗📜Readme.md
Assembly repacking
Assembly repacking is used to merge multiple assemblies into a single Dll, primarily to avoid dependency conflicts between different add-ins.
If you need to repack assemblies into a single Dll, enable the IsRepackable property.
ILRepack package is required in your project.
<PropertyGroup>
<IsRepackable>true</IsRepackable>
</PropertyGroup>
Default: false
To exclude certain assemblies from repacking if they cause unexpected behavior, specify them using the RepackBinariesExcludes property:
<PropertyGroup>
<RepackBinariesExcludes>$(AssemblyName).UI.dll;System*.dll</RepackBinariesExcludes>
</PropertyGroup>
Wildcards are supported. All binaries are repacked into the bin directory after the build.
For .NET Core applications, it is recommended to disable this feature and use Dependency Isolation, which is available starting from Revit 2026.
Manifest patching
By default, enabled target is used to modify the Revit .addin manifest to ensure backward compatibility between different Revit versions.
For example, if the manifest includes nodes or properties, which is only supported in newest Revit version, it will be removed for older versions.
Currently, the SDK removes the ManifestSettings node for Revit versions older than 2026.
Original .addin manifest:
<RevitAddIns>
<AddIn Type="Application">
<Name>RevitAddin</Name>
<Assembly>RevitAddin\RevitAddin.dll</Assembly>
</AddIn>
<ManifestSettings>
<UseRevitContext>False</UseRevitContext>
</ManifestSettings>
</RevitAddIns>
Patched .addin manifest for Revit 2025 and older:
<RevitAddIns>
<AddIn Type="Application">
<Name>RevitAddin</Name>
<Assembly>RevitAddin\RevitAddin.dll</Assembly>
</AddIn>
</RevitAddIns>
Target is triggered automatically when the PublishAddin target runs.
Implicit global usings
By default, included a target for generating implicit global Usings depending on the project references. Helps to reduce the frequent use of using in a project.
| Global Using | Enabled by reference |
|---|---|
| using Autodesk.Revit.DB; | RevitAPI.dll |
| using JetBrains.Annotations; | JetBrains.Annotations.dll |
| using Nice3point.Revit.Extensions; | Nice3point.Revit.Extensions.dll |
| using Nice3point.Revit.Toolkit; | Nice3point.Revit.Toolkit.dll |
| using CommunityToolkit.Mvvm.Input; | CommunityToolkit.Mvvm.dll |
| using CommunityToolkit.Mvvm.ComponentModel; | CommunityToolkit.Mvvm.dll |
To disable implicit usings, set the ImplicitRevitUsings property:
<PropertyGroup>
<ImplicitRevitUsings>false</ImplicitRevitUsings>
<ImplicitUsings>false</ImplicitUsings>
</PropertyGroup>
Alternatively, you can disable individual usings:
<ItemGroup>
<Using Remove="Autodesk.Revit.DB"/>
</ItemGroup>
Launch configuration
To configure a default debug profile that launches the target Revit version, enable the LaunchRevit property:
<PropertyGroup>
<LaunchRevit>true</LaunchRevit>
</PropertyGroup>
If you want to run Revit in a different language or installed in a different directory, also override some properties.:
<PropertyGroup>
<StartProgram>C:\Program Files\Autodesk\Revit $(RevitVersion)\Revit.exe</StartProgram>
<StartArguments>/language ENG</StartArguments>
</PropertyGroup>
Configuration
This Sdk overrides some Microsoft Sdk properties for the optimal add-in development:
| Property | Default value | Description |
|---|---|---|
| TargetFramework | dynamic | Automatically sets the TargetFramework based on the RevitVersion property. |
| LangVersion | latest | Sets the C# language version to the latest installed version. |
| Nullable | enable | Enables C# nullable reference types. |
| ImplicitUsings | true | Enables implicit usings for the project. |
| ImplicitRevitUsings | true | Enables generation of Revit-related implicit global usings (see section above). |
| AppendTargetFrameworkToOutputPath | false** | Prevents the TFM from being appended to the output path. Required for add-in publishing. |
| Optimize | dynamic | Enabled for Release configurations. |
| DebugSymbols | dynamic | Enabled for Debug configurations. |
| DebugType | dynamic | portable for Debug, none for Release configurations. |
These properties are automatically applied to the .csproj file, but can be overriden:
<PropertyGroup>
<ImplicitRevitUsings>false</ImplicitRevitUsings>
<TargetFramework Condition="$(RevitVersion) == '2025'">net8.0</TargetFramework>
</PropertyGroup>
** When packing/publishing a NuGet package (if PackageType or PackageId is specified), the SDK forces AppendTargetFrameworkToOutputPath=true to keep outputs separated by TFM.
TargetFramework default values:
| RevitVersion | TargetFramework |
|---|---|
| 2014 | net40 |
| 2015 | net45 |
| 2016-2017 | net452 |
| 2018 | net46 |
| 2019-2020 | net47 |
| 2021-2024 | net48 |
| 2025-2026+ | net8.0-windows7.0 |
Learn more about Target Frameworks and .NET Standard.
This package has no dependencies.
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
SDK
• Added support for Revit 2027.
• Fixed Visual Studio launch profile support.
• Updated Polyfill to 9.7.0.
Solution template
• Updated Sourcy.DotNet to 1.0.0.
• Updated assertions in CreateBundleModule.
Revit Test (TUnit) template
• Updated TUnit to 1.9.81.
• Added EnableTUnitPolyfills property.