ADN Open CIS
Сообщество программистов Autodesk в СНГ

18/12/2015

Работа с параметрами

На форуме возникла небольшая дискуссия, на, казалось бы, простые вопросы по работе с параметрами. Решил немного внести ясность и разобрать по подробней как работать с параметрами элементов.

Доступ к параметрам. Поиск параметра.

Чтобы получить доступ ко всем параметрам элемента, необходимо воспользоваться свойством Element.Parameters. Так как практически все объекты Revit наследуются от базового класса Element, то данный подход можно применять для любого объекта модели – экземпляр, тип, семейство, инженерная система, материал и т.п. Свойство возвращает коллекцию параметров ParameterSet, который реализует интерфейс IEnumerable. Следовательно, можно работать с параметрами с помощью foreach или LINQ.

Код - C#: [Выделить]
  1. foreach (Parameter parameter in element.Parameters)
  2. {
  3.                 Debug.Print("{0}", parameter.Definition.Name)
  4. }

Если нам нужно получить конкретный параметр, то существует несколько способов.

  1. С помощью индексированного свойства Element.Parameter[]. Так как конструкция языка C# не поддерживает индексированные свойства, то в C# генерируется метод Element.get_Parameter(). В VB.NET, на сколько мне известно, индексируемые свойства поддерживаются. Насчет Python – не уверен.
    Существует 4 перегруженных метода Element.get_Parameter()
  • Element.get_Parameter(BuiltInParamter) – Поиск встроенного параметра. Для поиска встроенного в Revit параметра, рекомендуется пользоваться только этим методом, так как он не зависит от языка, и позволяет избежать проблемы параметров с одинаковым наименованием.
  • Element.get_Parameter(Guid) – Поиск общего параметра по его идентификатору
  • Element.get_Parameter(Definition) – Поиск параметра, по его описанию. Не могу придумать пример, когда это может быть нужно.
  • Element.get_Parameter(String) – Поиск параметра, по его названию. Метод устарел в Revit 2016, и будет удален в Revit 2017.

Метод возвращает объект типа Parameter, если параметр найден и null, если не найден. В случае, если осуществляется поиск по наименованию, и существует больше чем один параметр с таким названием, будет возвращен первый из них. Причем заранее не известно какой именно и в будущем, в теории, этот порядок может измениться. Вполне может получиться так, что через какое-то время, Revit вернет не тот параметр, который вы ожидали. В итоге ваша надстройка будет работать неверно. Поэтому методом поиска по названию пользоваться не рекомендуется.

  1. Метод Element.LookupParameter(String). Метод целиком и полностью работает также, как и Element.get_Parameter(String) со всеми его недостатками.
  2. Element.GetParameters(String). Метод ищет параметры по названию. Но, возвращает коллекцию параметров, а не один параметр.
  3. C помощью LINQ. Например, получить все параметры, тип которых равен Integer:
    Код - C#: [Выделить]
    1. var parameters =
    2.  
    3.                 element
    4.                 .Parameters
    5.                 .OfType<Parameter>()
    6.                 .Where(p=>parameter.StorageType == StorageType.Integer)
    7.                 .ToList()

     

    Значение параметра

    Каждый параметр имеет свой тип для хранения данных. Получить тип данных можно с помощью свойства Parameter.StorageType и может приникать одно из 5 значений:

    • None – не используется
    • Integer – хранение целочисленных значений. Используется также для параметра типа Да/Нет.
    • Double – для хранения дробного числа.
    • String – хранение строкового значения.
    • ElementId – когда значение параметра ссылается на другой элемент.

    В зависимости от типа хранения данных, для чтения значения параметра нужно применять соответствующий метод.

    • Parameter.AsInteger()
    • Parameter.AsDouble()
    • Parameter.AsString()
    • Parameter.AsElementId()

    Однако, есть еще один способ – Element.AsValueString(). Метод возвращает значение параметра в том виде, в каком его видит пользователь, включая единицу измерения. Для параметров, у которых StorageType=String, метод возвращает пустую строку. Поэтому для таких параметров всегда нужно использовать Parameter.AsString()

    Рассмотрим по подробней.

    Тип Integer. Помимо целочисленных данных, используется так же для параметров типа Да/Нет. В случае значения Да, метод AsInteger() вернет 1, а метод AsValueString()Да. Причем, слово Да, будет локализовано.

     

    Тип Double. В подавляющем большинстве, данный тип используется для параметров, имеющих единицу измерения. Внутренне Revit значения всех параметров хранит в базовой единице измерения, основанную на Британской системе единиц измерения. Например, длина всегда хранится в футах. Пользователь же видит длину в тех единицах измерения, которые заданы в настройках проекта. Если значение параметра равно 1 метр, то AsDouble() будет равно 3.280839895013123 (1 фут равен 0,3048 метра). AsValueString() включает в себя значение параметра в единицах измерения проекта плюс локализованную единицу измерения в опять же в том виде, котором она задана в настройках, например, 1 м

    Тип ElementId. Значение хранится в виде идентификатора – Ссылки на другой объект. Например, свойство Уровень. AsElementId вернет что-то типа 123456, а AsValueString()Уровень 1

    Чтобы установить значение параметра, необходимо воспользоваться перегруженным методом Parameter.Set(). Аргумент зависит от того, какого типа параметр. В зависимости от этого нужно передать String, Double, Integer или ElementId. Если параметр успешно записан, то вернется значение true. Иначе – false.

    Также есть метод Parameter.SetValueString(String). Метод в качестве аргумента принимает значение параметра в том виде, в котором его видит пользователь. Т.е. можно для записи длины передать 2 м и Revit сам попытается его распарсить и преобразовать во внутреннее значение. Данный метод нельзя применить для параметра типа ElementId

    Автор: Виктор Чекалин

    Обсуждение: http://adn-cis.org/forum/index.php?topic=3287

    Опубликовано 18.12.2015
    Отредактировано 18.12.2015 в 10:28:11