当前位置: 首页 > backend >正文

Python+DRVT 从外部调用 Revit:批量创建门

    昨天实现了一个完整的示例 Python+DRVT 从外部调用 Revit:批量创建墙,今天我们将在此基础上稍作扩展:每创建一堵墙之后,在其中间位置创建一扇门。

from typing import List
import math
# drvt_pybind 支持多会话、多文档,先从简单的单会话、单文档开始
# MyContext是在Python中用户自定义的单会话、单文档的上下文管理类
from packs.core import MyContext, m2feet, feet2m, isNone# 导入驱动 Revit 的核心模块
from drvt_pybind.Autodesk import Revit
from drvt_pybind.Autodesk.Revit import DB
from drvt_pybind.Autodesk.Revit.DB import Structure# 遍历标高,返回按Elevation从低到高的List[DB.Level]
def getLevels(ctx : MyContext) -> List[DB.Level]:tmp : List[DB.Level] = []levelList = DB.FilteredElementCollector.ctor(ctx.session, ctx.doc).OfClass(ctx.session.typeof(DB.Level)).ToElements()for i in range(levelList.getCount()):l = DB.asLevel(levelList.getItem(i))if isNone(l):continuetmp.append(l)ret = sorted(tmp, key=lambda x:x.getElevation())return ret# 遍历WallType,返回List[DB.WallType]
def getWallTypes(ctx : MyContext) -> List[DB.WallType]:wallTypeList : List[DB.WallType] = []listWt = DB.FilteredElementCollector.ctor(ctx.session, ctx.doc).OfClass(ctx.session.typeof(DB.WallType)).ToElements()for i in range(listWt.getCount()):wt = DB.asWallType(listWt.getItem(i))if isNone(wt):continuewallTypeList.append(wt)return wallTypeList# 遍历门FamilySymbol,返回List[DB.FamilySymbol]
def getDoorFamilySymobls(ctx : MyContext) -> List[DB.FamilySymbol]:doorFamilySymobls : List[DB.FamilySymbol] = []listSy = DB.FilteredElementCollector.ctor(ctx.session, ctx.doc).OfClass(ctx.session.typeof(DB.FamilySymbol)).ToElements()for i in range(listSy.getCount()):fs = DB.asFamilySymbol(listSy.getItem(i))if isNone(fs):continuecat = fs.getCategory()if isNone(cat) or cat.getBuiltInCategory() != DB.BuiltInCategory.OST_Doors:continue;doorFamilySymobls.append(fs)return doorFamilySymobls# 示例创建墙并在墙上创建门
def DoorCreation(ctx: MyContext) -> None:"""本示例展示如何使用Python+DRVT,在外部让Revit批量创建墙并在墙上创建门"""if ctx.doc is not None:ctx.closeDoc(True)template = "建筑样板.rte"fileName = "DoorCreation.rvt"err = ctx.createAndActiveDoc(template, fileName)if err != 0:raise AssertionError(f"创建项目文档失败: 错误码 {err}")session = ctx.sessiondoc = ctx.doc# 取所有标高,缺省是两个levelList = getLevels(ctx)if len(levelList) < 2:raise AssertionError(f"标高过少,本示例用到2个标高")level0 = levelList[0].getId()level1 = levelList[1].getId()ele0 = levelList[0].getElevation()try:# 取所有墙类型wallTypeList = getWallTypes(ctx)# 取所有门类型doorFamilySymoblList = getDoorFamilySymobls(ctx)# 涉及到修改操作的,需要锁定并用事务包装ctx.lockAndStartTransaction("批量创建示例")docCreate = doc.getCreate()for i in range(0,10):# 取一个WallTypewallType = wallTypeList[i % len(wallTypeList)]# 设置WallTypectx.doc.SetDefaultElementTypeId(DB.ElementTypeGroup.WallType, wallType.getId())# 这里使用轴线法# 创建墙的轴线x = m2feet(i*3)y1 = m2feet(3)y0 = -y1p0 = DB.XYZ.ctor(session, x, y0, ele0)p1 = DB.XYZ.ctor(session, x, y1, ele0)line = DB.Line.CreateBound(session, p0, p1)# 创建墙wall = DB.Wall.Create(session, doc, line, level0, False)# 取“顶部约束”参数p = wall.getParameter(DB.BuiltInParameter.WALL_HEIGHT_TYPE)# 更新其值为“标高2”的IDp.Set(level1)# 选择门FamyliSymboldoorFamilySymbol = doorFamilySymoblList[i % len(doorFamilySymoblList)]if not doorFamilySymbol.getIsActive():doorFamilySymbol.Activate()# 确定门的位置doorPos = DB.XYZ.ctor(session, x, 0, ele0)# 创建门实例docCreate.NewFamilyInstance(doorPos, doorFamilySymbol, wall, levelList[0], Structure.StructuralType.NonStructural)# 提交事务并解锁,若没有错误则修改操作将会生效ctx.commitTransactionAndUnlock()except Exception as e:print(f"【异常】{e}")# 回滚事务并解锁ctx.rollbackTransactionAndUnlock()# 下面这段代码,看过“创建新项目”示例的会很熟悉,就是照搬过来的
# 创建新的上下文(可以按需创建多个,意味着能直接管理多个 Revit 会话)
ctx = MyContext("在这里指定会话名称")
# 初始化会话(启动 Revit 进程实例)
ctx.initSession()# 调用DoorCreation
DoorCreation(ctx)# 保存文档并关闭
ctx.closeDoc(True)# 结束会话(Revit 进程实例将退出)
ctx.dispose()

又是一个完整的自动化脚本,与前一示例相比,只增加了:

        a、门FamilySymbol的获取

        b、创建墙之后,在其中部创建门实例

这么点代码做了什么:

1、创建Revit会话,启动Revit进程(可见、可交互,与手工启动的无任何差异)

2、批量创建墙并在墙上创建一扇门

3、保存项目文件并关闭

4、结束会话,退出Revit进程

其中“2、批量创建墙并在墙上创建一扇门”做了以下工作:

        1)创建项目 “DoorCreation.rvt” 并作为当前活动文档(可见、可交互)

        2)获取该文档中所有标高(按Elevation排序)

        3)获取该文档中所有WallType元素

        4)获取所有门FamilySymbol

        5)创建轴线

        6)按轴线创建墙

        7)更新墙的参数“顶部约束”

        8)选择一个门FamilySymbol并激活

        9)在6)创建的墙体中间位置创建门实例

运行结果(3D视图):

全自动完成,全程不必手工操作。有了DRVT的加持,Revit插件的核心能力可以在外面用Python脚本轻松驾驭了。自动化生产流水线的雏形渐渐呈现,将Revit深度集成到自己的系统已轻而易举。


  相关文章

Python+DRVT 从外部调用 Revit:从外部启动 Revit-CSDN博客

Python+DRVT 从外部调用 Revit:打开项目文件-CSDN博客

Python+DRVT 从外部调用 Revit:获取项目信息-CSDN博客

Python+DRVT 从外部调用 Revit:更新项目信息-CSDN博客

Python+DRVT 从外部调用 Revit:第一个完整示例-CSDN博客

Python+DRVT 从外部调用 Revit:创建新项目-CSDN博客

Python+DRVT 从外部调用 Revit:创建族文档-CSDN博客

Python+DRVT 从外部调用 Revit:批量创建轴网-CSDN博客

Python+DRVT 从外部调用 Revit:批量创建标高-CSDN博客

Python+DRVT 从外部调用 Revit:创建风管系统加劲肋-CSDN博客

Python+DRVT 从外部调用 Revit:创建剖面-CSDN博客

Python+DRVT 从外部调用 Revit:创建桁架族-CSDN博客

Python+DRVT 从外部调用 Revit:批量创建墙-CSDN博客

深度嵌入数字化工作流:DRVT 的思考与实践-CSDN博客

从插件化走向系统集成——Revit-CSDN博客

Revit变身智能组件,BIM未来可期-CSDN博客

#SystemIntegration #Revit #RevitAPI #Python #Automation #DesignAutomation #BIM #Interop #AEC #DigitalTwin #Workflow

http://www.xdnf.cn/news/19796.html

相关文章:

  • Streamable HTTP
  • sv中forever如何结束
  • AI 在金融、医疗、教育、制造业等领域有着广泛的应用,以下是这些领域的一些落地案例
  • STM32HAL 快速入门(十七):UART 硬件结构 —— 从寄存器到数据收发流程
  • 告别剪辑烦恼!3个超实用技巧,让你的视频瞬间高级起来
  • 【音视频】视频秒播优化实践
  • UnityWebRequest 数据获取和提交
  • wpf 只能输入int类型的文本框
  • WebSocket客户端库:websocket-fruge365
  • Ubuntu下把 SD 卡格式化为 FAT32
  • Hostol Magento电商服务器套餐:基于阿里云,预配置高性能环境,一键开店
  • 如何用java给局域网的电脑发送开机数据包
  • B样条曲线,已知曲线上的某个点到起点的距离,确定这个点的参数u的值的方法
  • 新手向:破解VMware迁移难题
  • MP4视频太大如何压缩?分享6种简单便捷的压缩小技巧
  • websocket用于控制在当前页只允许一个用户进行操作,其他用户等待
  • 硬件(一)51单片机
  • 阿里开源首个图像生成基础模型——Qwen-Image本地部署教程,中文渲染能力刷新SOTA
  • HTTP 协议核心组件与安全扩展深度解析
  • 机器学习与深度学习的 Python 基础之 NumPy(2)
  • uniapp+vue3 微信小程序全屏广告组件功能
  • AI IDE+AI 辅助编程,真能让程序员 “告别 996” 吗?
  • 【LeetCode_283】移动零
  • 技术小白如何快速的了解opentenbase?--把握四大特色
  • XE 旧版本 JSON 处理
  • 使用 Uni-app 打包 外链地址APK 及 iOS 注意事项
  • K8S-基础架构
  • 离开职场2个月,后知后觉的反思。
  • 素材合集!直播间带货音乐BGM合集,抖音直播间常用热门音乐合集,根据中文分类,方便查找
  • 力扣hot100:矩阵置零(73)(原地算法)