You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1001 lines
27 KiB

/*
** Zabbix
** Copyright (C) 2001-2023 Zabbix SIA
**
** This program is free software; you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by
** the Free Software Foundation; either version 2 of the License, or
** (at your option) any later version.
**
** This program is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
** GNU General Public License for more details.
**
** You should have received a copy of the GNU General Public License
** along with this program; if not, write to the Free Software
** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
**/
class CWidgetNavTree extends CWidget {
static EVENT_MARK = 'widget-navtree.mark';
static EVENT_SELECT = 'widget-navtree.select';
static WIDGET_MAP_EVENT_SUBMAP_SELECT = 'widget-map.submap-select';
static hasReferenceField() {
return true;
}
onInitialize() {
this._severity_levels = null;
this._navtree = [];
this._maps = [];
this._navtree_items_opened = [];
this._navtree_item_selected = null;
this._maps_accessible = null;
this._show_unavailable = false;
this._problems = null;
this._max_depth = null;
this._last_id = null;
this._has_contents = false;
this._registerContentsEvents();
}
onActivate() {
if (this._has_contents) {
if (this._target.querySelector('.root') === null) {
this._makeTree();
this._activateTree();
}
this._activateContentsEvents();
}
}
onDeactivate() {
this._deactivateContentsEvents();
}
announceWidgets(widgets) {
super.announceWidgets(widgets);
this._deactivateContentsEvents();
this._maps = [];
for (const widget of widgets) {
if (this._fields.reference === widget._fields.filter_widget_reference) {
this._maps.push(widget);
}
}
if (this._has_contents) {
this._activateContentsEvents();
}
}
getDataCopy({is_single_copy}) {
this._deactivateContentsEvents();
this._setTreeHandlers();
this._updateWidgetFields();
this._activateContentsEvents();
return super.getDataCopy({is_single_copy});
}
onEdit() {
if (this._has_contents) {
this._deactivateContentsEvents();
this._removeTree();
}
if (this._has_contents && this._state === WIDGET_STATE_ACTIVE) {
this._makeTree();
this._activateTree();
this._activateContentsEvents();
}
}
processUpdateResponse(response) {
if (this._has_contents) {
this._deactivateContentsEvents();
this._removeTree();
this._has_contents = false;
}
super.processUpdateResponse(response);
if (response.navtree_data !== undefined) {
this._has_contents = true;
this._severity_levels = response.navtree_data.severity_levels;
this._navtree = response.navtree_data.navtree;
this._navtree_items_opened = response.navtree_data.navtree_items_opened;
this._navtree_item_selected = response.navtree_data.navtree_item_selected;
this._maps_accessible = response.navtree_data.maps_accessible;
this._show_unavailable = response.navtree_data.show_unavailable;
this._problems = response.navtree_data.problems;
this._max_depth = response.navtree_data.max_depth;
this._makeTree();
this._activateTree();
this._activateContentsEvents();
}
}
_registerContentsEvents() {
this._events = {
...this._events,
addChild: (e) => {
const button = e.target;
const depth = parseInt(button.closest('.tree-list').getAttribute('data-depth'));
const parent = button.getAttribute('data-id');
this._itemEditDialog(0, parent, depth + 1, button);
},
addMaps: (e) => {
const button = e.target;
const depth = parseInt(button.closest('.tree-list').getAttribute('data-depth'));
const id = button.getAttribute('data-id');
if (typeof window.addPopupValues === 'function') {
window.old_addPopupValues = window.addPopupValues;
}
window.addPopupValues = (data) => {
this._deactivateContentsEvents();
const root = this._target.querySelector(`.tree-item[data-id="${id}"] > ul.tree-list`);
if (root !== null) {
for (const item of data.values) {
root.appendChild(this._makeTreeItem({
id: this._getNextId(),
name: item.name,
sysmapid: item.id,
parent: id
}, depth + 1));
}
const tree_item = root.closest('.tree-item');
tree_item.classList.remove('closed');
tree_item.classList.add('opened');
}
this._setTreeHandlers();
this._updateWidgetFields();
if (typeof old_addPopupValues === 'function') {
window.addPopupValues = old_addPopupValues;
delete window.old_addPopupValues;
}
this._activateContentsEvents();
};
return PopUp('popup.generic', {
srctbl: 'sysmaps',
srcfld1: 'sysmapid',
srcfld2: 'name',
multiselect: '1'
}, {dialogue_class: 'modal-popup-generic', trigger_element: e.target});
},
editItem: (e) => {
const button = e.target;
const id = button.getAttribute('data-id');
const parent = this._target.querySelector(`input[name="navtree.parent.${id}"]`).value;
const depth = parseInt(button.closest('[data-depth]').getAttribute('data-depth'));
this._itemEditDialog(id, parent, depth, button);
},
removeItem: (e) => {
const button = e.target;
this._deactivateContentsEvents();
this._target.querySelector(`[data-id="${button.getAttribute('data-id')}"]`).remove();
this._setTreeHandlers();
this._updateWidgetFields();
this._activateContentsEvents();
},
select: (e) => {
const link = e.target;
const itemid = link.closest('.tree-item').getAttribute('data-id');
if (this._markTreeItemSelected(itemid)) {
this._openBranch(this._navtree_item_selected);
updateUserProfile('web.dashboard.widget.navtree.item.selected', this._navtree_item_selected,
[this._widgetid]
);
this.fire(CWidgetNavTree.EVENT_SELECT, {
sysmapid: this._navtree[this._navtree_item_selected].sysmapid,
itemid: this._navtree_item_selected
});
}
e.preventDefault();
},
selectSubmap: (e) => {
if (e.detail.back) {
if (e.detail.parent_itemid !== null) {
this._markTreeItemSelected(e.detail.parent_itemid);
}
}
else {
for (let [itemid, item] of Object.entries(this._navtree)) {
if (item.sysmapid != e.detail.sysmapid || item.parent != e.detail.parent_itemid) {
continue;
}
if (this._markTreeItemSelected(itemid)) {
this._openBranch(this._navtree_item_selected);
}
}
}
}
}
}
_activateTree() {
if (this._is_edit_mode) {
this._makeSortable();
}
else {
this._parseProblems();
if (this._navtree_item_selected === null
|| !jQuery(`.tree-item[data-id=${this._navtree_item_selected}]`).is(':visible')) {
this._navtree_item_selected = jQuery('.tree-item:visible', jQuery(this._target))
.not('[data-sysmapid="0"]')
.first()
.data('id');
}
let sysmapid = 0;
if (this._markTreeItemSelected(this._navtree_item_selected)) {
sysmapid = this._navtree[this._navtree_item_selected].sysmapid;
}
this.fire(CWidgetNavTree.EVENT_SELECT, {sysmapid, itemid: this._navtree_item_selected});
}
}
_activateContentsEvents() {
if (this._state === WIDGET_STATE_ACTIVE && this._has_contents) {
if (this._is_edit_mode) {
for (const button of this._target.querySelectorAll('.js-add-child')) {
button.addEventListener('click', this._events.addChild);
}
for (const button of this._target.querySelectorAll('.js-add-maps')) {
button.addEventListener('click', this._events.addMaps);
}
for (const button of this._target.querySelectorAll('.js-edit')) {
button.addEventListener('click', this._events.editItem);
}
for (const button of this._target.querySelectorAll('.js-remove')) {
button.addEventListener('click', this._events.removeItem);
}
}
else {
for (const link of this._target.querySelectorAll('a[data-sysmapid]')) {
link.addEventListener('click', this._events.select);
}
}
}
if (!this._is_edit_mode) {
for (const widget of this._maps) {
widget.on(CWidgetNavTree.WIDGET_MAP_EVENT_SUBMAP_SELECT, this._events.selectSubmap);
}
}
}
_deactivateContentsEvents() {
if (this._has_contents) {
if (this._is_edit_mode) {
for (const button of this._target.querySelectorAll('.js-add-child')) {
button.removeEventListener('click', this._events.addChild);
}
for (const button of this._target.querySelectorAll('.js-add-maps')) {
button.removeEventListener('click', this._events.addMaps);
}
for (const button of this._target.querySelectorAll('.js-edit')) {
button.removeEventListener('click', this._events.editItem);
}
for (const button of this._target.querySelectorAll('.js-remove')) {
button.removeEventListener('click', this._events.removeItem);
}
}
else {
for (const link of this._target.querySelectorAll('a[data-sysmapid]')) {
link.removeEventListener('click', this._events.select);
}
}
}
if (!this._is_edit_mode) {
for (const widget of this._maps) {
widget.off(CWidgetNavTree.WIDGET_MAP_EVENT_SUBMAP_SELECT, this._events.selectSubmap);
}
}
}
_buildTree(parent_id = 0) {
const tree = [];
for (const i in this._navtree) {
const tree_item = {
id: i,
name: this._navtree[i].name,
order: this._navtree[i].order,
parent: this._navtree[i].parent,
sysmapid: this._navtree[i].sysmapid
};
if (tree_item.id > this._last_id) {
this._last_id = tree_item.id;
}
if (tree_item.parent == parent_id) {
const children = this._buildTree(tree_item.id);
if (children.length > 0) {
tree_item.children = children;
}
tree_item.item_active = (tree_item.sysmapid == 0 || this._maps_accessible.includes(tree_item.sysmapid));
tree_item.item_visible = (this._show_unavailable || tree_item.item_active);
tree.push(tree_item);
}
}
tree.sort((a, b) => {
return a.order - b.order;
});
return tree;
}
_makeTree() {
const tree = this._buildTree();
let root = this._makeTreeBranch();
root.classList.add('root');
this._target.querySelector('.tree').appendChild(root);
if (this._is_edit_mode) {
const root_item = this._makeTreeItem({name: t('root'), id: 0}, 0, false);
root.appendChild(root_item);
if (tree.length > 0) {
if (root_item.classList.contains('closed')) {
root_item.classList.add('opened');
root_item.classList.remove('closed');
}
}
root = document.getElementById(`${this._unique_id}_children-of-0`);
}
for (const item of tree) {
root.appendChild(this._makeTreeItem(item));
}
this._setTreeHandlers();
}
_makeTreeBranch(parent_id = null) {
const ul = document.createElement('ul');
if (parent_id !== null) {
ul.id = `${this._unique_id}_children-of-${parent_id}`;
}
ul.classList.add('tree-list');
return ul;
}
_makeTreeItem(item, depth = 1, editable = true) {
const li_item = document.createElement('li');
li_item.classList.add('tree-item');
if (!editable || this._navtree_items_opened.includes(item.id)) {
li_item.classList.add('opened');
}
else {
li_item.classList.add('closed');
}
if (!editable) {
li_item.classList.add('root-item');
}
if (this._is_edit_mode && item.sysmapid == 0) {
li_item.classList.add('no-map');
}
const ul = this._makeTreeBranch(item.id);
if (item.children !== undefined && this._max_depth > depth) {
let child_items_visible = 0;
for (const child of item.children) {
if (typeof child !== 'object') {
continue;
}
ul.appendChild(this._makeTreeItem(child, depth + 1));
if (child.id > this._last_id) {
this._last_id = child.id;
}
if (child.item_visible === true) {
child_items_visible++;
}
}
if (item.children.length > 0 && child_items_visible > 0) {
li_item.classList.add('is-parent');
}
}
if (!this._is_edit_mode && item.sysmapid != 0 && !item.item_active) {
li_item.classList.add('inaccessible');
}
let link;
if (!this._is_edit_mode && item.sysmapid != 0 && item.item_active) {
link = document.createElement('a');
link.href = '#';
link.setAttribute('data-sysmapid', item.sysmapid);
}
else {
link = document.createElement('span');
}
link.title = item.name;
link.innerText = item.name;
link.classList.add('item-name');
li_item.id = `${this._unique_id}_tree-item-${item.id}`;
li_item.setAttribute('data-id', item.id);
if (item.sysmapid != 0) {
li_item.setAttribute('data-sysmapid', item.sysmapid);
}
if (item.item_visible === false) {
li_item.style.display = 'none';
}
const tree_row = document.createElement('div');
tree_row.classList.add('tree-row');
li_item.appendChild(tree_row);
const content = document.createElement('div');
content.classList.add('content');
tree_row.appendChild(content);
const margin_lvl = document.createElement('div');
margin_lvl.classList.add('margin-lvl');
content.appendChild(margin_lvl);
if (this._is_edit_mode) {
const tools = document.createElement('div');
tools.classList.add('tools');
tree_row.appendChild(tools);
const button_add_child = document.createElement('button');
button_add_child.type = 'button';
button_add_child.title = t('Add child element');
button_add_child.classList.add(ZBX_STYLE_BTN_ICON, ZBX_ICON_PLUS, 'js-add-child');
button_add_child.setAttribute('data-id', item.id);
tools.appendChild(button_add_child);
const button_add_maps = document.createElement('button');
button_add_maps.type = 'button';
button_add_maps.title = t('Add multiple maps');
button_add_maps.classList.add(ZBX_STYLE_BTN_ICON, ZBX_ICON_COPY, 'js-add-maps');
button_add_maps.setAttribute('data-id', item.id);
tools.appendChild(button_add_maps);
if (editable) {
const button_edit = document.createElement('button');
button_edit.type = 'button';
button_edit.title = t('Edit');
button_edit.classList.add(ZBX_STYLE_BTN_ICON, ZBX_ICON_PENCIL, 'js-edit');
button_edit.setAttribute('data-id', item.id);
tools.appendChild(button_edit);
const button_remove = document.createElement('button');
button_remove.type = 'button';
button_remove.title = t('Remove');
button_remove.classList.add(ZBX_STYLE_BTN_ICON, ZBX_ICON_REMOVE_SMALL, 'js-remove');
button_remove.setAttribute('data-id', item.id);
tools.appendChild(button_remove);
const drag = document.createElement('div');
drag.classList.add('drag-icon');
content.appendChild(drag);
}
}
else {
const problems = document.createElement('div');
problems.classList.add('problem-icon-list');
tree_row.appendChild(problems);
}
const arrow = document.createElement('div');
arrow.classList.add('arrow');
content.appendChild(arrow);
if (editable) {
const arrow_btn = document.createElement('button');
const arrow_span = document.createElement('span');
arrow_btn.type = 'button';
arrow_btn.classList.add('treeview');
arrow_span.classList.add(li_item.classList.contains('opened') ? 'arrow-down' : 'arrow-right');
arrow_btn.appendChild(arrow_span);
arrow.appendChild(arrow_btn);
arrow_btn.addEventListener('click', () => {
const branch = arrow_btn.closest('[data-id]');
let closed_state = '1';
if (branch.classList.contains('opened')) {
arrow_btn.querySelector('span').classList.add('arrow-right');
arrow_btn.querySelector('span').classList.remove('arrow-down');
branch.classList.add('closed');
branch.classList.remove('opened');
}
else {
arrow_btn.querySelector('span').classList.add('arrow-down');
arrow_btn.querySelector('span').classList.remove('arrow-right');
branch.classList.add('opened');
branch.classList.remove('closed');
closed_state = '0';
}
if (this._widgetid !== null) {
updateUserProfile(`web.dashboard.widget.navtree.item-${branch.getAttribute('data-id')}.toggle`,
closed_state, [this._widgetid]
);
const index = this._navtree_items_opened.indexOf(branch.getAttribute('data-id'));
if (index > -1) {
if (closed_state === '1') {
this._navtree_items_opened.splice(index, 1);
}
else {
this._navtree_items_opened.push(branch.getAttribute('data-id'));
}
}
else if (index === -1 && closed_state === '0') {
this._navtree_items_opened.push(branch.getAttribute('data-id'));
}
}
});
}
content.appendChild(link);
li_item.appendChild(ul);
if (this._is_edit_mode && editable) {
const name_fld = document.createElement('input');
name_fld.id = `${this._unique_id}_navtree.name.${item.id}`;
name_fld.type = 'hidden';
name_fld.name = `navtree.name.${item.id}`;
name_fld.value = item.name;
li_item.appendChild(name_fld);
const parent_fld = document.createElement('input');
parent_fld.id = `${this._unique_id}_navtree.parent.${item.id}`;
parent_fld.type = 'hidden';
parent_fld.name = `navtree.parent.${item.id}`;
parent_fld.value = item.parent || 0;
li_item.appendChild(parent_fld);
const mapid_fld = document.createElement('input');
mapid_fld.id = `${this._unique_id}_navtree.sysmapid.${item.id}`;
mapid_fld.type = 'hidden';
mapid_fld.name = `navtree.sysmapid.${item.id}`;
mapid_fld.value = item.sysmapid;
li_item.appendChild(mapid_fld);
}
return li_item;
}
_removeTree() {
const root = this._target.querySelector('.root');
if (root !== null) {
root.remove();
}
}
_setTreeHandlers() {
// Add .is-parent class for branches with sub-items.
jQuery('.tree-list', jQuery(this._target)).not('.ui-sortable, .root').each(function() {
if (jQuery('>li', jQuery(this)).not('.inaccessible').length) {
jQuery(this).closest('.tree-item').addClass('is-parent');
}
else {
jQuery(this).closest('.tree-item').removeClass('is-parent');
}
});
// Set [data-depth] for list and each sublist.
jQuery('.tree-list', jQuery(this._target)).each(function() {
jQuery(this).attr('data-depth', jQuery(this).parents('.tree-list').length);
});
// Change arrow style.
jQuery('.is-parent', jQuery(this._target)).each(function() {
const $arrow = jQuery('> .tree-row > .content > .arrow > .treeview > span', jQuery(this));
if (jQuery(this).hasClass('opened')) {
$arrow.removeClass('arrow-right').addClass('arrow-down');
}
else {
$arrow.removeClass('arrow-down a1').addClass('arrow-right');
}
});
for (const tree_element of document.querySelectorAll('.tree-list')) {
for (const button of tree_element.querySelectorAll('.js-add-child, .js-add-maps')) {
button.disabled = tree_element.dataset.depth >= this._max_depth;
}
}
}
_markTreeItemSelected(itemid) {
const selected_item = document.getElementById(`${this._unique_id}_tree-item-${itemid}`);
const item = this._navtree[itemid];
if (item === undefined || selected_item === null || item === this._navtree_item_selected) {
return false;
}
this._navtree_item_selected = itemid;
let step_in_path = selected_item.closest('.tree-item');
this._target.querySelectorAll('.selected').forEach((selected) => {
selected.classList.remove('selected');
});
while (step_in_path !== null) {
step_in_path.classList.add('selected');
step_in_path = step_in_path.parentNode.closest('.tree-item');
}
updateUserProfile('web.dashboard.widget.navtree.item.selected', this._navtree_item_selected, [this._widgetid]);
this.fire(CWidgetNavTree.EVENT_MARK, {itemid: this._navtree_item_selected});
return true;
}
_openBranch(itemid) {
if (!jQuery(`.tree-item[data-id=${itemid}]`).is(':visible')) {
const selector = '> .tree-row > .content > .arrow > .treeview > span';
let branch_to_open = jQuery(`.tree-item[data-id=${itemid}]`).closest('.tree-list').not('.root');
while (branch_to_open.length) {
branch_to_open.closest('.tree-item.is-parent')
.removeClass('closed')
.addClass('opened');
jQuery(selector, branch_to_open.closest('.tree-item.is-parent'))
.removeClass('arrow-right')
.addClass('arrow-down');
branch_to_open = branch_to_open.closest('.tree-item.is-parent')
.closest('.tree-list').not('.root');
}
}
}
_getNextId() {
this._last_id++;
while (jQuery(`[name="navtree.name.${this._last_id}"]`).length) {
this._last_id++;
}
return this._last_id;
}
_makeSortable() {
jQuery('.root-item > .tree-list', jQuery(this._target))
.sortable_tree({
max_depth: this._max_depth,
stop: () => {
this._setTreeHandlers();
this._updateWidgetFields();
}
})
.disableSelection();
}
_parseProblems() {
if (this._severity_levels === null) {
return false;
}
const empty_template = {};
for (const [severity, _] in Object.entries(this._severity_levels)) {
empty_template[severity] = 0;
}
for (const [itemid, problems] of Object.entries(this._problems)) {
for (const [severity, value] of Object.entries(problems || empty_template)) {
if (value) {
this._target.querySelectorAll(`.tree-item[data-id="${itemid}"]`).forEach((item) => {
item.setAttribute(`data-problems${severity}`, value);
})
}
}
}
for (const [severity, value] of Object.entries(this._severity_levels)) {
for (const problem of this._target.querySelectorAll(`[data-problems${severity}]`)) {
const indicator = document.createElement('span');
indicator.title = value.name;
indicator.classList.add('problem-icon-list-item', value.style_class);
indicator.innerText = problem.getAttribute(`data-problems${severity}`);
problem.querySelector('.tree-row > .problem-icon-list')
.appendChild(indicator)
}
}
}
_itemEditDialog(id, parent, depth, trigger_elmnt) {
const url = new Curl('zabbix.php');
const item_edit = id != 0;
url.setArgument('action', 'widget.navtree.item.edit');
jQuery.ajax({
url: url.getUrl(),
method: 'POST',
data: {
name: item_edit ? this._target.querySelector(`[name="navtree.name.${id}"]`).value : '',
sysmapid: item_edit ? this._target.querySelector(`[name="navtree.sysmapid.${id}"]`).value : 0,
depth: depth
},
dataType: 'json',
success: (resp) => {
if (resp.debug !== undefined) {
resp.body += resp.debug;
}
overlayDialogue({
'title': t('Edit tree element'),
'class': 'modal-popup',
'content': resp.body,
'buttons': [
{
'title': item_edit ? t('Apply') : t('Add'),
'class': 'dialogue-widget-save',
'action': (overlay) => {
const form = document.getElementById('widget-dialogue-form');
const form_inputs = form.elements;
const url = new Curl('zabbix.php');
url.setArgument('action', 'widget.navtree.item.update');
overlay.setLoading();
overlay.xhr = $.ajax({
url: url.getUrl(),
method: 'POST',
data: {
name: form_inputs.name.value.trim(),
sysmapid: form_inputs.sysmapid !== undefined
? form_inputs.sysmapid.value
: '0',
add_submaps: form_inputs.add_submaps !== undefined
&& form_inputs.add_submaps.checked ? 1 : 0,
depth: depth
},
dataType: 'json',
complete: () => {
overlay.unsetLoading();
},
success: (resp) => {
form.querySelectorAll('.msg-bad').forEach((msg) => {
msg.remove();
})
if ('error' in resp) {
const message_box = makeMessageBox('bad', resp.error.messages,
resp.error.title
)[0];
form.insertAdjacentElement('afterbegin', message_box);
return false;
}
else {
this._deactivateContentsEvents();
if (item_edit) {
const $row = jQuery(`[data-id="${id}"]`, jQuery(this._target));
jQuery(`[name="navtree.name.${id}"]`, $row).val(resp.name);
jQuery(`[name="navtree.sysmapid.${id}"]`, $row)
.val(resp['sysmapid']);
jQuery('> .tree-row > .content > .item-name', $row)
.empty()
.attr('title', resp['name'])
.append(jQuery('<span>').text(resp.name));
$row.toggleClass('no-map', resp.sysmapid == 0);
}
else {
const root = this._target
.querySelector(`.tree-item[data-id="${parent}"]>ul.tree-list`);
id = this._getNextId();
if (root !== null) {
root.append(this._makeTreeItem({
id: id,
name: resp['name'],
sysmapid: resp['sysmapid'],
parent: parent
}, depth + 1));
root.closest('.tree-item').classList.remove('closed');
root.closest('.tree-item').classList.add('opened', 'is-parent');
}
}
const add_child_level = (sysmapid, itemid, depth) => {
if (resp.hierarchy[sysmapid] !== undefined
&& depth <= this._max_depth) {
const root = this._target
.querySelector(`.tree-item[data-id="${itemid}"]>ul.tree-list`);
$.each(resp.hierarchy[sysmapid], (i, submapid) => {
if (resp.submaps[submapid] === undefined) {
return;
}
const submap_item = resp.submaps[submapid];
const submap_itemid = this._getNextId();
root.append(this._makeTreeItem({
id: submap_itemid,
name: submap_item['name'],
sysmapid: submap_item['sysmapid'],
parent: itemid
}));
add_child_level(submapid, submap_itemid, depth + 1);
});
root.closest('.tree-item').classList.remove('closed');
root.closest('.tree-item').classList.add('opened', 'is-parent');
}
};
add_child_level(resp['sysmapid'], id, depth + 1);
overlayDialogueDestroy(overlay.dialogueid);
this._updateWidgetFields();
this._setTreeHandlers();
this._activateContentsEvents();
}
}
});
return false;
},
'isSubmit': true
},
{
'title': t('Cancel'),
'class': 'btn-alt',
'action': () => {}
}
],
'dialogueid': 'navtreeitem',
'script_inline': resp.script_inline
}, trigger_elmnt);
}
});
}
_updateWidgetFields() {
const prefix = `${this.getUniqueId()}_`;
if (!this._is_edit_mode) {
return false;
}
for (const name in this._fields) {
if (/^navtree\.(name|order|parent|sysmapid)\.\d+$/.test(name)) {
delete this._fields[name]
}
}
jQuery('input[name^="navtree.name."]', jQuery(this._body)).each((index, field) => {
const id = field.getAttribute('name').substr(13);
if (id) {
const parent = document.getElementById(`${prefix}navtree.parent.${id}`).value;
const sysmapid = document.getElementById(`${prefix}navtree.sysmapid.${id}`).value;
const element = document.getElementById(`${prefix}children-of-${parent}`);
let order = 0;
if (element !== null) {
const sibling = element.childNodes;
while (sibling[order] !== undefined && sibling[order].getAttribute('data-id') != id) {
order++;
}
}
this._fields[`navtree.name.${id}`] = field.value;
if (parent != 0) {
this._fields[`navtree.parent.${id}`] = parent;
}
if (order != 0) {
this._fields[`navtree.order.${id}`] = order + 1;
}
if (sysmapid != 0) {
this._fields[`navtree.sysmapid.${id}`] = sysmapid;
}
}
});
}
}