12. Revit 载入族(LoadFamily)
前言
最近测试一个功能时,遇到了个问题,使用代码创建了个族,然后发现族无法载入到项目中,依稀记得这个问题以前是处理过的,那么再确认一下,顺便写一写吧。
LoadFamily 使用
LoadFamily方法位于Document上,有5个重载,但其实就两类。
- 用于项目文档
// projectDoc.LoadFamily(族文件路径, ...)Public method LoadFamily(String, IFamilyLoadOptions, out Family);
Public method LoadFamily(String, out Family);
Public method LoadFamily(String);
- 用于族文档
// familyDoc.LoadFamily(projectDoc, ...)Public method LoadFamily(Document, IFamilyLoadOptions);
Public method LoadFamily(Document);
IFamilyLoadOptions
IFamilyLoadOptions 表示的是族载入到项目中,当项目中已存在 同名族 或 同名共享族 时的处理策略。比如我们编辑项目中的族,又重新加载项目中时,就会弹出是否覆盖的提示框,IFamilyLoadOptions 就是做这事儿的。
这个接口需要实现两个方法:OnFamilyFound(..)和OnSharedFamilyFound(..),很好理解,就不多写了。

问题与处理
经过测试,当使用族文档的 LoadFamily 方法时,如果项目中存在默认族名的族,则「可能」出现族加载失败的情况,且此时错误信息只有“族加载失败”。

触发条件与原因
创建好的族,加载到项目中时,族名称就是默认格式的,即“族+数字”,对应正则^族\d+$。一般来讲,这个数字是自增的,就是创建了一个族,默认族1,及时删除后再创建一个,后续也会是族2。
问题就在这儿,这个数字似乎不是存在项目文件中的,从别处拿来一个新文档,里面有默认族了,但你通过代码创建时,那可能就冲突了,而且这种冲突,没法通过设置 IFamilyLoadOptions 来处理。

处理方法
既然知道原因了,怎么处理就很明确了:避免载入时重名。那么进一步的有两种方案。
第一个方案,这个看着比较“抽象”,但确实好用
- 先修改默认族名(
^族\d+$)。如 族1 -> xxx-族1 - 再加载新建族,给新建族重命名。新建族载入-> 族xx -> 自定义名
- 最后再将原来族名称改回去。 xxx-族1 -> 族1
第二个方案,就是给新建的族一个名字,这个方案有坑,且涉及文件读写,比较慢。
- 使用
SaveAs方法,将族保存起来,此时可以命名。 - 接着,采用
familyDoc.LoadFamily(projectDoc)或是projectDoc.LoadFamily(path)都可以,几乎一样的速度。建议用前面一个,因为后面的需要单开一个事务,多写几行代码。 - 关闭文件,
familyDoc.Close(),这一步非常重要!!
如果不关闭文档,这个文件就会一直被占用着,而且在 Revit 中是找不到对应族文档界面的。手动操作时,也只能找到文件的保存路径,打开它,再重新关闭一次才能释放。当然直接关闭整个 Revit 也是可以的。

结尾
不保存族文档直接加载非常快,涉及到保存就会慢很多,能明显看到 Revit 底部的读条。
第一种方案中,改族名也是个很快的操作,但要是每创建一个族都来回改一次就有点抽象了,最好抽离为单独的方法。
使用上,如果不需要将族保存为单独文件,那就用第一种。
