EaBIM一直以来积极响应国家“十二五”推进建筑业信息化的号召,对建筑领域的信息技术开展深入技术交流和探讨!致力于打造“BIM-建筑师-生态技术”三位一体综合资源交流共享平台,希望为BIM与可持续设计理念及技术的普及做出微小的贡献!!!

萧闫子 发表于 2014-1-9 12:23:02

Parameter of Revit API – 16: FamilyParameter SetValue Extension Methods

We introduced some help methods in the previous article to address various FamilyParameter value setting scenarios. In this post, let’s see how to do so with some extension methods to the family parameter class, FamilyParameter.
The following extension method will set a value regardless of data type to the calling FamilyParameter regarding the specified FamilyType in the specified FamilyManager:      public static void SetValue(this FamilyParameter fp, FamilyManager fm, FamilyType ft, object value)
      {
            FamilyType curFamType = fm.CurrentType;
            fm.CurrentType = ft;            try
            {
                switch (fp.StorageType)
                {
                  case StorageType.None:
                        break;
                  case StorageType.Double:
                        if (value.GetType().Equals(typeof(string)))
                        {
                            fm.Set(fp, double.Parse(value as string));
                        }
                        else
                        {
                            fm.Set(fp, Convert.ToDouble(value));
                        }
                        break;
                  case StorageType.Integer:
                        if (value.GetType().Equals(typeof(string)))
                        {
                            fm.Set(fp, int.Parse(value as string));
                        }
                        else
                        {
                            fm.Set(fp, Convert.ToInt32(value));
                        }
                        break;
                  case StorageType.ElementId:
                        if (value.GetType().Equals(typeof(ElementId)))
                        {
                            fm.Set(fp, value as ElementId);
                        }
                        else if (value.GetType().Equals(typeof(string)))
                        {
                            fm.Set(fp, new ElementId(int.Parse(value as string)));
                        }
                        else
                        {
                            fm.Set(fp, new ElementId(Convert.ToInt32(value)));
                        }
                        break;
                  case StorageType.String:
                        fm.Set(fp, value.ToString());
                        break;
                }
            }
            catch
            {
                throw new Exception("Invalid Value Input!");
            }
            finally
            {
                fm.CurrentType = curFamType;
            }
      }It pretty much does the same thing as the comprehensive help method introduced previously. However, some questions may come in mind of some readers:
1. Why must we provide the FamilyManager as an argument to these methods?
2. Can a particular FamilyParameter instance belong to different FamilyManager objects?
3. Can a specific FamilyType reside in multiple FamilyManager objects?The answer to the first question is that we have to since the associated FamilyManager cannot be found anywhere either from the FamilyParameter or the FamilyType.The answer to the last two is apparently the same, NO, but on the other hand the same FamilyParameter instance can be associated with some different FamilyType instances.Anyway, it does not seem a big deal to always have the FamilyManager as an argument in these methods.The following extension method will set a value regardless of data type to the calling FamilyParameter in case the name of the FamilyType of interest is known:      public static void SetValue(this FamilyParameter fp, FamilyManager fm, string familyTypeName, object value)
      {
            FamilyType FT = (from FamilyType ft in fm.Types select ft).ToList()
                .FirstOrDefault(e=>e.Name.Equals(familyTypeName, StringComparison.CurrentCultureIgnoreCase));            if( FT == null )
            {
                throw new Exception("Invalid Value Input!");
            }            fp.SetValue(fm, FT, value);
      }Let’s do a bit more this time. How to set a value to a FamilyParameter of all FamilyType instances of the family document of interest represented by the FamilyManager?It is very simple supposing the comprehensive one has already been there in the same place. Here it is:      public static void SetValue(this FamilyParameter fp, FamilyManager fm, object value)
      {
            foreach (FamilyType ft in fm.Types)
            {
                fp.SetValue(fm, ft, value);
            }
      }By the way, please do not forget to put these extension methods into a public static class and import its namespace into the source that you are working on.
The following test code can be used to exercise these extension methods:…
if (CachedDoc.IsFamilyDocument)
{
    FamilyManager fm = CachedDoc.FamilyManager;
    FamilyType ft = RawConvertSetToList<FamilyType>(fm.Types);    FamilyParameter urlFP = RawFindFamilyParameter(fm, "URL");
    FamilyParameter legHeightFP = RawFindFamilyParameter(fm, "Leg Height");
    FamilyParameter depthFP = RawFindFamilyParameter(fm, "Depth");
    FamilyParameter the1stStringFP = RawConvertSetToList<FamilyParameter>(fm.Parameters)
      .First(e => e.StorageType == StorageType.String);    urlFP.SetValue(fm, "http://spiderinnet.typepad.com");    legHeightFP.SetValue(fm, ft, 1.11);
    depthFP.SetValue(fm, ft, 2.22);
    the1stStringFP.SetValue(fm, ft, "The first family parameter having the String StorageType.");
}
…FamilyParameter Writer of RevitAddinWizardcan help do all of these in a configurable and flexible way.

chen_0003 发表于 2014-2-20 15:01:45

顶......
楼下跟上.....

页: [1]
查看完整版本: Parameter of Revit API – 16: FamilyParameter SetValue Extension Methods