Здравствуйте. Мне нужно создать древовидный реестр (как структура в проектах). Пробовал сделать по примеру структуры в проектах, но не получилось. Объект я наследовал от базового иерархического справочника, далее я добавил поле типа справочник Parent, которое ссылается на этот же объект. В свойстве "Родитель в иерархии" объекта указал поле Parent. Создал новый справочник, в нем иерархия работает. Далее создал страницу реестра и сделал ее по примеру страницы детали Структуры. В итоге у меня данная деталь отображается, в ней есть данные (не пишет "Нет данных", а отображаются названия колонок), но эти данные не отображаются.
Опишите, пожалуйста, поэтапно процесс созданий детали такого типа. Может я что-то упускаю.
Нравится
Добрый день!
В данный момент формируем для Вас инструкцию. Предоставим в ближайшее время.
Здравствуйте!
Минимально необходимый код для иерархической детали (основано на детали «Структура проекта» из XRM):
define("HierarchyDeatilV2", [], function () { return { entitySchemaName: "Project", attributes: { /** * Отвечает за загруженные уровни иерархии */ "expandedElements": { dataValueType: Terrasoft.DataValueType.CUSTOM_OBJECT, type: Terrasoft.ViewModelColumnType.VIRTUAL_COLUMN }, /** * Отвечает за список развернутых элементов, * хранит массив уникальных идентификаторов записей */ "expandHierarchyLevels": { dataValueType: Terrasoft.DataValueType.CUSTOM_OBJECT, type: Terrasoft.ViewModelColumnType.VIRTUAL_COLUMN }, /** * Отвечает за хранение разворачиваемого элемента иерархии */ "ExpandItemId": { dataValueType: Terrasoft.DataValueType.GUID, type: Terrasoft.ViewModelColumnType.VIRTUAL_COLUMN } }, methods: { /** * @overridden */ disableGridSorting: Ext.emptyFn, /** * @overridden */ sortColumn: Ext.emptyFn, /** * Инициализирует параметры детали * @protected * @overridden */ initData: function () { this.callParent(arguments); this.set("expandedElements", {}); this.set("expandHierarchyLevels", []); }, /** * Очищает информацию о загруженных и развернутых уровнях * @protected * @virtual */ clearExpandHierarchyLevels: function () { this.set("expandedElements", {}); this.set("expandHierarchyLevels", []); }, /** * Убирает информацию о том, что элемент развернут из системных параметров * @protected * @virtual * @param {String} itemId Уникальный идентификатор записи */ removeExpandHierarchyLevel: function (itemId) { var expandHierarchyLevels = this.get("expandHierarchyLevels"); this.set("expandHierarchyLevels", Terrasoft.without(expandHierarchyLevels, itemId)); }, /** * Добавляет в экземпляр запроса колонки: * Родительский проект, Позиция, вычисляемую колонку количества дочерних элементов * @protected * @overridden * @param {Terrasoft.EntitySchemaQuery} esq Запрос, в который будут добавлены колонки по умолчанию */ addGridDataColumns: function (esq) { this.callParent(arguments); this.putParentColumn(esq); this.putNestingColumn(esq); }, /** * Добавляет колонку родительского проекта, если идет иерархический запрос * @protected * @virtual * @param {Terrasoft.EntitySchemaQuery} esq Запрос, * в который будет добавлена колонка родительского проекта */ putParentColumn: function (esq) { var parentItem = this.get("ExpandItemId"); if (parentItem && !esq.columns.contains("ParentId")) { esq.addColumn("ParentProject.Id", "ParentId"); } }, /** * Добавляет агрегирующую колонку количества дочерних элементов для записи * @protected * @virtual * @param {Terrasoft.EntitySchemaQuery} esq Запрос, * в который будет добавлена агрегирующая колонка */ putNestingColumn: function (esq) { var aggregationColumn = this.Ext.create("Terrasoft.AggregationQueryColumn", { aggregationType: Terrasoft.AggregationType.COUNT, columnPath: "[Project:ParentProject].Id" }); if (!esq.columns.contains("HasNesting")) { esq.addColumn(aggregationColumn, "HasNesting"); } }, /** * Возвращает объект со списком загруженных уровней * @protected * @virtual * @return {Object} Возвращает объект со списком загруженных уровней */ getExpandedItems: function () { return this.get("expandedElements"); }, /** * Вносит информацию о новом загруженном уровне * @protected * @virtual * @param primaryColumnValue Уникальный идентификатор записи */ setExpandedItem: function (primaryColumnValue) { (this.getExpandedItems()[primaryColumnValue]) = { "page": 0 }; }, /** * Проверяет, были ли загружены дочерние элементы выбранной записи * @protected * @virtual * @param primaryColumnValue Уникальный идентификатор записи * @return {boolean} */ isItemExpanded: function (primaryColumnValue) { return !!(this.getExpandedItems()[primaryColumnValue]); }, /** * Обрабатывает загрузку данных в коллекцию, добавляя загрузку новых уровней в иерархию списка * @protected * @overridden * @param {Terrasoft.Collection} dataCollection коллекция новых элементов * @param {Object} options Объект конфигурации загрузки данных */ addItemsToGridData: function (dataCollection, options) { if (dataCollection.isEmpty()) { return; } var firstItem = dataCollection.getByIndex(0); var parentId = firstItem.get("ParentId"); if (parentId) { options = { mode: "child", target: parentId }; var gridData = this.getGridData(); var parentObj = gridData.get(parentId); if (parentObj) { parentObj.set("HasNesting", 1); } if (!this.isItemExpanded(parentId)) { return; } } else { this.set("LastRecord", dataCollection.getByIndex(dataCollection.getCount() - 1)); } this.callParent([dataCollection, options]); if (options && (options.mode === "child" || options.mode === "top")) { var gridDataChild = this.getGridData(); var tempCollection = this.Ext.create("Terrasoft.Collection"); tempCollection.loadAll(gridDataChild); gridDataChild.clear(); gridDataChild.loadAll(tempCollection); } this.set("ExpandItemId", null); }, /** * Обработчик загрузки дочерних элементов. Осуществляет проверку загружености * дочерних элементов выбранной записи. Запускает загрузку нового уровня. * @protected * @virtual * @param {String} primaryColumnValue Уникальный идентификатор записи * @param {Boolean} isExpanded Признак того, разворачивает или сворачивает пользователь дочерние элементы * true - если разворачивает, false в обратном случае */ onExpandHierarchyLevels: function (primaryColumnValue, isExpanded) { if (!isExpanded || this.isItemExpanded(primaryColumnValue)) { return; } this.setExpandedItem(primaryColumnValue); this.set("ExpandItemId", primaryColumnValue); this.loadGridData(); }, /** * Удаляет логику постраничности если загружаются дочерние объекты * @protected * @overridden */ initQueryOptions: function () { var parentItem = this.get("ExpandItemId"); if (!parentItem) { var isClearGridData = this.get("IsClearGridData"); if (isClearGridData) { this.clearExpandHierarchyLevels(); } this.callParent(arguments); } }, /** * Удаляет логику постраничности если загружаются дочерние объекты * @protected * @overridden */ initCanLoadMoreData: function () { var parentItem = this.get("ExpandItemId"); if (!parentItem) { this.callParent(arguments); } }, /** * Обновляет фильтры в зависимости от того, загружается ли записи в корень или в новый уровень * @protected * @overridden * @return {Terrasoft.FilterGroup} Примененные в данной схеме фильтры */ getFilters: function () { var parentItem = this.get("ExpandItemId"); if (parentItem) { var parentProjectFilterGroup = this.Terrasoft.createFilterGroup(); parentProjectFilterGroup.addItem(this.Terrasoft.createColumnFilterWithParameter( this.Terrasoft.ComparisonType.EQUAL, "ParentProject", parentItem, Terrasoft.DataValueType.GUID )); return parentProjectFilterGroup; } else { var filters = this.callParent(arguments); if (this.get("DetailColumnName") !== "ParentProject") { var group = this.Terrasoft.createFilterGroup(); group.addItem(filters); group.addItem( Terrasoft.createColumnIsNullFilter(this.entitySchema.hierarchicalColumnName) ); filters = group; } return filters; } } }, diff: /**SCHEMA_DIFF*/[ { "operation": "merge", "name": "DataGrid", "values": { "type": "listed", "hierarchical": true, "sortColumnDirection": { "bindTo": "disableGridSorting" }, "hierarchicalColumnName": "ParentId", "updateExpandHierarchyLevels": { "bindTo": "onExpandHierarchyLevels" }, "expandHierarchyLevels": { "bindTo": "expandHierarchyLevels" } } } ]/**SCHEMA_DIFF*/ }; } );