Revit API二次开发入门,完整学习流程,附源码

Posted chenyanbin

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Revit API二次开发入门,完整学习流程,附源码相关的知识,希望对你有一定的参考价值。

Revit二次开发入门

Revit二次开发的完整过程

  • 完整演示最简单命令Hello World
  • 调试代码
  • 命令类属性用法
  • 输入输出参数含义
  • 用addin文件加载外部命令
  • 外部命令加载工具AddinManager

两种方式来扩展Revit的功能

方式一:外部命令(External Command)

功能:添加一个Revit命令

描述:由用户点击按钮来启动命令

使用最频繁

方式二:外部应用(External Application)

功能:可以添加菜单和工具条,或其他初始化命令

描述:在启动和关闭Revit.exe时自动执行

一般会用到,用量不多

演示最简单外部命令

功能:运行命令后,弹出消息框,显示Hello World

步骤:使用C#语言创建一个类库

技术图片

技术图片

导入依赖库(重要)

技术图片

技术图片

演示

技术图片

using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Attributes;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace RevitDevTV
{
    [Transaction(TransactionMode.Manual)]
    [Regeneration(RegenerationOption.Manual)]
    public class DevTVHelloWorld : IExternalCommand
    {
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
            MessageBox.Show("Hello World");
            return Result.Succeeded;
        }
    }
    [Transaction(TransactionMode.Manual)]
    [Regeneration(RegenerationOption.Manual)]
    public class ArgumentUsage : IExternalCommand
    {
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
            //获取uiapp信息
            UIApplication uiApp = commandData.Application;
            //获取文档级的application信息
            Autodesk.Revit.ApplicationServices.Application app = uiApp.Application;
            //获取当前模型
            Document doc = uiApp.ActiveUIDocument.Document;
            string strAppInfo = app.VersionBuild+";"+app.VersionName+";"+app.VersionNumber;
            //获取当前选择集
            Autodesk.Revit.UI.Selection.Selection sel = uiApp.ActiveUIDocument.Selection;
            message = "当前选择集中包含如下对象";
            //为了显示错误信息框,需要返回Failled
            return Result.Failed;
        }
    }
}

跟踪调试Revit程序

  Revit运行时调试

  方法:Tools->attach to process->Attach to Revit.exe

  特点:可以随时在VS中Detach调试,此时Revit不退出,灵活方便,可以在Revit不退出的情况下调试多个程序

  用Detach中断调试,继续修改代码,再次绑定来调试

演示

技术图片

Execute参数应用

演示使用Execute的输入输出参数

  • 获取Application对象,供本命令使用
  • 读取版本信息
  • 获取当前文档
  • 返回提示字符串消息
  • 返回选中对象,供用户

Execute参数解释

 public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)

传入参数

  ExternCommandData

  由此获取应用程序对象和文档对象

传出参数

  ref string:传出提示字符串,提示用户存在的问题

  ElementSet:传出一个对象集合,用户可查看其中的对象

外部命令属性

命令前面的两个属性:事务和更新属性

  • [Transaction(TransactionMode.**)]
  • [Regeneration(RegenerationOption.**)]

 两种事务模式

  • 自动事务模式:TransactionMode.Automatic
  • 手工事务模式:TransactionMode.Manual

创建外部应用演示

实现的功能

  在Revit启动时,弹出对话框

  在Revit退出时,弹出一个对话框

实现类:IExternalApplication接口派生

实现OnStartup()和OnShutdown()方法

using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Attributes;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace RevitDevTV
{
    [Transaction(TransactionMode.Manual)]
    [Regeneration(RegenerationOption.Manual)]
    public class DevTVApplication : IExternalApplication
    {
        /// <summary>
        /// 应用关闭实现的功能
        /// </summary>
        /// <param name="application"></param>
        /// <returns></returns>
        public Result OnShutdown(UIControlledApplication application)
        {
            MessageBox.Show("Revit is stop");
            return Result.Failed;
        }
        /// <summary>
        /// 应用启动实现功能
        /// </summary>
        /// <param name="application"></param>
        /// <returns></returns>
        public Result OnStartup(UIControlledApplication application)
        {
            MessageBox.Show("Revit is starting");
            return Result.Succeeded;
        }
    }
}

命令加载

方式一:通过addin文件

  *.addin文件

    可用任意文件名,只要扩展名是addin即可

    只能存放在指定的目录中

      C:Documents and SettingsAll UsersApplication DataAutodeskREVITAddins201*

    在该文件夹下可有多个*.addin文件并存,Revit依次加载其中设置的加载项目

<?xml version="1.0" encoding="utf‐8"?>
<RevitAddIns>
<AddIn Type="Application">
<Name>External Tool</Name>
<Assembly>C:SDKRevitLookupCSinDebugRevitLookup.dll</Assembly>
<ClientId>9631d07b‐ade1‐4ea1‐b566‐049161afcc4c</ClientId>
<FullClassName>RvtMgdDbg.App</FullClassName>
</AddIn>
</RevitAddIns>

方式二:通过Revit.ini文件

  Revit.ini 文件

    该文件位于产品安装目录的Program子文件夹中

    可以加载外部命令和外部应用

    在2012中,不再支持这个方法

[ExternalApplications]
EACount=2
EAClassName1=RvtMgdDbg.App
EAAssembly1=C:alib
evit2011SDKRevitLookupCSinDebugRevitLookup.dll
EAClassName2=RvtSamples.Application
EAAssembly2=C:alib
evit2011SDKSamplesRvtSamplesCSRvtSamples.dll

加载工具AddinManager

  • 加载和卸载用户的程序
  • 加载后,立即可以运行
  • 无需手工编辑addin文件
  • 自动保存加载命令
  • 修改代码编译后立即再次运行
  • 包含在SDK中,需预先安装

Revit数据库对象

技术图片

 

Revit数据库对象的基本特点

构建类型,即构件定义

  存储在数据库中,作为插入到建筑模型中的对象的模板使用。在建筑模型中不可见

  把相同的数据只保存一份

  一个定义,多次使用

  例如:柱类型

构件实例

  已经插入到建筑模型中,在视图中可见。

  时构件定义的引用,如果构件定义改变,实例跟着改变

  例如:插入到建筑模型中的柱。

常用类继承关系图

技术图片

 

访问Revit对象

2011版提供新的对象过滤方法

找出符合条件的对象集合

  找出模型中窗户的数量

using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Attributes;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace RevitDevTV
{
    [Transaction(TransactionMode.Manual)]
    [Regeneration(RegenerationOption.Manual)]
    public class GetAllWindows : IExternalCommand
    {
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
            //获取uiapp信息
            UIApplication uiApp = commandData.Application;
            //获取文档级的application信息
            Autodesk.Revit.ApplicationServices.Application app = uiApp.Application;
            //获取当前模型
            Document doc = uiApp.ActiveUIDocument.Document;
            //方式一:获得所有窗户
            FilteredElementCollector collector = new FilteredElementCollector(doc);
            collector.OfClass(typeof(FamilyInstance)).OfCategory(BuiltInCategory.OST_Windows); //添加限制,找窗户OST_Windows
            IList<Element> lists = collector.ToElements();
            string strMsg = string.Format("there are {0} windows in current model",lists.Count);
            MessageBox.Show(strMsg);
            //方式二:过滤器来获取所有的门
            FilteredElementCollector collector2 = new FilteredElementCollector(doc);
            ElementClassFilter classFilter = new ElementClassFilter(typeof(FamilyInstance));
            ElementCategoryFilter catFilter = new ElementCategoryFilter(BuiltInCategory.OST_Doors);
            LogicalAndFilter logicalFilter = new LogicalAndFilter(classFilter, catFilter);
            collector2.WherePasses(logicalFilter);
            IList<Element> lists2 = collector2.ToElements();
            string strMsg2 = string.Format("there are {0} doors in current model", lists2.Count);
            MessageBox.Show(strMsg2);
            return Result.Succeeded;
        }
    }
}

  找出一层中有多少个窗户

using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Attributes;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace RevitDevTV
{
    [Transaction(TransactionMode.Manual)]
    [Regeneration(RegenerationOption.Manual)]
    public class GetAllWindowsInLevel : IExternalCommand
    {
        public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
        {
            //获取uiapp信息
            UIApplication uiApp = commandData.Application;
            //获取文档级的application信息
            Autodesk.Revit.ApplicationServices.Application app = uiApp.Application;
            //获取当前模型
            Document doc = uiApp.ActiveUIDocument.Document;
            //方式一:获得所有窗户
            FilteredElementCollector collector = new FilteredElementCollector(doc);
            collector.OfClass(typeof(FamilyInstance)).OfCategory(BuiltInCategory.OST_Windows); //添加限制,找窗户OST_Windows
            IList<Element> lists = collector.ToElements();
            //获得一层窗户
            var windowInLevel1 = from element in collector where element.Name == "Level 1" select element;
            string strMsg = string.Format("there are {0} windows in level 1", windowInLevel1.Count());
            MessageBox.Show(strMsg);
            return Result.Succeeded;
        }
    }
}

FilteredElementCollector用法

直接添加过滤条件

  • OfCategory
  • OfCategoryId
  • OfClass

过滤器

  • 使用单一过滤器
  • 多个过滤器的逻辑组合过滤器

使用LINQ

  • .NET 3.5提供功能
  • 可以做更加具体的对象过滤

Revit对象的标识

Revit对象的类名称

  • 直接可以用类名唯一标识出来:如:Wall,WallType,Floor,FloorType...
  • 不同对象,但是公用一个类,FamilyInstance,FamilySymbol,Family,Element

Revit对象的Category名称

  • 通过Revit的Category可以唯一标识对象的类别
  • 门实例和门类型具有相同的Category

其他属性

  • 如所在的楼层
  • 如某一个参数的值

如何识别Revit中不同对象

  • 根据标识来识别区分不同对象
  • 只使用类名来判断
    • 他们的特点
      • 片状能容纳其他对象或特定用途的类
      • 如:Wall、Floor、contFooting、CeilingAndFloor等系统族的实例。
  • 如果通过类名无法分别出来,需联合对象的类别(Category)来判断
    • 门、窗、柱等对象没有专用的类来标识,都是FamilyInstance的实例
    • 用Category来判断其类别
      • 用枚举型的BuiltInCategory,来创建ElementCategoryFilter对象,支持所有国家语言

访问和编辑对象的参数

  • API类:Parameter
  • 作用:保存对象的属性
  • 分类:内置参数和共享参数
  • 优点:扩充共享参数,没有自定义实体的读写权限

访问选中对象所有参数

  • 遍历参数集合:Element.Parameters

演示

 

四种方法获取参数

  • Parameter( parameterId As Parameters.BuiltInParameter )
  • Parameter( definition As Parameters.Definition )
  • Parameter( guid As System.Guid )
  • Parameter(name As String)

修改参数值

  • Parameter.Set()

调试工具之一 RevitLookup

  SDK的根目录下

  读取Revit对象属性和此参数

  提供源代码和工具类

  快速查查看对象数据

SDK中资源介绍

说明性文档

  • Read Me First.doc
  • Getting Started with the Revit API.doc
  • Revit Platform API Changes and Additions.doc
  • Revit 2011 API Namespace Remapping.xlsx

开发参考文档

  • RevitAPI.chm
  • Revit 2011 API Developer Guide.pdf

需要时阅读

  • RevitAddInUtility.chm – 制作安装程序时
  • Autodesk Icon Guidelines.pdf – 制作用户界面
  • Revit Structure – section definitions and mate

重要工具

  • Add‐In Manager 
  • RevitLookup

 

以上是关于Revit API二次开发入门,完整学习流程,附源码的主要内容,如果未能解决你的问题,请参考以下文章

Revit二次开发API PromptForFamilyInstancePlacement

Revut二次开发入门

revit 二次开发之读取参数

Revit二次开发 族参数的获取

Revit 二次开发 元素创建与修改练习

Revit二次开发--Hello World