Tidy up markdown toolbar handling across all editors

Any editor for the markdown mode will now automatically get
the markdown toolbar added.

The comment node has been updated to handle this properly and
to not add two copies of its content to the sidebar.
This commit is contained in:
Nick O'Leary 2018-12-10 15:23:02 +00:00
parent cf3b4e9e63
commit 6201247875
No known key found for this signature in database
GPG Key ID: 4F2157149161A6C9
12 changed files with 83 additions and 68 deletions

View File

@ -27,8 +27,7 @@
"status": "Status", "status": "Status",
"enabled": "Enabled", "enabled": "Enabled",
"disabled":"Disabled", "disabled":"Disabled",
"info": "Description", "info": "Description"
"tip": "Description accepts Markdown and will appear in the Info tab."
}, },
"menu": { "menu": {
"label": { "label": {
@ -279,7 +278,6 @@
"deleteSubflow": "delete subflow", "deleteSubflow": "delete subflow",
"info": "Description", "info": "Description",
"category": "Category", "category": "Category",
"format":"markdown format",
"errors": { "errors": {
"noNodesSelected": "<strong>Cannot create subflow</strong>: no nodes selected", "noNodesSelected": "<strong>Cannot create subflow</strong>: no nodes selected",
"multipleInputsToSelection": "<strong>Cannot create subflow</strong>: multiple inputs to selection" "multipleInputsToSelection": "<strong>Cannot create subflow</strong>: multiple inputs to selection"
@ -719,7 +717,8 @@
"format": "format JSON" "format": "format JSON"
}, },
"markdownEditor": { "markdownEditor": {
"title": "Markdown editor" "title": "Markdown editor",
"format": "Formatted with markdown"
}, },
"bufferEditor": { "bufferEditor": {
"title": "Buffer editor", "title": "Buffer editor",

View File

@ -27,8 +27,7 @@
"status": "状態", "status": "状態",
"enabled": "有効", "enabled": "有効",
"disabled": "無効", "disabled": "無効",
"info": "詳細", "info": "詳細"
"tip": "マークダウン形式で記述した「詳細」は「情報タブ」に表示されます。"
}, },
"menu": { "menu": {
"label": { "label": {
@ -278,7 +277,6 @@
"deleteSubflow": "サブフローを削除", "deleteSubflow": "サブフローを削除",
"info": "詳細", "info": "詳細",
"category": "カテゴリ", "category": "カテゴリ",
"format": "マークダウン形式",
"errors": { "errors": {
"noNodesSelected": "<strong>サブフローを作成できません</strong>: ノードが選択されていません", "noNodesSelected": "<strong>サブフローを作成できません</strong>: ノードが選択されていません",
"multipleInputsToSelection": "<strong>サブフローを作成できません</strong>: 複数の入力が選択されています" "multipleInputsToSelection": "<strong>サブフローを作成できません</strong>: 複数の入力が選択されています"

View File

@ -22,8 +22,7 @@
"status": "状态", "status": "状态",
"enabled": "有效", "enabled": "有效",
"disabled": "无效", "disabled": "无效",
"info": "详细描述", "info": "详细描述"
"tip": "详细描述支持Markdown轻量级标记语言并将出现在信息标签中。"
}, },
"menu": { "menu": {
"label": { "label": {
@ -191,7 +190,6 @@
"output": "输出:", "output": "输出:",
"deleteSubflow": "删除子流程", "deleteSubflow": "删除子流程",
"info": "详细描述", "info": "详细描述",
"format": "标记格式",
"errors": { "errors": {
"noNodesSelected": "<strong>无法创建子流程</strong>: 未选择节点", "noNodesSelected": "<strong>无法创建子流程</strong>: 未选择节点",
"multipleInputsToSelection": "<strong>无法创建子流程</strong>: 多个输入到了选择" "multipleInputsToSelection": "<strong>无法创建子流程</strong>: 多个输入到了选择"

View File

@ -38,7 +38,7 @@ RED.popover = (function() {
var direction = options.direction || "right"; var direction = options.direction || "right";
var trigger = options.trigger; var trigger = options.trigger;
var content = options.content; var content = options.content;
var delay = options.delay; var delay = options.delay || { show: 750, hide: 50 };
var autoClose = options.autoClose; var autoClose = options.autoClose;
var width = options.width||"auto"; var width = options.width||"auto";
var size = options.size||"default"; var size = options.size||"default";
@ -172,6 +172,18 @@ RED.popover = (function() {
openPopup(); openPopup();
} }
}); });
if (autoClose) {
target.on('mouseleave disabled', function(e) {
if (timer) {
clearTimeout(timer);
}
if (active) {
active = false;
setTimeout(closePopup,autoClose);
}
});
}
} else if (trigger === 'modal') { } else if (trigger === 'modal') {
$(document).on('mousedown.modal-popover-close', function (event) { $(document).on('mousedown.modal-popover-close', function (event) {
var target = event.target; var target = event.target;

View File

@ -929,7 +929,7 @@ RED.editor = (function() {
function buildDescriptionForm(container,node) { function buildDescriptionForm(container,node) {
var dialogForm = $('<form class="dialog-form form-horizontal" autocomplete="off"></form>').appendTo(container); var dialogForm = $('<form class="dialog-form form-horizontal" autocomplete="off"></form>').appendTo(container);
var toolbarRow = $('<div></div>').appendTo(dialogForm); var toolbarRow = $('<div></div>').appendTo(dialogForm);
var row = $('<div class="form-row node-text-editor-row" style="position:relative; padding-top: 4px; height: calc(100% - 36px);"></div>').appendTo(dialogForm); var row = $('<div class="form-row node-text-editor-row" style="position:relative; padding-top: 4px; height: 100%"></div>').appendTo(dialogForm);
$('<div style="height: 100%" class="node-text-editor" id="node-info-input-info-editor" ></div>').appendTo(row); $('<div style="height: 100%" class="node-text-editor" id="node-info-input-info-editor" ></div>').appendTo(row);
var nodeInfoEditor = RED.editor.createEditor({ var nodeInfoEditor = RED.editor.createEditor({
id: "node-info-input-info-editor", id: "node-info-input-info-editor",
@ -939,26 +939,6 @@ RED.editor = (function() {
if (node.info) { if (node.info) {
nodeInfoEditor.getSession().setValue(node.info, -1); nodeInfoEditor.getSession().setValue(node.info, -1);
} }
var toolbar = RED.editor.types._markdown.buildToolbar(toolbarRow,nodeInfoEditor);
$('<button id="node-info-input-info-expand" class="editor-button" style="float: right;"><i class="fa fa-expand"></i></button>').appendTo(toolbar);
$('#node-info-input-info-expand').click(function(e) {
e.preventDefault();
var value = nodeInfoEditor.getValue();
RED.editor.editMarkdown({
value: value,
width: "Infinity",
cursor: nodeInfoEditor.getCursorPosition(),
complete: function(v,cursor) {
nodeInfoEditor.setValue(v, -1);
nodeInfoEditor.gotoLine(cursor.row+1,cursor.column,false);
setTimeout(function() {
nodeInfoEditor.focus();
},300);
}
})
});
return nodeInfoEditor; return nodeInfoEditor;
} }
@ -2206,7 +2186,10 @@ RED.editor = (function() {
createEditor: function(options) { createEditor: function(options) {
var editor = ace.edit(options.id||options.element); var el = options.element || $("#"+options.id)[0];
var toolbarRow = $("<div>").appendTo(el);
el = $("<div>").appendTo(el).addClass("node-text-editor-container")[0];
var editor = ace.edit(el);
editor.setTheme("ace/theme/tomorrow"); editor.setTheme("ace/theme/tomorrow");
var session = editor.getSession(); var session = editor.getSession();
session.on("changeAnnotation", function () { session.on("changeAnnotation", function () {
@ -2254,6 +2237,39 @@ RED.editor = (function() {
} }
},100); },100);
} }
if (options.mode === 'ace/mode/markdown') {
$(el).addClass("node-text-editor-container-toolbar");
editor.toolbar = RED.editor.types._markdown.buildToolbar(toolbarRow,editor);
if (options.expandable !== false) {
var expandButton = $('<button class="editor-button" style="float: right;"><i class="fa fa-expand"></i></button>').appendTo(editor.toolbar);
expandButton.click(function(e) {
e.preventDefault();
var value = editor.getValue();
RED.editor.editMarkdown({
value: value,
width: "Infinity",
cursor: editor.getCursorPosition(),
complete: function(v,cursor) {
editor.setValue(v, -1);
editor.gotoLine(cursor.row+1,cursor.column,false);
setTimeout(function() {
editor.focus();
},300);
}
})
});
}
var helpButton = $('<button class="node-text-editor-help editor-button editor-button-small"><i class="fa fa-question"></i></button>').appendTo($(el).parent());
RED.popover.create({
target: helpButton,
trigger: 'click',
size: "small",
direction: "left",
content: RED._("markdownEditor.format"),
autoClose: 50
});
}
return editor; return editor;
} }
} }

View File

@ -41,7 +41,7 @@ RED.editor.types._markdown = (function() {
'<div id="node-input-markdown-panel-editor" class="red-ui-panel">'+ '<div id="node-input-markdown-panel-editor" class="red-ui-panel">'+
'<div style="height: 100%; margin: auto; max-width: 1000px;">'+ '<div style="height: 100%; margin: auto; max-width: 1000px;">'+
'<div id="node-input-markdown-toolbar"></div>'+ '<div id="node-input-markdown-toolbar"></div>'+
'<div class="node-text-editor" style="height: calc(100% - 50px)" id="node-input-markdown"></div>'+ '<div class="node-text-editor" style="height: 100%" id="node-input-markdown"></div>'+
'</div>'+ '</div>'+
'</div>'+ '</div>'+
'<div class="red-ui-panel">'+ '<div class="red-ui-panel">'+
@ -112,7 +112,8 @@ RED.editor.types._markdown = (function() {
expressionEditor = RED.editor.createEditor({ expressionEditor = RED.editor.createEditor({
id: 'node-input-markdown', id: 'node-input-markdown',
value: value, value: value,
mode:"ace/mode/markdown" mode:"ace/mode/markdown",
expandable: false
}); });
var changeTimer; var changeTimer;
expressionEditor.getSession().on("change", function() { expressionEditor.getSession().on("change", function() {
@ -138,11 +139,10 @@ RED.editor.types._markdown = (function() {
} }
}); });
panels.ratio(1); panels.ratio(1);
var toolbar = RED.editor.types._markdown.buildToolbar($("#node-input-markdown-toolbar"), expressionEditor);
$('<span class="button-group" style="float:right">'+ $('<span class="button-group" style="float:right">'+
'<button id="node-btn-markdown-preview" class="editor-button toggle single"><i class="fa fa-eye"></i></button>'+ '<button id="node-btn-markdown-preview" class="editor-button toggle single"><i class="fa fa-eye"></i></button>'+
'</span>').appendTo(toolbar); '</span>').appendTo(expressionEditor.toolbar);
$("#node-btn-markdown-preview").click(function(e) { $("#node-btn-markdown-preview").click(function(e) {
e.preventDefault(); e.preventDefault();

View File

@ -146,7 +146,6 @@ RED.workspaces = (function() {
height -= $(rows[i]).outerHeight(true); height -= $(rows[i]).outerHeight(true);
} }
height -= (parseInt($("#dialog-form").css("marginTop"))+parseInt($("#dialog-form").css("marginBottom"))); height -= (parseInt($("#dialog-form").css("marginTop"))+parseInt($("#dialog-form").css("marginBottom")));
height -= 28;
$(".node-text-editor").css("height",height+"px"); $(".node-text-editor").css("height",height+"px");
tabflowEditor.resize(); tabflowEditor.resize();
}, },
@ -166,7 +165,6 @@ RED.workspaces = (function() {
var row = $('<div class="form-row node-text-editor-row">'+ var row = $('<div class="form-row node-text-editor-row">'+
'<label for="node-input-info" data-i18n="editor:workspace.info" style="width:300px;"></label>'+ '<label for="node-input-info" data-i18n="editor:workspace.info" style="width:300px;"></label>'+
'<div class="node-text-editor-toolbar"></div>'+
'<div style="min-height:250px;" class="node-text-editor" id="node-input-info"></div>'+ '<div style="min-height:250px;" class="node-text-editor" id="node-input-info"></div>'+
'</div>').appendTo(dialogForm); '</div>').appendTo(dialogForm);
tabflowEditor = RED.editor.createEditor({ tabflowEditor = RED.editor.createEditor({
@ -175,10 +173,6 @@ RED.workspaces = (function() {
value: "" value: ""
}); });
var toolbar = RED.editor.types._markdown.buildToolbar(row.find(".node-text-editor-toolbar"),tabflowEditor);
$('<button id="node-info-input-info-expand" class="editor-button" style="float: right;"><i class="fa fa-expand"></i></button>').appendTo(toolbar);
$('#node-info-input-info-expand').click(function(e) { $('#node-info-input-info-expand').click(function(e) {
e.preventDefault(); e.preventDefault();
var value = tabflowEditor.getValue(); var value = tabflowEditor.getValue();

View File

@ -209,11 +209,28 @@
} }
.node-text-editor { .node-text-editor {
position: relative;
.node-text-editor-help {
position: absolute;
bottom: 0px;
right: 1px;
border-bottom-right-radius: 5px;
z-Index: 8;
border-bottom: none;
border-right: none;
}
}
.node-text-editor-container {
border:1px solid #ccc; border:1px solid #ccc;
border-radius:5px; border-radius:5px;
overflow: hidden; overflow: hidden;
font-size: 14px !important; font-size: 14px !important;
font-family: Menlo, Consolas, 'DejaVu Sans Mono', Courier, monospace !important; font-family: Menlo, Consolas, 'DejaVu Sans Mono', Courier, monospace !important;
height: 100%;
&.node-text-editor-container-toolbar {
height: calc(100% - 40px);
}
} }
.editor-button { .editor-button {
@ -333,7 +350,7 @@
padding: 10px; padding: 10px;
border:1px solid #ccc; border:1px solid #ccc;
border-radius:5px; border-radius:5px;
height: calc(100% - 31px); height: calc(100% - 21px);
overflow-y: scroll; overflow-y: scroll;
background: #fff; background: #fff;
} }

View File

@ -1,17 +1,13 @@
<script type="text/x-red" data-template-name="comment"> <script type="text/x-red" data-template-name="comment">
<div class="form-row"> <div class="form-row">
<label for="node-input-name"><i class="fa fa-comment"></i> <span data-i18n="comment.label.title"></span></label> <label for="node-input-name"><i class="fa fa-tag"></i> <span data-i18n="common.label.name"></span></label>
<input type="text" id="node-input-name"> <input type="text" id="node-input-name">
</div> </div>
<div class="form-row" style="margin-bottom: 0px;">
<label for="node-input-info" style="width: 100% !important;"><i class="fa fa-comments"></i> <span data-i18n="comment.label.body"></span></label>
<input type="hidden" id="node-input-info" autofocus="autofocus">
</div>
<div class="form-row node-text-editor-row"> <div class="form-row node-text-editor-row">
<input type="hidden" id="node-input-info" autofocus="autofocus">
<div style="height: 250px; min-height:150px;" class="node-text-editor" id="node-input-info-editor"></div> <div style="height: 250px; min-height:150px;" class="node-text-editor" id="node-input-info-editor"></div>
</div> </div>
<div class="form-tips" data-i18n="[html]comment.tip"></div>
</script> </script>
<script type="text/javascript"> <script type="text/javascript">
@ -32,7 +28,7 @@
return this.name?"node_label_italic":""; return this.name?"node_label_italic":"";
}, },
info: function() { info: function() {
return (this.name?"# "+this.name+"\n":"")+(this.info||""); return this.name?"# "+this.name+"\n\n---\n\n":"";
}, },
oneditprepare: function() { oneditprepare: function() {
var that = this; var that = this;

View File

@ -307,12 +307,7 @@
} }
}, },
"comment": { "comment": {
"comment": "comment", "comment": "comment"
"label": {
"title": "Title",
"body": "Body"
},
"tip": "Tip: The body text can be styled as <a href=\"https://help.github.com/articles/markdown-basics/\" target=\"_blank\">GitHub flavoured Markdown</a>"
}, },
"unknown": { "unknown": {
"label": { "label": {

View File

@ -307,12 +307,7 @@
} }
}, },
"comment": { "comment": {
"comment": "comment", "comment": "comment"
"label": {
"title": "タイトル",
"body": "本文"
},
"tip": "注釈: 本文は<a href=\"https://help.github.com/articles/markdown-basics/\" target=\"_blank\">GitHubのMarkdown形式</a>として整形されます。"
}, },
"unknown": { "unknown": {
"label": { "label": {

View File

@ -297,11 +297,6 @@
} }
}, },
"comment": { "comment": {
"label": {
"title": "标题",
"body": "主体"
},
"tip": "提示: 主题内容可被格式化为 <a href=\"https://help.github.com/articles/markdown-basics/\" target=\"_blank\">GitHub风格的Markdown</a>"
}, },
"unknown": { "unknown": {
"label": { "label": {