/** * Copyright JS Foundation and other contributors, http://js.foundation * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. **/ RED.sidebar.config = (function() { let flashingConfigNode; let flashingConfigNodeTimer; var content = document.createElement("div"); content.className = "red-ui-sidebar-node-config"; content.id = "red-ui-sidebar-node-config"; content.tabIndex = 0; $('
'+ ''+ ' '+ '
' ).appendTo(content); var toolbar = $('
'+ ' '+ ''+ '
'); var globalCategories = $("
").appendTo(content); var flowCategories = $("
").appendTo(content); var subflowCategories = $("
").appendTo(content); var showUnusedOnly = false; var categories = {}; function getOrCreateCategory(name,parent,label,isLocked) { name = name.replace(/\./i,"-"); if (!categories[name]) { var container = $('
').appendTo(parent); var header = $('
').appendTo(container); let lockIcon if (label) { lockIcon = $('').appendTo(header) lockIcon.toggle(!!isLocked) $('').text(label).appendTo(header); } else { $('').appendTo(header); } $('').appendTo(header); category = $('
    ').appendTo(container); category.on("click", function(e) { $(content).find(".red-ui-palette-node").removeClass("selected"); }); container.i18n(); var icon = header.find("i"); var result = { label: label, lockIcon, list: category, size: function() { return result.list.find("li:not(.red-ui-palette-node-config-none)").length }, open: function(snap) { if (!icon.hasClass("expanded")) { icon.addClass("expanded"); if (snap) { result.list.show(); } else { result.list.slideDown(); } } }, close: function(snap) { if (icon.hasClass("expanded")) { icon.removeClass("expanded"); if (snap) { result.list.hide(); } else { result.list.slideUp(); } } }, isOpen: function() { return icon.hasClass("expanded"); } }; header.on('click', function(e) { if (result.isOpen()) { result.close(); } else { result.open(); } }); categories[name] = result; } else { if (isLocked !== undefined && categories[name].lockIcon) { categories[name].lockIcon.toggle(!!isLocked) } if (categories[name].label !== label) { categories[name].list.parent().find('.red-ui-palette-node-config-label').text(label); categories[name].label = label; } } return categories[name]; } function createConfigNodeList(id,nodes) { var category = getOrCreateCategory(id.replace(/\./i,"-")) var list = category.list; nodes.sort(function(A,B) { if (A.type < B.type) { return -1;} if (A.type > B.type) { return 1;} return 0; }); if (showUnusedOnly) { var hiddenCount = nodes.length; nodes = nodes.filter(function(n) { return n._def.hasUsers!==false && n.users.length === 0; }) hiddenCount = hiddenCount - nodes.length; if (hiddenCount > 0) { list.parent().find('.red-ui-sidebar-node-config-filter-info').text(RED._('sidebar.config.filtered',{count:hiddenCount})).show(); } else { list.parent().find('.red-ui-sidebar-node-config-filter-info').hide(); } } else { list.parent().find('.red-ui-sidebar-node-config-filter-info').hide(); } list.empty(); if (nodes.length === 0) { $('
  • NONE
  • ').i18n().appendTo(list); category.close(true); } else { var currentType = ""; nodes.forEach(function(node) { var labelText = RED.utils.getNodeLabel(node,node.id); if (node.type != currentType) { $('
  • '+node.type+'
  • ').appendTo(list); currentType = node.type; } if (node.changed) { labelText += "!!" } var entry = $('
  • ').appendTo(list); var nodeDiv = $('
    ').appendTo(entry); entry.data('node',node.id); nodeDiv.data('node',node.id); var label = $('
    ').text(labelText).appendTo(nodeDiv); if (node.d) { nodeDiv.addClass("red-ui-palette-node-config-disabled"); $('').prependTo(label); } if (node._def.hasUsers !== false) { var iconContainer = $('
    ',{class:"red-ui-palette-icon-container red-ui-palette-icon-container-right"}).appendTo(nodeDiv); if (node.users.length === 0) { iconContainer.text(0); } else { $('').on("click", function(e) { e.stopPropagation(); e.preventDefault(); RED.search.show(node.id); }).text(node.users.length).appendTo(iconContainer); } RED.popover.tooltip(iconContainer,RED._('editor.nodesUse',{count:node.users.length})); if (node.users.length === 0) { nodeDiv.addClass("red-ui-palette-node-config-unused"); } } nodeDiv.on('click',function(e) { e.stopPropagation(); RED.view.select(false); if (e.metaKey) { $(this).toggleClass("selected"); } else { $(content).find(".red-ui-palette-node").removeClass("selected"); $(this).addClass("selected"); } RED.sidebar.info.refresh(node); }); nodeDiv.on('dblclick',function(e) { e.stopPropagation(); RED.editor.editConfig("", node.type, node.id); }); var userArray = node.users.map(function(n) { return n.id }); nodeDiv.on('mouseover',function(e) { RED.nodes.eachNode(function(node) { if( userArray.indexOf(node.id) != -1) { node.highlighted = true; node.dirty = true; } }); RED.view.redraw(); }); nodeDiv.on('mouseout',function(e) { RED.nodes.eachNode(function(node) { if(node.highlighted) { node.highlighted = false; node.dirty = true; } }); RED.view.redraw(); }); }); category.open(true); } } function refreshConfigNodeList() { var validList = {"global":true}; getOrCreateCategory("global",globalCategories); RED.nodes.eachWorkspace(function(ws) { validList[ws.id.replace(/\./g,"-")] = true; getOrCreateCategory(ws.id,flowCategories,ws.label, ws.locked); }) RED.nodes.eachSubflow(function(sf) { validList[sf.id.replace(/\./g,"-")] = true; getOrCreateCategory(sf.id,subflowCategories,sf.name); }) $(".red-ui-sidebar-config-category").each(function() { var id = $(this).attr('id').substring("red-ui-sidebar-config-category-".length); if (!validList[id]) { $(this).remove(); delete categories[id]; } }) var globalConfigNodes = []; var configList = {}; RED.nodes.eachConfig(function(cn) { if (cn.z) { configList[cn.z.replace(/\./g,"-")] = configList[cn.z.replace(/\./g,"-")]||[]; configList[cn.z.replace(/\./g,"-")].push(cn); } else if (!cn.z) { globalConfigNodes.push(cn); } }); for (var id in validList) { if (validList.hasOwnProperty(id)) { createConfigNodeList(id,configList[id]||[]); } } createConfigNodeList('global',globalConfigNodes); } function init() { RED.sidebar.addTab({ id: "config", label: RED._("sidebar.config.label"), name: RED._("sidebar.config.name"), content: content, toolbar: toolbar, iconClass: "fa fa-cog", action: "core:show-config-tab", onchange: function() { refreshConfigNodeList(); } }); RED.actions.add("core:show-config-tab", function() {RED.sidebar.show('config')}); RED.actions.add("core:select-all-config-nodes", function() { $(content).find(".red-ui-palette-node").addClass("selected"); }) RED.actions.add("core:delete-config-selection", function() { var selectedNodes = []; $(content).find(".red-ui-palette-node.selected").each(function() { selectedNodes.push($(this).parent().data('node')); }); if (selectedNodes.length > 0) { var historyEvent = { t:'delete', nodes:[], changes: {}, dirty: RED.nodes.dirty() } for (let i = 0; i < selectedNodes.length; i++) { let node = RED.nodes.node(selectedNodes[i]) if (node.z) { let ws = RED.nodes.workspace(node.z) if (ws && ws.locked) { return } } } selectedNodes.forEach(function(id) { var node = RED.nodes.node(id); try { if (node._def.oneditdelete) { node._def.oneditdelete.call(node); } } catch(err) { console.log("oneditdelete",node.id,node.type,err.toString()); } historyEvent.nodes.push(node); for (var i=0;i 0) { categories[cat].open(); } } } }); $('#red-ui-sidebar-config-filter-all').on("click",function(e) { e.preventDefault(); if (showUnusedOnly) { $(this).addClass('selected'); $('#red-ui-sidebar-config-filter-unused').removeClass('selected'); showUnusedOnly = !showUnusedOnly; refreshConfigNodeList(); } }); $('#red-ui-sidebar-config-filter-unused').on("click",function(e) { e.preventDefault(); if (!showUnusedOnly) { $(this).addClass('selected'); $('#red-ui-sidebar-config-filter-all').removeClass('selected'); showUnusedOnly = !showUnusedOnly; refreshConfigNodeList(); } }); RED.popover.tooltip($('#red-ui-sidebar-config-filter-all'), RED._("sidebar.config.showAllConfigNodes")); RED.popover.tooltip($('#red-ui-sidebar-config-filter-unused'), RED._("sidebar.config.showAllUnusedConfigNodes")); } function flashConfigNode(el) { if(flashingConfigNode && flashingConfigNode.length) { //cancel current flashing node before flashing new node clearInterval(flashingConfigNodeTimer); flashingConfigNodeTimer = null; flashingConfigNode.children("div").removeClass('highlighted'); flashingConfigNode = null; } if(!el || !el.children("div").length) { return; } flashingConfigNodeTimer = setInterval(function(flashEndTime) { if (flashEndTime >= Date.now()) { const highlighted = el.children("div").hasClass("highlighted"); el.children("div").toggleClass('highlighted', !highlighted) } else { clearInterval(flashingConfigNodeTimer); flashingConfigNodeTimer = null; flashingConfigNode = null; el.children("div").removeClass('highlighted'); } }, 100, Date.now() + 2200); flashingConfigNode = el; el.children("div").addClass('highlighted'); } function show(id) { if (typeof id === 'boolean') { if (id) { $('#red-ui-sidebar-config-filter-unused').trigger("click"); } else { $('#red-ui-sidebar-config-filter-all').trigger("click"); } } refreshConfigNodeList(); if (typeof id === "string") { $('#red-ui-sidebar-config-filter-all').trigger("click"); id = id.replace(/\./g,"-"); setTimeout(function() { var node = $(".red-ui-palette-node_id_"+id); var y = node.position().top; var h = node.height(); var scrollWindow = $(".red-ui-sidebar-node-config"); var scrollHeight = scrollWindow.height(); if (y+h > scrollHeight) { scrollWindow.animate({scrollTop: '-='+(scrollHeight-(y+h)-30)},150); } else if (y<0) { scrollWindow.animate({scrollTop: '+='+(y-10)},150); } flashConfigNode(node, id); },100); } RED.sidebar.show("config"); } return { init:init, show:show, refresh:refreshConfigNodeList } })();