Revit二次开发入门:第八章交互及UIAPI
本章内容
1.Selection交互API
-
Selection类:
Selection selection=commandData.Application.ActiveUIDocument.Selection;
-
Pick方法-点XYZ(s):PickPoint\PickBox
方法 描述 PickPoint() 提示用户在当前工作平面选取点 PickPoint(string) 用户定义的文字,提示用户在当前工作平面选取点 PickPoint(ObjectSnapTypes) 调用是定的对象捕捉,提示用户在当前工作平面选取一个点 PickPoint(ObjectSnapTypes,string) 调用指定的对象捕捉并用自定义的文字,提示用户在当前工作平面选取一个点 PickBox(PickBoxStyle) 选择一个PickBox PickBox(pickBoxSytle,string) 自定义的文字,提示用户选择一个PickBox -
Pick方法-元素Elements:PickElementsByRectangle
方法 描述 PickElementByRectangle() 提示用户画一个矩形来选取多个元素 PickElementByRectangle(string) 用自定义的文字提示用户画一个矩形来选取过个元素 PickElementByRectangle(ISelectionFilte) 传入一个自定义过滤器,并提示用户画一个矩形来选取过个元素 PickElementByRectangle(ISelectionFilte,string) 传入一个自定义过滤器并用自定义的文字,提示用户画一个矩形来选取多个元素 IList<Element> pickElements = selection.PickElementsByRectangle("Pick Elements"); foreach (Element pickElement in pickElements) { }
IList<Element> pickElements2 = selection.PickElementsByRectangle(new WallSelectionFilter(),"Pick Element"); public class WallSelectionFilter : ISelectionFilter { public bool AllowElement(Element elem) { return elem is Wall; } public bool AllowReference(Reference reference, XYZ position) { return true; } }
-
Pick方法-几何引用Reference(s):PickObject\PickObjects
方法 描述 PickObject(ObjectType) 提示用户选择一个指定类型的Reference PickObject(ObjectType,ISelectionFilter) 传入一个自定义过滤器并提示用户选择一个指定类型的Reference PickObject(ObjectType,string) 用自定义的文字,提示用户选择一个指定类型的Reference PickObject(ObjectType,ISelectionFilter,string) 传入一个自定义过滤器并用自定义的文字,提示用户选择一个指定类型的Reference PickObjects(ObjectType) 提示用户选择多个指定类型的Reference PickObjects(ObjectType,ISelectionFilter) 传入一个自定义过滤器并提示用户选择多个指定类型的Reference PickObjects(ObjectType,string) 用自定义的文字,提示用户选择多个指定类型的Reference PickObjects(ObjectType,ISelectionFilter,string) 传入一个自定义过滤器并用自定义的文字,提示用户选择多个指定类型的Reference Reference reference = selection.PickObject(ObjectType.Face, "Select a Wall"); Element wall = doc.GetElement(reference);
Reference reference = selection.PickObject(ObjectType.Face, new WallSelectionFilter(),"Select a Wall"); Element wall = doc.GetElement(reference); Face face=wall.GetGeometryObjectFromReference(reference) as Face;
-
取消选择
(ESC)->OperationCanceledException
try { //pick... } catch (OperationCanceledException) { //ESC pressed }
-
实例练习
-
选择一个点,再改点创建一个柱子
-
选择刚创建的柱子,计算器体积
-
框选若干元素,得到选中的墙的数量
using Autodesk.Revit.Attributes; using Autodesk.Revit.DB; using Autodesk.Revit.DB.Structure; using Autodesk.Revit.UI; using Autodesk.Revit.UI.Selection; using System.Collections.Generic; using System.Linq; using OperationCanceledException = Autodesk.Revit.Exceptions.OperationCanceledException; namespace SelectTest { [TransactionAttribute(TransactionMode.Manual)] [RegenerationAttribute(RegenerationOption.Manual)] public class SelectTest : IExternalCommand { public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements) { UIDocument uiDoc = commandData.Application.ActiveUIDocument; Document doc = uiDoc.Document; Selection selection = uiDoc.Selection; XYZ point = null; try { point = selection.PickPoint("请选择一个点"); } catch (OperationCanceledException e) { TaskDialog.Show("Error", e.Message); return Result.Succeeded; } using (Transaction t1 = new Transaction(doc, "T1")) { t1.Start(); FamilySymbol familySymbol = doc.GetElement(new ElementId(338370)) as FamilySymbol; if (familySymbol != null) { if (!familySymbol.IsActive) { familySymbol.Activate(); } } else { return Result.Failed; } Level level = doc.GetElement(new ElementId(311)) as Level; FamilyInstance familyInstance = doc.Create.NewFamilyInstance(point, familySymbol, level, StructuralType.NonStructural);//创建柱子实体 t1.Commit(); } Selection selection2 = uiDoc.Selection; Reference re = selection2.PickObject(ObjectType.Element, "请选择一个物体"); Element ele = doc.GetElement(re); Options opt = new Options(); GeometryElement geometry = ele.get_Geometry(opt); double v = 0.0; v = GetSolid(geometry).Sum(m => m.Volume * 0.3048 * 0.3048 * 0.3048); TaskDialog.Show("Hint", "选中的物体的体积为" + v.ToString("f3")); IList<Element> pickElements = selection2.PickElementsByRectangle(new WallSelectionFilter(), "请框选目标物体"); double num = pickElements.Count; TaskDialog.Show("T", "已选中墙数为" + num); return Result.Succeeded; } private List<Solid> GetSolid(GeometryElement gelem) { List<Solid> solids = new List<Solid>(); foreach (GeometryObject o in gelem) { if (o is Solid) { solids.Add(o as Solid); } if (o is GeometryElement) { solids.AddRange(GetSolid(o as GeometryElement)); } if (o is GeometryInstance) { GeometryInstance geometryInstance = o as GeometryInstance; GeometryElement geometry = geometryInstance.GetInstanceGeometry(); solids.AddRange(GetSolid(geometry)); } } return solids; } } public class WallSelectionFilter : ISelectionFilter { public bool AllowElement(Element elem) { return elem is Wall; } public bool AllowReference(Reference reference, XYZ position) { return true; } } }
-
-
2.TaskDialog任务对话框
在RevIt中,任务对话框是具有Revit风格的Windows对话框的替代品,是一种典型的模态对话框。
-
创建展示任务对话框的两种方法:
- 创建并单独设任务对话框,使用Show()方法显示给用户
- 运用静态Show方法直接创建并展示给用户(仅有一个子集的选项可被设定)
-
任务对话框可以被用于:
- 给用户提供信息
- 询问用户,并得到反馈
- 允许用户选择,并执行相应的命令
-
任务对话框的控件:
-
Title-标题
-
Main Instruction-主标题
-
Main Content-主要内容
-
Expanded Content-扩展内容
-
Command Links-命令链接
-
Common Button-普通按钮
-
Default button or link-默认按钮或链接
-
DNSM CheckBox-不再提示复选框
-
Footer Text文字信息
方法 描述 Show() 显示任务对话框 show(string,string) 显示一个包含标题、主要说明和关闭按钮的任务对话框 Show(string,string,TaskDialogCommonButtons) 显示一个包含标题、主要说明和普通按钮的对话框 Show(string,string,TaskDialogCommonButtons,TaskDialogResult) 显示一个包含标题、主要说明、普通按钮和默认按钮的任务对话框
Taskdialog.Show("title","Instruction");
TaskDialogResult result = TaskDialog.Show("title", "Instruction", TaskDialogCommonButtons.Ok| TaskDialogCommonButtons.No, TaskDialogResult.No);
using Autodesk.Revit.ApplicationServices; using Autodesk.Revit.Attributes; using Autodesk.Revit.DB; using Autodesk.Revit.UI; namespace Dialog { [TransactionAttribute(TransactionMode.Manual)] [RegenerationAttribute(RegenerationOption.Manual)] public class DialogTest : IExternalCommand { public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements) { UIDocument uiDoc = commandData.Application.ActiveUIDocument; Document doc = uiDoc.Document; Application app = doc.Application; TaskDialog td = new TaskDialog("Title") { MainInstruction = "Instrution" }; td.AddCommandLink(TaskDialogCommandLinkId.CommandLink1, "Line1 content", "Support content1"); td.AddCommandLink(TaskDialogCommandLinkId.CommandLink2, "查看产品信息"); td.CommonButtons = TaskDialogCommonButtons.Close | TaskDialogCommonButtons.Yes | TaskDialogCommonButtons.No; td.DefaultButton = TaskDialogResult.Close; td.ExpandedContent = "Expanded"; td.FooterText = "<a href=\"https://www.5616760.com\">" + "关于我们</a>"; td.MainIcon = TaskDialogIcon.TaskDialogIconWarning; td.TitleAutoPrefix = false; td.VerificationText = "不再提醒"; TaskDialogResult result = td.Show(); bool ischecked = td.WasVerificationChecked(); if (result == TaskDialogResult.CommandLink1) { TaskDialog dialog1 = new TaskDialog("版本信息") { MainInstruction = "版本名:" + app.VersionName + "\n版本号:" + app.VersionNumber }; dialog1.Show(); } else if (result == TaskDialogResult.CommandLink2) { TaskDialog.Show("信息", "sdafasdf asfdsadf sdaf g gsadf sdaf"); } return Result.Succeeded; } } }
-
3.Ribbon菜单
- RibbonTab-选项卡页:用户可以创建一个新的选项卡页,用来管理自己的面板RibbonPanel
- RibbonPanel-面板:其他空间的容器
- PushButton-命令按钮:对应一个ExternalCommand,单击这个按钮,对应的ExternalCommand将被执行
- PulldownButton-下拉按钮:带有下拉列表的按钮控件,表中的每个元素都是一个命令按钮,在下拉列表的元素键可以加水平分割线
- SplitButton-下拉记忆按钮:是下拉按钮的派生类控件,分为上下两部分,上部分功能类似命令按钮,下部分按钮类似下拉按钮
- ComboBox-下拉组合框:是有下拉列表的选择控件,通过单击控件上的箭头可显示或隐藏下拉列表,此控件不支持多项选择
-
创建Ribbon对象
一般都在IExternalApplication的OnStartup函数里面,IExternalCommand也可以
-
创建RibbonTab:
UIControlledApplication.CreateRibbonTab(string)
UIApplication.CreateRibbonTab(string)
-
创建RibbonPanel:
UIControlledApplication.CreateRibbonPanel(tabName,panelName)
UIApplication.CreateRibbonPanel(tabName,panelName)
-
创建控件(按钮等)
RibbonPanel.AddItem(RibbonItemData)
using Autodesk.Revit.Attributes; using Autodesk.Revit.UI; using Autodesk.Revit.UI.Events; using System; using System.Windows.Media.Imaging; namespace Ribbon1 { [TransactionAttribute(TransactionMode.Manual)] [RegenerationAttribute(RegenerationOption.Manual)] public class RibbonTest : IExternalApplication { public Result OnShutdown(UIControlledApplication application) { return Result.Succeeded; } public Result OnStartup(UIControlledApplication application) { application.CreateRibbonTab("UCD场地工具"); RibbonPanel panel1 = application.CreateRibbonPanel("UCD场地工具", "欢迎页"); PushButtonData pbd = new PushButtonData("UCD场地工具", "欢迎使用", @"D:\Studay\CSharp\Work\Revit\HelloRevit\bin\Debug\HelloRevit.dll", "HelloRevit.Class1"); PushButton pb = panel1.AddItem(pbd) as PushButton; RibbonPanel panel2 = application.CreateRibbonPanel("UCD场地工具", "工具"); SplitButtonData splitData = new SplitButtonData("我的集合", "创建工具"); SplitButton sb = panel2.AddItem(splitData) as SplitButton; PushButtonData spd = new PushButtonData("UCD场地工具", "创建", @"D:\Studay\CSharp\Work\Revit\Create2\bin\Debug\Create2.dll", "Create2.CreateBox") { LargeImage = new BitmapImage(new Uri(@"D:\Studay\CSharp\Work\Revit\Ribbon1\img\sign_road.png")) }; sb.AddPushButton(spd); panel2.AddSeparator(); PulldownButtonData pdbd = new PulldownButtonData("UCD场地工具", "检查"); PushButtonData pushbtn = new PushButtonData("UCD场地工具", "碰撞检查", @"D:\Studay\CSharp\Work\Revit\Collision\bin\Debug\Collision.dll", "Collision.Class1"); PulldownButton btn = panel2.AddItem(pushbtn) as PulldownButton; btn.LongDescription = "检查当前物体是否碰撞"; btn.AddPushButton(pushbtn); RibbonPanel panel3 = application.CreateRibbonPanel("UCD场地工具", "文件"); ComboBoxData cbd = new ComboBoxData("选项"); ComboBox cBox = panel3.AddItem(cbd) as ComboBox; if (cBox != null) { cBox.ItemText = "选择操作"; cBox.ToolTip = "请选择想要进行的操作"; cBox.LongDescription = "选择一直接关闭,选择二关闭并修改"; ComboBoxMemberData cbmd = new ComboBoxMemberData("A", "关闭"); ComboBoxMemberData cbmd2 = new ComboBoxMemberData("B", "关闭并修改"); cbmd.GroupName = "编辑操作"; cBox.AddItem(cbmd); cBox.AddItem(cbmd2); } cBox.CurrentChanged += Change; cBox.CurrentChanged += Closed; return Result.Succeeded; } private void Closed(object sender, ComboBoxCurrentChangedEventArgs e) { TaskDialog.Show("关闭", "已关闭"); } private void Change(object sender, ComboBoxCurrentChangedEventArgs e) { TaskDialog.Show("修改", "已修改"); } } }
能正常显示了,虽然还不够完美。