Понадобилось нам выводить данные в виде дерева.
Причем, надо выводить не одно поле, а несколько. Поэтому стандартный TreeView подходит плохо.
В программе использовался WPF и компоненты DevExpress. Там есть навороченный GridControl, предоставляющий в числе прочего просмотр данных в виде дерева. То есть на первый взгляд проблема на полчаса.
В соответствии с инструкциями, настраиваем в GridControl'овском TreeListView свойства для вывода иерархии:
TreeListView tView = DataGrid.View as TreeListView;
tView.AutoPopulateServiceColumns = true;
tView.KeyFieldName = "Id";
tView.ParentFieldName = "Parent";
И получаем нечто непонятное:
Чуть поразмыслив, понимаю, что грид ждет именно имя поля в БД. А у меня не записи в БД, а объекты, получаемые через ORM (DataObjects.Net). И свойство Parent — указывающее на объект. А не на ключевое значение. В таблице БД оно отображается полем Parent.Id, но в свойствах объекта такого нет. Есть только Parent. И у него — Id. Пробую указать
tView.ParentFieldName = "Parent.Id";
Не помогает. (В исходниках DevExpress становится понятным, что и не поможет — нужно именно одно свойство, точнее — имя колонки в таблице.)
Хорошо, добавим в грид колонку, и выведем в нее это значение. Не помогает. При выполнении получаем сообщение — нельзя в качестве служебной колонки использовать вычисляемую хрень.
Стало быть, надо честно вводить такое свойство. Ну, ОК, это несложно, добавляем в класс вычисляемое свойство:
[HierarchyRoot]
public class NormPart : Entity
{
[Field, Key]
public int Id { get; set; }
[Field(Length = NameLength, Indexed = true)]
public string Name { get; set; }
[Field(Length = CodeLength, Indexed = true)]
public string Code { get; set; }
/// <summary> Родительский элемент
/// </summary>
[Field]
public NormPart Parent { get; set; }
/// <summary> Вывод Parent.Id в виде поля - для построения иерархического списка
/// </summary>
public int ParentId
{get
{
if (Parent == null) return 0;
return Parent.Id;
}
}
}
Теперь срабатывает прекрасно:
Автор: push