如有不明白,请qq254033230询问。
revit读取材料的外观信息不能通过lookup来搞定,所以读取起来稍微有点麻烦。但是在revit二次开发的官方基础教程里有相关的解释。
这里就以一个墙体为例,读取墙体材料的所有外观信息(如下图)。这里主要针对autodesk的官方材料库来说的。对于非官方材料库的,下面的代码里被注释掉的可以参考一下。其实读取材料的原理比较简单,过程如下:
1)获取材料的ID,ICollection
2)// 读取revit标准材质库
AssetSet objlibraryAsset = revitApp.get_Assets(AssetType.Appearance);
3)从CompoundStructureLayer中获得材料
4)分两种情况读取材料。
对于 APT_Asset和APT_Reference这两种类型还需要再次递归。具体代码如下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Autodesk.Revit.UI;
using Autodesk.Revit.DB;
using Autodesk.Revit.UI.Selection;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Utility;
using System.IO;
namespace 读取墙体材料
{
[Autodesk.Revit.Attributes.Transaction(Autodesk.Revit.Attributes.TransactionMode.Manual)]
[Autodesk.Revit.Attributes.Journaling(Autodesk.Revit.Attributes.JournalingMode.NoCommandData)]
[Autodesk.Revit.Attributes.Regeneration(Autodesk.Revit.Attributes.RegenerationOption.Manual)]
public class MyClass : IExternalCommand
{
public Result Execute(ExternalCommandData commandData, ref string message, ElementSet elements)
{
Document revitDoc = commandData.Application.ActiveUIDocument.Document; //取得文档
Application revitApp = commandData.Application.Application; //取得应用程序
UIDocument uiDoc = commandData.Application.ActiveUIDocument;
Selection sel = uiDoc.Selection;
Reference ref1 = sel.PickObject(ObjectType.Element, "选择一个族实例");
Element elem = revitDoc.GetElement(ref1);
// 读取revit标准材质库
AssetSet objlibraryAsset = revitApp.get_Assets(AssetType.Appearance);
Wall wall = elem as Wall;
ICollection matId = elem.GetMaterialIds(true);
#region 从elementId中获得材料,这种方法获得的是主材
//foreach (var item in matId)
//{
// TaskDialog.Show("REVIT", item.ToString());
// Material mat2 = revitDoc.GetElement(item) as Material; //从elementId中获得材料
//}
#endregion
#region 从CompoundStructureLayer中获得材料,这种方法可以获得与该元素相关的全部材料
WallType wallType = wall.WallType;
CompoundStructure compoundStructure = wallType.GetCompoundStructure();
IList layers = compoundStructure.GetLayers();
ReadAssetProperty readAssetProperty = new ReadAssetProperty();
foreach (var item in layers)
{
Material mat2 = revitDoc.GetElement(item.MaterialId) as Material;
// TaskDialog.Show("REVIT", mat2.Name.ToString()+ mat2.Id);
ElementId assetElementId = mat2.AppearanceAssetId;
if(assetElementId!=ElementId.InvalidElementId)
{
//获取外观元素
AppearanceAssetElement appearanceAssetElement = revitDoc.GetElement(assetElementId) as AppearanceAssetElement;
//读写外观元素
Asset currentAsset = appearanceAssetElement.GetRenderingAsset();
// TaskDialog.Show("revit", currentAsset.AssetType.ToString() + ";" + currentAsset.LibraryName.ToString()
// + ";" + currentAsset.Title.ToString()+";" + currentAsset.Size.ToString());
////外观子元素
//IList listProperty=new List() ;
//for(int i=0;i listProperty = new List();
if (currentAsset.Size == 0)
{
foreach (Asset objCurrentAsset in objlibraryAsset)
{
if (objCurrentAsset.Name == currentAsset.Name &&
objCurrentAsset.LibraryName == currentAsset.LibraryName)
{
for (int i = 0; i < objCurrentAsset.Size; i++)
{
listProperty.Add(objCurrentAsset[i]);
}
foreach (var item2 in listProperty)
{
ReadAutodeskAssetProperty(item2, readAssetProperty, objlibraryAsset,matId);
}
}
}
}
else
{
for (int i = 0; i < currentAsset.Size; i++)
{
listProperty.Add(currentAsset[i]);
}
foreach (var item2 in listProperty)
{
ReadAutodeskAssetProperty(item2, readAssetProperty, objlibraryAsset, matId);
}
}
}
public void ReadAutodeskAssetProperty(AssetProperty assetProperty, ReadAssetProperty readAssetProperty, AssetSet objlibraryAsset, string matId)
{
switch (assetProperty.Type)
{
case AssetPropertyType.APT_Integer:
var assetPropertyInt = assetProperty as AssetPropertyInteger;
if(readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyInt.Value.ToString());
}
break;
case AssetPropertyType.APT_Distance:
var assetPropertyDistance = assetProperty as AssetPropertyDistance;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyDistance.Value.ToString());
}
break;
case AssetPropertyType.APT_Double:
var assetPropertyDouble = assetProperty as AssetPropertyDouble;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyDouble.Value.ToString());
}
break;
case AssetPropertyType.APT_DoubleArray2d:
var assetPropertyDoubleArray2d = assetProperty as AssetPropertyDoubleArray2d;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyDoubleArray2d.Value.ToString());
}
break;
case AssetPropertyType.APT_DoubleArray4d:
var assetPropertyDoubleArray4d = assetProperty as AssetPropertyDoubleArray4d;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
string value4d = assetPropertyDoubleArray4d.Value.get_Item(0).ToString() + "," + assetPropertyDoubleArray4d.Value.get_Item(1).ToString() + "," +
assetPropertyDoubleArray4d.Value.get_Item(2).ToString() + "," + assetPropertyDoubleArray4d.Value.get_Item(3).ToString();
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), value4d);
}
break;
case AssetPropertyType.APT_String:
var assetPropertyString = assetProperty as AssetPropertyString;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyString.Value);
}
break;
case AssetPropertyType.APT_Boolean:
var assetPropertyBoolean = assetProperty as AssetPropertyBoolean;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyBoolean.Value.ToString());
}
break;
case AssetPropertyType.APT_Double44:
var assetPropertyDouble44 = assetProperty as AssetPropertyDoubleArray4d;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), assetPropertyDouble44.Value.ToString());
}
break;
case AssetPropertyType.APT_List:
AssetPropertyList propList = assetProperty as AssetPropertyList;
IList subProps = propList.GetValue();
if (subProps.Count == 0)
break;
switch (subProps[0].Type)
{
case AssetPropertyType.APT_Integer:
foreach (AssetProperty subProp in subProps)
{
AssetPropertyInteger intProp = subProp as AssetPropertyInteger;
if (readAssetProperty.CheckMaterialMxExists(matId, assetProperty.Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, assetProperty.Name, assetProperty.Type.ToString(), intProp.Value.ToString());
}
}
break;
}
break;
case AssetPropertyType.APT_Asset:
var assetPropertyAsset = assetProperty as Asset;
ReadAsset(assetPropertyAsset, objlibraryAsset, readAssetProperty,matId);
break;
case AssetPropertyType.APT_Reference:
var assetPropertyReference = assetProperty as AssetPropertyReference;
IList listProperty2 = assetPropertyReference.GetAllConnectedProperties();
foreach (var item3 in listProperty2)
{
var AssetProperty3 = item3 as Asset;
for (int i = 0; i < AssetProperty3.Size; i++)
{
switch (AssetProperty3[i].Type)
{
case AssetPropertyType.APT_Integer:
var assetPropertyInt2 = AssetProperty3[i] as AssetPropertyInteger;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyInt2.Value.ToString());
}
break;
case AssetPropertyType.APT_Distance:
var assetPropertyDistance2 = AssetProperty3[i] as AssetPropertyDistance;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyDistance2.Value.ToString());
}
break;
case AssetPropertyType.APT_Double:
var assetPropertyDouble2 = AssetProperty3[i] as AssetPropertyDouble;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyDouble2.Value.ToString());
}
break;
case AssetPropertyType.APT_DoubleArray2d:
var assetPropertyDoubleArray2d2 = AssetProperty3[i] as AssetPropertyDoubleArray2d;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyDoubleArray2d2.Value.ToString());
}
break;
case AssetPropertyType.APT_DoubleArray4d:
var assetPropertyDoubleArray4d2 = AssetProperty3[i] as AssetPropertyDoubleArray4d;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyDoubleArray4d2.Value.ToString());
}
break;
case AssetPropertyType.APT_String:
var assetPropertyString2 = AssetProperty3[i] as AssetPropertyString;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyString2.Value.ToString());
}
break;
case AssetPropertyType.APT_Boolean:
var assetPropertyBoolean2 = AssetProperty3[i] as AssetPropertyBoolean;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyBoolean2.Value.ToString());
}
break;
case AssetPropertyType.APT_Double44:
var assetPropertyDouble442 = AssetProperty3[i] as AssetPropertyDoubleArray4d;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), assetPropertyDouble442.Value.ToString());
}
break;
case AssetPropertyType.APT_List:
AssetPropertyList propList2 = AssetProperty3[i] as AssetPropertyList;
IList subProps2 = propList2.GetValue();
if (subProps2.Count == 0)
break;
switch (subProps2[0].Type)
{
case AssetPropertyType.APT_Integer:
foreach (AssetProperty subProp in subProps2)
{
AssetPropertyInteger intProp2 = subProp as AssetPropertyInteger;
if (readAssetProperty.CheckMaterialMxExists(matId, AssetProperty3[i].Name))
{
readAssetProperty.ReadAssetPropertyFromRevit(matId, AssetProperty3[i].Name, AssetProperty3[i].Type.ToString(), intProp2.Value.ToString());
}
}
break;
}
break;
}
}
}
break;
default:
//info += assetProperty.Name + ";" + assetProperty.Type.ToString() + "\n";
break;
}
}
}
}
这其中还有一个往数据库中读取材料性质的类,这个类有两个作用:
1)把材料放到数据库里
2)检查数据库里是否已经存在该材料的信息
其中下面这句代码是数据库的链接地址,依据个人的电脑不同而改变。
private string str = "Data Source=USER-20161016YA\\MEDICINE;Initial Catalog=MyMaterials;Integrated Security=True";
using System;
using System.Collections.Generic;
using System.Data.SqlClient;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace 读取墙体材料
{
public class ReadAssetProperty
{
private string str = "Data Source=USER-20161016YA\\MEDICINE;Initial Catalog=MyMaterials;Integrated Security=True";
public void ReadAssetPropertyFromRevit(string materialId ,string paramName, string type,string value)
{
int n = -1;
//连接数据库
using (SqlConnection con = new SqlConnection(str))
{
//string sql = string.Format("insert into MaterialFormRevit(MaterialId,ParamName, MatType, Value) values('{0}','{1}','{2}',{3})", 1,paramName, type, value);
string sql = string.Format("insert into MaterialFormRevit(MaterialId,ParamName, MatType, Value) values('{0}','{1}','{2}','{3}')", materialId, paramName, type, value);
using (SqlCommand cmd = new SqlCommand(sql, con))
{
con.Open();
n = cmd.ExecuteNonQuery();
}
}
//string msg = n > 0 ? "操作成功" : "操作失败";
//LoadData();//刷新数据
}
public bool CheckMaterialMxExists(string strMaterialId, string paramName)
{
bool flag = false;
SqlConnection mycon = new SqlConnection(str);
//查询此编号是否存在
mycon.Open();
SqlCommand mycmd = new SqlCommand("select MaterialId from MaterialFormRevit where MaterialId='" + strMaterialId + "'AND ParamName='" + paramName + "'", mycon);
SqlDataReader mysdr = mycmd.ExecuteReader();
if (mysdr.HasRows)
{
flag = false;
}
else
{
flag = true;
}
mysdr.Close();
mycon.Close();
return flag;
}
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace 读取墙体材料
{
public class Depart
{
private int _MaterialId;
private string _ParamName;
private string _Type;
private string _Value;
public int MaterialId
{
get
{
return _MaterialId;
}
set
{
_MaterialId = value;
}
}
public string ParamName
{
get
{
return _ParamName;
}
set
{
_ParamName = value;
}
}
public string Type
{
get
{
return _Type;
}
set
{
_Type = value;
}
}
public string Value
{
get
{
return _Value;
}
set
{
_Value = value;
}
}
}
}
最后Form的代码如下:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Data.SqlClient;
namespace 读取墙体材料
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
string str = "Data Source=USER-20161016YA\\MEDICINE;Initial Catalog=MyMaterials;Integrated Security=True";
private void Form1_Load(object sender, EventArgs e)
{
LoadData();
}
private void LoadData()
{
List list = new List();
//通过连接字符串连接数据库
using (SqlConnection con = new SqlConnection(str))
{
//拼接sql语句
string sql = "select * from MaterialFormRevit";
//准备执行sql语句的对象
using (SqlCommand cmd = new SqlCommand(sql, con))
{
con.Open();//打开数据库
//准备读数据
using (SqlDataReader reader = cmd.ExecuteReader())
{
//判断是否有数据(有没有行)
if (reader.HasRows)
{
//读取每一行
while (reader.Read())
{
Depart dk = new Depart();//创建部门对象
// dk.MaterialId= Convert.ToInt32(reader["MaterialId"]);
dk.MaterialId =Convert.ToInt32(reader["MaterialId"].ToString()) ;
dk.ParamName = reader["ParamName"].ToString();
dk.Type = reader["MatType"].ToString();
dk.Value = reader["Value"].ToString();
list.Add(dk);//添加到集合中
}//end while
}//end if
}// end sqldatareader
}//end using
}//end using
dgv.AutoGenerateColumns = false;//禁止自动生成列
dgv.DataSource = list;//绑定数据
//dgv.SelectedRows[0].Selected = false;//禁止被选中
}
}
}
最后结果如图: