mirror of
https://github.com/node-red/node-red.git
synced 2025-03-01 10:36:34 +00:00
Compare commits
331 Commits
delete-unu
...
0.20.0-bet
Author | SHA1 | Date | |
---|---|---|---|
|
d23b32a830 | ||
|
ceba08a801 | ||
|
e0bb03a53f | ||
|
2e063f91bc | ||
|
79062e2034 | ||
|
4baaaa8d59 | ||
|
c99b35428b | ||
|
3c8e4f8bbf | ||
|
aa9a37da38 | ||
|
85efb48c1f | ||
|
888e7ee023 | ||
|
d7bbf8a8da | ||
|
e2ee88de84 | ||
|
1d1ab5b7b2 | ||
|
54c863d48f | ||
|
acc633b4b6 | ||
|
766ccf85c2 | ||
|
7ab5a2be47 | ||
|
7a6e1fe566 | ||
|
4749c92252 | ||
|
0e035e47df | ||
|
1359545e13 | ||
|
5b2f24f842 | ||
|
bb73e30909 | ||
|
490903ca25 | ||
|
901b32297e | ||
|
dd72046922 | ||
|
6286b34d00 | ||
|
81f4e0de56 | ||
|
da756fa568 | ||
|
30aebc4ee3 | ||
|
45138ce5ca | ||
|
f26b9feeaf | ||
|
9e47d933af | ||
|
f309a9d537 | ||
|
a786b37cb9 | ||
|
6a519a30a2 | ||
|
81ae552e69 | ||
|
0ec04a3624 | ||
|
81d5b47fce | ||
|
ed31a0cf15 | ||
|
201d1926bc | ||
|
9ee6655bfa | ||
|
c4beab6b0d | ||
|
34b6643913 | ||
|
98e391b867 | ||
|
19eb8e9a6d | ||
|
43b7aa40c3 | ||
|
747af44fc1 | ||
|
a73381e24b | ||
|
d5ef428edd | ||
|
5fa4d227b8 | ||
|
cc7e3b0c26 | ||
|
473a2ae275 | ||
|
7f5d47f39d | ||
|
6031f146aa | ||
|
020a469f3b | ||
|
091de3aa66 | ||
|
b837f7608c | ||
|
afe9367bac | ||
|
9bd9023cb6 | ||
|
8502cf8498 | ||
|
33dade0584 | ||
|
84cc2ad0fa | ||
|
dc2d3bc7c0 | ||
|
64df557423 | ||
|
715cc77e76 | ||
|
b80d1af3d7 | ||
|
f05f534fd2 | ||
|
c0837ead0e | ||
|
a1f135bd66 | ||
|
978f4ecc58 | ||
|
46a8d96997 | ||
|
c283224000 | ||
|
a6ef755139 | ||
|
29a257d17a | ||
|
368b76a183 | ||
|
8bb861124d | ||
|
2f884ec778 | ||
|
8c561e92c8 | ||
|
633b9180d7 | ||
|
0e2d0e1b6f | ||
|
ea4d65ceee | ||
|
d47ac84d2e | ||
|
a97759aa35 | ||
|
3fcfd4abdd | ||
|
6d771da9a9 | ||
|
6201247875 | ||
|
8c367bcc53 | ||
|
8198132ca7 | ||
|
cf3b4e9e63 | ||
|
987dbf8a92 | ||
|
acf8c9bc4a | ||
|
7173895d36 | ||
|
43530d4a5f | ||
|
fefabef9ee | ||
|
0dd40a941b | ||
|
24b6670bc4 | ||
|
76661abbf5 | ||
|
e9dc9eff9b | ||
|
2f160743bc | ||
|
98616e772c | ||
|
bc014fec9b | ||
|
732598d9d2 | ||
|
2979acd5b8 | ||
|
fd20cd524e | ||
|
7b80ae42e1 | ||
|
b7012674c6 | ||
|
c76bd39280 | ||
|
09cd710f66 | ||
|
d9aadf9d98 | ||
|
86716b5ffb | ||
|
96e3aab3b4 | ||
|
72c78fe3ad | ||
|
abe746020b | ||
|
8e1c15419c | ||
|
ee47646cf7 | ||
|
32d9acdaa5 | ||
|
4eb3bd496b | ||
|
3c4f4d27d6 | ||
|
2060af8a92 | ||
|
21bf74a467 | ||
|
677833a277 | ||
|
0b5e4f2dd7 | ||
|
06a1f30350 | ||
|
c1ff241550 | ||
|
5717f75eac | ||
|
6b3b68a4e5 | ||
|
8bda2d0add | ||
|
bc02c9573c | ||
|
8167608f04 | ||
|
514e31aef9 | ||
|
20a31a6d38 | ||
|
4f0aa1bc02 | ||
|
be0ef6e594 | ||
|
93a8dbd31a | ||
|
cf931e8ddf | ||
|
510bfbf268 | ||
|
2f93bb969b | ||
|
27365c9f7b | ||
|
b1d2e188f5 | ||
|
e4f67df2a1 | ||
|
e094ea3d2a | ||
|
7515b745b5 | ||
|
0e902a7e71 | ||
|
2dfb443625 | ||
|
e6e7747ae1 | ||
|
d80ea6c0f5 | ||
|
ac6e3988a8 | ||
|
bfd98f3767 | ||
|
cc8bc1339f | ||
|
542d1dc600 | ||
|
1c66c88f95 | ||
|
dc880c672a | ||
|
073f38c68c | ||
|
6a6d13b075 | ||
|
9bb7e72c69 | ||
|
7436e01188 | ||
|
3d272d0f10 | ||
|
ee66a12dad | ||
|
47de85b012 | ||
|
f85b63a972 | ||
|
e630919ef8 | ||
|
2e3fd49b40 | ||
|
dd54af2c08 | ||
|
737bf411ff | ||
|
5070b1a6b5 | ||
|
c849da92cf | ||
|
6a4e7201fe | ||
|
ffa6dea452 | ||
|
30c1d31a99 | ||
|
6934a2d5c3 | ||
|
b9906ced9a | ||
|
5500b4fe35 | ||
|
2353f12cd6 | ||
|
1b8cab0f58 | ||
|
869c1d4ea4 | ||
|
9b938195a8 | ||
|
bb3c52821a | ||
|
81c8ae95e2 | ||
|
6098570ab7 | ||
|
d033c24fe5 | ||
|
4995e52dd6 | ||
|
c685a31056 | ||
|
c32ce3bb7b | ||
|
c0d8f904b3 | ||
|
8dba0dac9e | ||
|
d0bf4a5329 | ||
|
7b28ba6078 | ||
|
e6466c3c3a | ||
|
d96d3064d6 | ||
|
d4589ed7e3 | ||
|
5cfc52ea18 | ||
|
3fcacd8339 | ||
|
49fe13f22f | ||
|
4d27ba1bda | ||
|
b715ac8bf4 | ||
|
d96049416f | ||
|
1c4df785fd | ||
|
8f94c5efeb | ||
|
7cffa1ece7 | ||
|
1ac18d7b33 | ||
|
1111d2518b | ||
|
ba7416450e | ||
|
3b02d36acb | ||
|
c2aa9a5337 | ||
|
70fb181b7b | ||
|
e64f4e3f39 | ||
|
e4d518749f | ||
|
7dcca2c907 | ||
|
4a027b8a79 | ||
|
c2c6e6080e | ||
|
4f87ebdf0a | ||
|
09abec15b1 | ||
|
33d0d12bc8 | ||
|
f488869635 | ||
|
6382564727 | ||
|
7476b4c7db | ||
|
daf3e6a47a | ||
|
19b6cba398 | ||
|
5bd3d12c7b | ||
|
c9db74ebca | ||
|
f8a88cc1a4 | ||
|
4a081bf125 | ||
|
8a68a3e861 | ||
|
7a9dd9ad9c | ||
|
6c01d0f9d8 | ||
|
45a53ac168 | ||
|
dabb2790c9 | ||
|
c66c5ea53c | ||
|
0a98ba6985 | ||
|
bb8e491856 | ||
|
5590d31336 | ||
|
dc7e48dc53 | ||
|
371d357218 | ||
|
f22960ad59 | ||
|
34ead436b0 | ||
|
808d5a75ae | ||
|
55e897faac | ||
|
5a5dda21e4 | ||
|
f085655daa | ||
|
5cf9c07b73 | ||
|
9751089807 | ||
|
211eeea05d | ||
|
b2516117f5 | ||
|
2816b3edae | ||
|
242398c724 | ||
|
289583325d | ||
|
0f793ebd65 | ||
|
ce014044ea | ||
|
1064e531f0 | ||
|
dc3128fb3e | ||
|
51a3521834 | ||
|
d40aa7260f | ||
|
fc8c4063f2 | ||
|
f204c77ba3 | ||
|
7a8545273c | ||
|
6a9575e9f4 | ||
|
c13e79e9c3 | ||
|
62088259ae | ||
|
925ebcc06e | ||
|
a20eaf852f | ||
|
84a6a5235e | ||
|
8235b7b96d | ||
|
0376e0d711 | ||
|
6bd0682e8c | ||
|
e24c22f9be | ||
|
673a6bbe2c | ||
|
cf32a33984 | ||
|
f4ca8cd738 | ||
|
98c1bc276d | ||
|
629536b562 | ||
|
422109868d | ||
|
bcc7834650 | ||
|
1161e4f6c1 | ||
|
14435c24ac | ||
|
22ede79799 | ||
|
6cb3699ee9 | ||
|
6c65d3830e | ||
|
cdcf39fe82 | ||
|
1441042458 | ||
|
71403e5acd | ||
|
3d70bc722a | ||
|
b2f50da322 | ||
|
2a50c66df8 | ||
|
8de47c0a6e | ||
|
023391e22a | ||
|
a4ddfd404f | ||
|
7307e558cb | ||
|
47356f5221 | ||
|
c6f8950b64 | ||
|
58c8311d56 | ||
|
071f4eacde | ||
|
f96bdc578e | ||
|
e03a0fffa9 | ||
|
8e2c12f8d9 | ||
|
114420e8fd | ||
|
ba49b2c681 | ||
|
5391fc962a | ||
|
7cec7ae608 | ||
|
d6211af5bd | ||
|
ef114e31c2 | ||
|
fd74a03479 | ||
|
428bf634e9 | ||
|
c49f722e4f | ||
|
d4d95a43b6 | ||
|
8789d983ed | ||
|
10faa96bcf | ||
|
42d31b9ee6 | ||
|
c9dc9b4fe9 | ||
|
a345089c8b | ||
|
67c268e13d | ||
|
f13e02a1a9 | ||
|
1a7868159a | ||
|
c6a1c8e8c4 | ||
|
ce85c8d986 | ||
|
fde157ff50 | ||
|
51f875c02d | ||
|
f0957c838f | ||
|
f5bebef37f | ||
|
cb35604ef5 | ||
|
61681bb1d6 | ||
|
1a226c4dc6 | ||
|
716aa74004 | ||
|
c102828a99 | ||
|
cb0e631b85 | ||
|
b14a0e0dde | ||
|
e982f5076f | ||
|
42188b9f49 | ||
|
50e2dcbcd5 | ||
|
6104bb98f1 |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -21,3 +21,4 @@ nodes/core/locales/zz-ZZ
|
||||
packages/node_modules/@node-red/editor-client/public
|
||||
!test/**/node_modules
|
||||
docs
|
||||
!packages/node_modules/**/docs
|
||||
|
@@ -1,5 +1,4 @@
|
||||
/Gruntfile.js
|
||||
/.git/*
|
||||
/lib/*
|
||||
*.backup
|
||||
/public/*
|
||||
|
194
CHANGELOG.md
194
CHANGELOG.md
@@ -1,3 +1,197 @@
|
||||
#### 0.20.0-beta.4: Beta Release
|
||||
|
||||
Runtime
|
||||
|
||||
- Bump JSONata to 1.6.4
|
||||
- Add Flow.getSetting for resolving env-var properties
|
||||
- Refactor Subflow logic into own class
|
||||
- Restore RED.auth to node-red module api
|
||||
- Tidy up when usage in Flow and Node
|
||||
|
||||
Editor
|
||||
|
||||
- German translation
|
||||
- Change default dropdown appearance and sidebar tab menu handling
|
||||
- Handle multiple-select box when nothing selected Fixes #2021
|
||||
- Handle i18n properly when key is a valid sub-identifier Fixes #2028
|
||||
- Avoid duplicate links when missing node type installed Fixes #2032
|
||||
- Add View Tools
|
||||
- Don't collapse version control header when clicking refresh
|
||||
- Add fast entry via keyboard for string of nodes
|
||||
- Check for undeployed change before showing open project dialog
|
||||
- Add placeholder node when in quick-add mode
|
||||
- Move nodes to top-left corner when converting to subflow
|
||||
|
||||
Nodes
|
||||
|
||||
- Debug: Allow debug edit expression to be sent to status
|
||||
- WebSocket: Fix missing translated help
|
||||
|
||||
|
||||
#### 0.20.0-beta.3: Beta Release
|
||||
|
||||
Editor
|
||||
|
||||
- Update palette manager view properly when module updated
|
||||
- Add TreeList common widget
|
||||
- Fix visual jump when opening Comment editor on Safari Part of #2008
|
||||
- Fix vertical align of markdown editor in Safari Fixes #2008
|
||||
- Avoid marking node as changed if label state is default Fixes #2009
|
||||
- Highlight port on node hover while joining
|
||||
- Support drag-wiring of link nodes
|
||||
- Allow TypeSearch to include a filter option
|
||||
- Improve diff colouring
|
||||
- Allow sections to toggle in 2-element stack
|
||||
- Add support for ${} env var syntax when skipping validation Closes #1980
|
||||
- i18 support for markdown editor tooltip
|
||||
- Add RED.editor.registerTypeEditor for custom type editors
|
||||
- Tidy up markdown toolbar handling across all editors
|
||||
- Added validation while export into library
|
||||
- Reuse notification boxes rather than stack multiple of the same type
|
||||
- Make ssh key dialog accessible when opened from new proj dialog
|
||||
|
||||
Runtime
|
||||
|
||||
- Bump JSONata to 1.6.4 Fixes #2023
|
||||
- Add audit logging to admin api
|
||||
- Fix failure of RED.require #2010
|
||||
- Allow oauth strategy callback method to be customised Closes #1998
|
||||
- Ensure fs context cache is flushed on close Fixes #2001
|
||||
- Fix library Buffer( to Buffer.alloc( for node 10
|
||||
- Catch file-not-found on startup when non-existant flow file specified
|
||||
- Actively expire login sesssions and notify user
|
||||
- Add quotation marks for basic auth challenge #1976
|
||||
|
||||
Nodes
|
||||
|
||||
- Change: remove promises to improve performance
|
||||
- Debug: add ability to apply JSONata expression to message
|
||||
- Join: remove promises to improve performance
|
||||
- JSON: delete msg.schema before sending msg to avoid conflicts
|
||||
- Link: update UI to use common TreeList widget
|
||||
- Switch: remove promises to improve performance
|
||||
|
||||
#### 0.20.0-beta.2: Beta Release
|
||||
|
||||
- Split Node-RED internals into multiple sub-modules
|
||||
|
||||
Editor
|
||||
|
||||
- Allow the editor to use a custom admin api url root
|
||||
- Improve performance of Flow Diff dialog - @TothiViseo #1989
|
||||
- Add 'open project' option to Projects Welcome dialog
|
||||
- Add 'type already registered' check in palette editor
|
||||
- Handle missing tab.disabled property
|
||||
- Handle missing wires prop and string x/y props on import
|
||||
- Add RED.notifications.hide flag - for UI testing
|
||||
- Improve alignment of node label edit inputs
|
||||
- Show arrow-in node when invalid font-awesome icon name was specified for default icon
|
||||
- Add ability to delete context values from sidebar
|
||||
- Allow copy-to-clipboard copy whole tabs
|
||||
- Make disabled flows more obvious in editor
|
||||
- Allow import/export from file in editor
|
||||
- Allow config nodes to be selected in sidebar and deleted
|
||||
- Show port label of subflow with input port
|
||||
- Support ctrl-click selection of flow tabs
|
||||
- Allow left-hand node button to act as toggle
|
||||
- Support dbl-click in tab bar to add new flow in position
|
||||
- Fix duplicate subflow detection on import
|
||||
- Add import notification with info on what has been imported Closes #1862
|
||||
- Show error details when trying to import invalid json
|
||||
- Show default icon when non-existent font-awesome icon was specified
|
||||
- Add configurable option for showing node label
|
||||
- Avoid http redirects as Safari doesn't reuse Auth header Fixes #1903
|
||||
- Tidy up ace tooltip styling
|
||||
- Add event log to editor
|
||||
- Add tooltips to multiple editor elements
|
||||
- Allow palette to be hidden
|
||||
- Add node module into to sidebar and palette popover
|
||||
- Mark all newly imported nodes as changed
|
||||
- Allow a node label to be hidden
|
||||
- Add markdown formatting toolbar
|
||||
- Add markdown toolbar to various editors
|
||||
- Fix i18n handling for ja-JP locale on Safari/MacOS
|
||||
- Add node body tooltip
|
||||
- Decrease opacity of flow-navigator
|
||||
- Update tooltip style
|
||||
- Update ACE to 1.4.1-src-min-noconflict
|
||||
- Cache node locales by language
|
||||
- Show icon element with either icon image or fa-icon
|
||||
- Added font-awesome icons to user defined icon
|
||||
- Update info side bar with node description section
|
||||
- One-click search of config node users
|
||||
- Redesign node edit dialog to tabbed style
|
||||
- Add 'restart flows' option to deploy menu
|
||||
- Add node description property UI
|
||||
|
||||
|
||||
Runtime
|
||||
|
||||
- Allow a project to be loaded from cmdline
|
||||
- Handle lookup of undefined property in Global context Fixes #1978
|
||||
- Refuse to enable Manage Palette if npm too old
|
||||
- Remove restriction on upgrading non-local modules
|
||||
- Remove deprecated Buffer constructor usage Fixes #1709
|
||||
- Update httpServerOptions doc in settings.js
|
||||
- Exclude non-testable .js files from the unit tests
|
||||
- Add --safe mode flag to allow starting without flows running
|
||||
- Add setting-defined accessToken for automated access to the adminAPI - #1789
|
||||
|
||||
Nodes
|
||||
|
||||
- Move all core node EN help to their own locale files - #1990
|
||||
- CSV: better regex for number detection
|
||||
- Debug: hide button if not configured to send to sidebar
|
||||
- Delay: report queue activity when in by-topic mode
|
||||
- Delay: add msg.flush mode
|
||||
- Exec: Preserve existing properties on msg object
|
||||
- File: remove CR/LF from incoming filename
|
||||
- Function: create custom ace javascript mode to handle ES6 Fixes #1911
|
||||
- Function: add env.get
|
||||
- HTTP Request: Add http-proxy config #1913
|
||||
- HTTP Request: add msg.redirectList to output
|
||||
- HTTP Request: add msg.requestTimeout option for per-message setting - @natcl #1959
|
||||
- MQTT: add auto-detect and base64 output to mqtt node Fixes #1912 - @DurandA
|
||||
- MQTT: only unsubscribe node that is being removed
|
||||
- Sentiment: move to node-red-node-sentiment
|
||||
- Switch: add missing edit dialog icon
|
||||
- Tail: move to node-red-node-tail
|
||||
- TCPGet: clear status if user changes target per message
|
||||
- Template: tidy up edit dialog
|
||||
- UDP: more resilient binding to correct port for udp, give input side priority
|
||||
- Split/Join: add msg.reset to info panel
|
||||
- Split/Join: reset join without sending part array
|
||||
- Watch: add msg.filename so can feed direct to file in node
|
||||
- WebSocket: preserve \_session on msg but don't send as part of wholemsg
|
||||
|
||||
|
||||
#### 0.19.5: Maintenance Release
|
||||
|
||||
- Recognize pip installs of RPi.GPIO (#1934)
|
||||
- Merge pull request #1941 from node-red-hitachi/master-batch
|
||||
- Merge pull request #1931 from node-red-hitachi/master-typedinput
|
||||
- Set min value of properties and spinners for batch
|
||||
- Fix that unnecessary optionMenu remains
|
||||
- Merge pull request #1894 from node-red-hitachi/fix-overlapping-file-node-execution
|
||||
- Merge pull request #1924 from imZack/patch-1
|
||||
- Add missing comma
|
||||
- Do not disable context sidebar during node edit Fixes #1921
|
||||
- Don't allow virtual links to be spliced Fixes #1920
|
||||
- Merge project package changes to avoid overwritten changes
|
||||
- Handle manually added project deps that are unused Fixes #1908
|
||||
- update close & input handling of File node
|
||||
- make close handler argument only one
|
||||
- Merge pull request #1907 from amilajack/patch-2
|
||||
- Change repo badge to point to master branch
|
||||
- invoke callbacks if async handler is specified
|
||||
- Merge pull request #1891 from camlow325/resolve-example-path-for-windows-support
|
||||
- Merge pull request #1900 from kazuhitoyokoi/master-addtestcases4settings.js
|
||||
- wait closing while pending messages exist
|
||||
- Add test cases for red/api/editor/settings.js
|
||||
- Ensure all palette categories are opened properly Closes #1893
|
||||
- Resolve path when sending example file for Windows support
|
||||
- fix multiple input message processing of file node
|
||||
|
||||
#### 0.19.4: Maintenance Release
|
||||
|
||||
- Fix race condition in non-cache lfs context Fixes #1888
|
||||
|
103
Gruntfile.js
103
Gruntfile.js
@@ -15,6 +15,7 @@
|
||||
**/
|
||||
|
||||
var path = require("path");
|
||||
var fs = require("fs-extra");
|
||||
|
||||
module.exports = function(grunt) {
|
||||
|
||||
@@ -57,7 +58,8 @@ module.exports = function(grunt) {
|
||||
ignoreLeaks: false,
|
||||
ui: 'bdd',
|
||||
reportFormats: ['lcov','html'],
|
||||
print: 'both'
|
||||
print: 'both',
|
||||
istanbulOptions: ['--no-default-excludes', '-i','**/packages/node_modules/**']
|
||||
},
|
||||
all: { src: ["test/unit/_spec.js","test/unit/**/*_spec.js","test/nodes/**/*_spec.js"] },
|
||||
core: { src: ["test/unit/_spec.js","test/unit/**/*_spec.js"]},
|
||||
@@ -118,6 +120,7 @@ module.exports = function(grunt) {
|
||||
src: [
|
||||
// Ensure editor source files are concatenated in
|
||||
// the right order
|
||||
"packages/node_modules/@node-red/editor-client/src/js/jquery-addons.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/red.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/events.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/i18n.js",
|
||||
@@ -128,10 +131,12 @@ module.exports = function(grunt) {
|
||||
"packages/node_modules/@node-red/editor-client/src/js/text/format.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/state.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/nodes.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/font-awesome.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/history.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/validators.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/utils.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/common/editableList.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/common/treeList.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/common/checkboxSet.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/common/menu.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/common/panels.js",
|
||||
@@ -147,6 +152,7 @@ module.exports = function(grunt) {
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/workspaces.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/view.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/view-navigator.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/view-tools.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/sidebar.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/palette.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/tab-info.js",
|
||||
@@ -155,6 +161,7 @@ module.exports = function(grunt) {
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/palette-editor.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/editor.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/editors/*.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/event-log.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/tray.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/clipboard.js",
|
||||
"packages/node_modules/@node-red/editor-client/src/js/ui/library.js",
|
||||
@@ -226,7 +233,7 @@ module.exports = function(grunt) {
|
||||
messages: {
|
||||
src: [
|
||||
'packages/node_modules/@node-red/nodes/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/editor-api/lib/editor/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/editor-client/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/runtime/locales/**/*.json'
|
||||
]
|
||||
},
|
||||
@@ -281,7 +288,7 @@ module.exports = function(grunt) {
|
||||
json: {
|
||||
files: [
|
||||
'packages/node_modules/@node-red/nodes/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/editor-api/lib/editor/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/editor-client/locales/**/*.json',
|
||||
'packages/node_modules/@node-red/runtime/locales/**/*.json'
|
||||
],
|
||||
tasks: ['jsonlint:messages']
|
||||
@@ -368,6 +375,16 @@ module.exports = function(grunt) {
|
||||
{
|
||||
src: 'CHANGELOG.md',
|
||||
dest: 'packages/node_modules/@node-red/editor-client/public/red/about'
|
||||
},
|
||||
{
|
||||
src: 'CHANGELOG.md',
|
||||
dest: 'packages/node_modules/node-red/'
|
||||
},
|
||||
{
|
||||
cwd: 'packages/node_modules/@node-red/editor-client/src/ace/bin/',
|
||||
src: '**',
|
||||
expand: true,
|
||||
dest: 'packages/node_modules/@node-red/editor-client/public/vendor/ace/'
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -383,6 +400,28 @@ module.exports = function(grunt) {
|
||||
]
|
||||
}
|
||||
},
|
||||
'npm-command': {
|
||||
options: {
|
||||
cmd: "pack",
|
||||
cwd: "<%= paths.dist %>/modules"
|
||||
},
|
||||
'node-red': { options: { args: [__dirname+'/packages/node_modules/node-red'] } },
|
||||
'@node-red/editor-api': { options: { args: [__dirname+'/packages/node_modules/@node-red/editor-api'] } },
|
||||
'@node-red/editor-client': { options: { args: [__dirname+'/packages/node_modules/@node-red/editor-client'] } },
|
||||
'@node-red/nodes': { options: { args: [__dirname+'/packages/node_modules/@node-red/nodes'] } },
|
||||
'@node-red/registry': { options: { args: [__dirname+'/packages/node_modules/@node-red/registry'] } },
|
||||
'@node-red/runtime': { options: { args: [__dirname+'/packages/node_modules/@node-red/runtime'] } },
|
||||
'@node-red/util': { options: { args: [__dirname+'/packages/node_modules/@node-red/util'] } }
|
||||
|
||||
|
||||
},
|
||||
mkdir: {
|
||||
release: {
|
||||
options: {
|
||||
create: ['<%= paths.dist %>/modules']
|
||||
},
|
||||
},
|
||||
},
|
||||
compress: {
|
||||
release: {
|
||||
options: {
|
||||
@@ -397,28 +436,43 @@ module.exports = function(grunt) {
|
||||
}
|
||||
},
|
||||
jsdoc : {
|
||||
runtimeAPI: {
|
||||
src: 'packages/node_modules/@node-red/runtime/lib/api/*.js',
|
||||
modules: {
|
||||
src: [
|
||||
'packages/node_modules/node-red/lib/red.js',
|
||||
'packages/node_modules/@node-red/runtime/lib/index.js',
|
||||
'packages/node_modules/@node-red/runtime/lib/api/*.js',
|
||||
'packages/node_modules/@node-red/runtime/lib/events.js',
|
||||
'packages/node_modules/@node-red/util/**/*.js',
|
||||
'packages/node_modules/@node-red/editor-api/lib/index.js',
|
||||
'packages/node_modules/@node-red/editor-api/lib/auth/index.js'
|
||||
],
|
||||
options: {
|
||||
destination: 'docs',
|
||||
configure: './jsdoc.json'
|
||||
}
|
||||
},
|
||||
nodeREDUtil: {
|
||||
src: 'packages/node_modules/@node-red/util/**/*.js',
|
||||
editor: {
|
||||
src: [
|
||||
'packages/node_modules/@node-red/editor-client/src/js'
|
||||
],
|
||||
options: {
|
||||
destination: 'packages/node_modules/@node-red/util/docs',
|
||||
destination: 'packages/node_modules/@node-red/editor-client/docs',
|
||||
configure: './jsdoc.json'
|
||||
}
|
||||
}
|
||||
|
||||
},
|
||||
jsdoc2md: {
|
||||
runtimeAPI: {
|
||||
options: {
|
||||
separators: true
|
||||
},
|
||||
src: 'packages/node_modules/@node-red/runtime/lib/api/*.js',
|
||||
dest: 'docs/runtime-api.md'
|
||||
src: [
|
||||
'packages/node_modules/@node-red/runtime/lib/index.js',
|
||||
'packages/node_modules/@node-red/runtime/lib/api/*.js',
|
||||
'packages/node_modules/@node-red/runtime/lib/events.js'
|
||||
],
|
||||
dest: 'packages/node_modules/@node-red/runtime/docs/api.md'
|
||||
},
|
||||
nodeREDUtil: {
|
||||
options: {
|
||||
@@ -447,6 +501,8 @@ module.exports = function(grunt) {
|
||||
grunt.loadNpmTasks('grunt-webdriver');
|
||||
grunt.loadNpmTasks('grunt-jsdoc');
|
||||
grunt.loadNpmTasks('grunt-jsdoc-to-markdown');
|
||||
grunt.loadNpmTasks('grunt-npm-command');
|
||||
grunt.loadNpmTasks('grunt-mkdir');
|
||||
|
||||
grunt.registerMultiTask('attachCopyright', function() {
|
||||
var files = this.data.src;
|
||||
@@ -489,11 +545,21 @@ module.exports = function(grunt) {
|
||||
});
|
||||
|
||||
grunt.registerTask('verifyPackageDependencies', function() {
|
||||
var done = this.async();
|
||||
var verifyDependencies = require("./scripts/verify-package-dependencies.js");
|
||||
var failures = verifyDependencies();
|
||||
if (failures.length > 0) {
|
||||
failures.forEach(f => grunt.log.error(f));
|
||||
grunt.fail.fatal("Failed to verify package dependencies");
|
||||
verifyDependencies().then(function(failures) {
|
||||
if (failures.length > 0) {
|
||||
failures.forEach(f => grunt.log.error(f));
|
||||
grunt.fail.fatal("Failed to verify package dependencies");
|
||||
}
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
grunt.registerTask('verifyUiTestDependencies', function() {
|
||||
if (!fs.existsSync(path.join("node_modules", "chromedriver"))) {
|
||||
grunt.fail.fatal('You need to run "npm install chromedriver@2" before running UI test.');
|
||||
return false;
|
||||
}
|
||||
});
|
||||
|
||||
@@ -517,7 +583,7 @@ module.exports = function(grunt) {
|
||||
|
||||
grunt.registerTask('test-ui',
|
||||
'Builds editor content then runs unit tests on editor ui',
|
||||
['build','jshint:editor','webdriver:all']);
|
||||
['verifyUiTestDependencies','build','jshint:editor','webdriver:all']);
|
||||
|
||||
grunt.registerTask('test-nodes',
|
||||
'Runs unit tests on core nodes',
|
||||
@@ -533,7 +599,12 @@ module.exports = function(grunt) {
|
||||
|
||||
grunt.registerTask('release',
|
||||
'Create distribution zip file',
|
||||
['build','verifyPackageDependencies','clean:release','chmod:release','compress:release']);
|
||||
['build','verifyPackageDependencies','clean:release','mkdir:release','chmod:release','compress:release','pack-modules']);
|
||||
|
||||
grunt.registerTask('pack-modules',
|
||||
'Create module pack files for release',
|
||||
['mkdir:release','npm-command']);
|
||||
|
||||
|
||||
grunt.registerTask('coverage',
|
||||
'Run Istanbul code test coverage task',
|
||||
|
@@ -2,7 +2,7 @@
|
||||
|
||||
http://nodered.org
|
||||
|
||||
[](https://travis-ci.org/node-red/node-red)
|
||||
[](https://travis-ci.org/node-red/node-red)
|
||||
[](https://coveralls.io/r/node-red/node-red?branch=master)
|
||||
|
||||
A visual tool for wiring the Internet of Things.
|
||||
|
@@ -15,7 +15,6 @@
|
||||
},
|
||||
"templates": {
|
||||
"systemName": "Node-RED Runtime API",
|
||||
"theme":"yeti",
|
||||
"footer": "",
|
||||
"copyright": "Released under the Apache License v2.0",
|
||||
"default": {
|
||||
|
57
package.json
57
package.json
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "node-red",
|
||||
"version": "0.20.0-alpha.0",
|
||||
"version": "0.20.0-beta.4",
|
||||
"description": "A visual tool for wiring the Internet of Things",
|
||||
"homepage": "http://nodered.org",
|
||||
"license": "Apache-2.0",
|
||||
@@ -24,37 +24,39 @@
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"ajv": "6.5.3",
|
||||
"basic-auth": "2.0.0",
|
||||
"ajv": "6.7.0",
|
||||
"basic-auth": "2.0.1",
|
||||
"bcryptjs": "2.4.3",
|
||||
"body-parser": "1.18.3",
|
||||
"cheerio": "0.22.0",
|
||||
"clone": "2.1.2",
|
||||
"cookie": "0.3.1",
|
||||
"cookie-parser": "1.4.3",
|
||||
"cors": "2.8.4",
|
||||
"cron": "1.4.1",
|
||||
"denque": "1.3.0",
|
||||
"express": "4.16.3",
|
||||
"cors": "2.8.5",
|
||||
"cron": "1.6.0",
|
||||
"denque": "1.4.0",
|
||||
"express": "4.16.4",
|
||||
"express-session": "1.15.6",
|
||||
"fs-extra": "5.0.0",
|
||||
"fs-extra": "7.0.1",
|
||||
"fs.notify": "0.0.4",
|
||||
"hash-sum": "1.0.2",
|
||||
"https-proxy-agent": "2.2.1",
|
||||
"i18next": "11.6.0",
|
||||
"i18next": "13.1.0",
|
||||
"is-utf8": "0.2.1",
|
||||
"js-yaml": "3.12.0",
|
||||
"js-yaml": "3.12.1",
|
||||
"json-stringify-safe": "5.0.1",
|
||||
"jsonata": "1.5.4",
|
||||
"media-typer": "0.3.0",
|
||||
"jsonata": "1.6.4",
|
||||
"media-typer": "1.0.1",
|
||||
"memorystore": "1.6.0",
|
||||
"mime": "1.4.1",
|
||||
"mime": "2.4.0",
|
||||
"mqtt": "2.18.8",
|
||||
"multer": "1.3.1",
|
||||
"mustache": "2.3.2",
|
||||
"node-red-node-email": "0.1.*",
|
||||
"node-red-node-feedparser": "^0.1.12",
|
||||
"multer": "1.4.1",
|
||||
"mustache": "3.0.1",
|
||||
"node-red-node-email": "1.0.*",
|
||||
"node-red-node-feedparser": "^0.1.14",
|
||||
"node-red-node-rbe": "0.2.*",
|
||||
"node-red-node-sentiment": "^0.1.0",
|
||||
"node-red-node-tail": "^0.0.2",
|
||||
"node-red-node-twitter": "^1.1.0",
|
||||
"nopt": "4.0.1",
|
||||
"oauth2orize": "1.11.0",
|
||||
@@ -64,21 +66,19 @@
|
||||
"passport-oauth2-client-password": "0.1.2",
|
||||
"raw-body": "2.3.3",
|
||||
"request": "2.88.0",
|
||||
"semver": "5.5.1",
|
||||
"sentiment": "2.1.0",
|
||||
"semver": "5.6.0",
|
||||
"uglify-js": "3.4.9",
|
||||
"when": "3.7.8",
|
||||
"ws": "1.1.5",
|
||||
"ws": "6.1.3",
|
||||
"xml2js": "0.4.19"
|
||||
},
|
||||
"optionalDependencies": {
|
||||
"bcrypt": "~2.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"chromedriver": "^2.41.0",
|
||||
"grunt": "~1.0.3",
|
||||
"grunt-chmod": "~1.1.1",
|
||||
"grunt-cli": "~1.3.1",
|
||||
"grunt-cli": "~1.3.2",
|
||||
"grunt-concurrent": "~2.3.1",
|
||||
"grunt-contrib-clean": "~1.1.0",
|
||||
"grunt-contrib-compress": "~1.4.0",
|
||||
@@ -90,8 +90,10 @@
|
||||
"grunt-jsdoc": "^2.2.1",
|
||||
"grunt-jsdoc-to-markdown": "^4.0.0",
|
||||
"grunt-jsonlint": "~1.1.0",
|
||||
"grunt-mkdir": "~1.0.0",
|
||||
"grunt-mocha-istanbul": "5.0.2",
|
||||
"grunt-nodemon": "~0.4.2",
|
||||
"grunt-npm-command": "~0.1.2",
|
||||
"grunt-sass": "~2.0.0",
|
||||
"grunt-simple-mocha": "~0.4.1",
|
||||
"grunt-webdriver": "^2.0.3",
|
||||
@@ -99,14 +101,15 @@
|
||||
"istanbul": "0.4.5",
|
||||
"minami": "1.2.3",
|
||||
"mocha": "^5.2.0",
|
||||
"mosca": "^2.8.3",
|
||||
"should": "^8.4.0",
|
||||
"sinon": "1.17.7",
|
||||
"stoppable": "^1.0.6",
|
||||
"supertest": "3.1.0",
|
||||
"wdio-chromedriver-service": "^0.1.3",
|
||||
"wdio-mocha-framework": "^0.6.2",
|
||||
"stoppable": "^1.1.0",
|
||||
"supertest": "3.4.2",
|
||||
"wdio-chromedriver-service": "^0.1.5",
|
||||
"wdio-mocha-framework": "^0.6.4",
|
||||
"wdio-spec-reporter": "^0.1.5",
|
||||
"webdriverio": "^4.13.1",
|
||||
"webdriverio": "^4.14.1",
|
||||
"node-red-node-test-helper": "node-red/node-red-node-test-helper",
|
||||
"jsdoc-nr-template": "node-red/jsdoc-nr-template"
|
||||
},
|
||||
|
2
packages/node_modules/@node-red/editor-api/.npmignore
vendored
Normal file
2
packages/node_modules/@node-red/editor-api/.npmignore
vendored
Normal file
@@ -0,0 +1,2 @@
|
||||
src
|
||||
docs
|
@@ -37,5 +37,20 @@ module.exports = {
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
},
|
||||
|
||||
delete: function(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
scope: req.params.scope,
|
||||
id: req.params.id,
|
||||
key: req.params[0],
|
||||
store: req.query['store']
|
||||
}
|
||||
runtimeAPI.context.delete(opts).then(function(result) {
|
||||
res.status(204).end();
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@@ -62,6 +62,11 @@ module.exports = {
|
||||
adminApp.get("/context/:scope(node|flow)/:id",needsPermission("context.read"),context.get,apiUtil.errorHandler);
|
||||
adminApp.get("/context/:scope(node|flow)/:id/*",needsPermission("context.read"),context.get,apiUtil.errorHandler);
|
||||
|
||||
// adminApp.delete("/context/:scope(global)",needsPermission("context.write"),context.delete,apiUtil.errorHandler);
|
||||
adminApp.delete("/context/:scope(global)/*",needsPermission("context.write"),context.delete,apiUtil.errorHandler);
|
||||
// adminApp.delete("/context/:scope(node|flow)/:id",needsPermission("context.write"),context.delete,apiUtil.errorHandler);
|
||||
adminApp.delete("/context/:scope(node|flow)/:id/*",needsPermission("context.write"),context.delete,apiUtil.errorHandler);
|
||||
|
||||
return adminApp;
|
||||
}
|
||||
}
|
||||
|
@@ -14,6 +14,11 @@
|
||||
* limitations under the License.
|
||||
**/
|
||||
|
||||
|
||||
/**
|
||||
* @mixin @node-red/editor-api_auth
|
||||
*/
|
||||
|
||||
var passport = require("passport");
|
||||
var oauth2orize = require("oauth2orize");
|
||||
|
||||
@@ -39,11 +44,19 @@ server.exchange(oauth2orize.exchange.password(strategies.passwordTokenExchange))
|
||||
function init(_settings,storage) {
|
||||
settings = _settings;
|
||||
if (settings.adminAuth) {
|
||||
Users.init(settings.adminAuth);
|
||||
Tokens.init(settings.adminAuth,storage);
|
||||
var mergedAdminAuth = Object.assign({}, settings.adminAuth, settings.adminAuth.module);
|
||||
Users.init(mergedAdminAuth);
|
||||
Tokens.init(mergedAdminAuth,storage);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns an Express middleware function that ensures the user making a request
|
||||
* has the necessary permission.
|
||||
*
|
||||
* @param {String} permission - the permission required for the request, such as `flows.write`
|
||||
* @return {Function} - an Express middleware
|
||||
* @memberof @node-red/editor-api_auth
|
||||
*/
|
||||
function needsPermission(permission) {
|
||||
return function(req,res,next) {
|
||||
if (settings && settings.adminAuth) {
|
||||
@@ -79,23 +92,24 @@ function getToken(req,res,next) {
|
||||
function login(req,res) {
|
||||
var response = {};
|
||||
if (settings.adminAuth) {
|
||||
if (settings.adminAuth.type === "credentials") {
|
||||
var mergedAdminAuth = Object.assign({}, settings.adminAuth, settings.adminAuth.module);
|
||||
if (mergedAdminAuth.type === "credentials") {
|
||||
response = {
|
||||
"type":"credentials",
|
||||
"prompts":[{id:"username",type:"text",label:"user.username"},{id:"password",type:"password",label:"user.password"}]
|
||||
}
|
||||
} else if (settings.adminAuth.type === "strategy") {
|
||||
} else if (mergedAdminAuth.type === "strategy") {
|
||||
|
||||
var urlPrefix = (settings.httpAdminRoot==='/')?"":settings.httpAdminRoot;
|
||||
response = {
|
||||
"type":"strategy",
|
||||
"prompts":[{type:"button",label:settings.adminAuth.strategy.label, url: urlPrefix + "auth/strategy"}]
|
||||
"prompts":[{type:"button",label:mergedAdminAuth.strategy.label, url: urlPrefix + "auth/strategy"}]
|
||||
}
|
||||
if (settings.adminAuth.strategy.icon) {
|
||||
response.prompts[0].icon = settings.adminAuth.strategy.icon;
|
||||
if (mergedAdminAuth.strategy.icon) {
|
||||
response.prompts[0].icon = mergedAdminAuth.strategy.icon;
|
||||
}
|
||||
if (settings.adminAuth.strategy.image) {
|
||||
response.prompts[0].image = theme.serveFile('/login/',settings.adminAuth.strategy.image);
|
||||
if (mergedAdminAuth.strategy.image) {
|
||||
response.prompts[0].image = theme.serveFile('/login/',mergedAdminAuth.strategy.image);
|
||||
}
|
||||
}
|
||||
if (theme.context().login && theme.context().login.image) {
|
||||
@@ -180,7 +194,12 @@ function genericStrategy(adminApp,strategy) {
|
||||
passport.authenticate(strategy.name, {session:false, failureRedirect: settings.httpAdminRoot }),
|
||||
completeGenerateStrategyAuth
|
||||
);
|
||||
adminApp.get('/auth/strategy/callback',
|
||||
|
||||
var callbackMethodFunc = adminApp.get;
|
||||
if (/^post$/i.test(options.callbackMethod)) {
|
||||
callbackMethodFunc = adminApp.post;
|
||||
}
|
||||
callbackMethodFunc('/auth/strategy/callback',
|
||||
passport.authenticate(strategy.name, {session:false, failureRedirect: settings.httpAdminRoot }),
|
||||
completeGenerateStrategyAuth
|
||||
);
|
||||
|
@@ -25,25 +25,39 @@ function generateToken(length) {
|
||||
|
||||
|
||||
var storage;
|
||||
|
||||
var sessionExpiryTime
|
||||
|
||||
var sessions = {};
|
||||
|
||||
var loadedSessions = null;
|
||||
var apiAccessTokens;
|
||||
var sessionExpiryListeners = [];
|
||||
var expiryTimeout;
|
||||
|
||||
function expireSessions() {
|
||||
if (expiryTimeout) {
|
||||
clearTimeout(expiryTimeout);
|
||||
expiryTimeout = null;
|
||||
}
|
||||
var nextExpiry = Number.MAX_SAFE_INTEGER;
|
||||
var now = Date.now();
|
||||
var modified = false;
|
||||
for (var t in sessions) {
|
||||
if (sessions.hasOwnProperty(t)) {
|
||||
var session = sessions[t];
|
||||
if (!session.hasOwnProperty("expires") || session.expires < now) {
|
||||
sessionExpiryListeners.forEach(listener => { listener(session) })
|
||||
delete sessions[t];
|
||||
modified = true;
|
||||
} else {
|
||||
if (session.expires < nextExpiry) {
|
||||
nextExpiry = session.expires;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (nextExpiry < Number.MAX_SAFE_INTEGER) {
|
||||
// Allow 5 seconds grace
|
||||
expiryTimeout = setTimeout(expireSessions,(nextExpiry - Date.now()) + 5000)
|
||||
}
|
||||
if (modified) {
|
||||
return storage.saveSessions(sessions);
|
||||
} else {
|
||||
@@ -63,20 +77,40 @@ function loadSessions() {
|
||||
module.exports = {
|
||||
init: function(adminAuthSettings, _storage) {
|
||||
storage = _storage;
|
||||
|
||||
sessionExpiryListeners = [];
|
||||
|
||||
sessionExpiryTime = adminAuthSettings.sessionExpiryTime || 604800; // 1 week in seconds
|
||||
// At this point, storage will not have been initialised, so defer loading
|
||||
// the sessions until there's a request for them.
|
||||
loadedSessions = null;
|
||||
|
||||
apiAccessTokens = {};
|
||||
if ( Array.isArray(adminAuthSettings.tokens) ) {
|
||||
apiAccessTokens = adminAuthSettings.tokens.reduce(function(prev, current) {
|
||||
prev[current.token] = {
|
||||
user: current.user,
|
||||
scope: current.scope
|
||||
};
|
||||
return prev;
|
||||
}, {});
|
||||
}
|
||||
return Promise.resolve();
|
||||
},
|
||||
get: function(token) {
|
||||
return loadSessions().then(function() {
|
||||
if (sessions[token]) {
|
||||
if (sessions[token].expires < Date.now()) {
|
||||
return expireSessions().then(function() { return null });
|
||||
var info = apiAccessTokens[token] || null;
|
||||
|
||||
if (info) {
|
||||
return Promise.resolve(info);
|
||||
} else {
|
||||
if (sessions[token]) {
|
||||
if (sessions[token].expires < Date.now()) {
|
||||
return expireSessions().then(function() { return null });
|
||||
}
|
||||
}
|
||||
return Promise.resolve(sessions[token]);
|
||||
}
|
||||
return Promise.resolve(sessions[token]);
|
||||
});
|
||||
},
|
||||
create: function(user,client,scope) {
|
||||
@@ -93,6 +127,11 @@ module.exports = {
|
||||
expires: accessTokenExpiresAt
|
||||
};
|
||||
sessions[accessToken] = session;
|
||||
|
||||
if (!expiryTimeout) {
|
||||
expiryTimeout = setTimeout(expireSessions,(accessTokenExpiresAt - Date.now()) + 5000)
|
||||
}
|
||||
|
||||
return storage.saveSessions(sessions).then(function() {
|
||||
return {
|
||||
accessToken: accessToken,
|
||||
@@ -106,5 +145,8 @@ module.exports = {
|
||||
delete sessions[token];
|
||||
return storage.saveSessions(sessions);
|
||||
});
|
||||
},
|
||||
onSessionExpiry: function(callback) {
|
||||
sessionExpiryListeners.push(callback);
|
||||
}
|
||||
}
|
||||
|
@@ -15,6 +15,7 @@
|
||||
**/
|
||||
|
||||
var ws = require("ws");
|
||||
var url = require("url");
|
||||
|
||||
var log = require("@node-red/util").log; // TODO: separate module
|
||||
var Tokens;
|
||||
@@ -40,11 +41,19 @@ function init(_server,_settings,_runtimeAPI) {
|
||||
settings = _settings;
|
||||
runtimeAPI = _runtimeAPI;
|
||||
Tokens = require("../auth/tokens");
|
||||
Tokens.onSessionExpiry(handleSessionExpiry);
|
||||
Users = require("../auth/users");
|
||||
Permissions = require("../auth/permissions");
|
||||
|
||||
}
|
||||
|
||||
function handleSessionExpiry(session) {
|
||||
activeConnections.forEach(connection => {
|
||||
if (connection.token === session.accessToken) {
|
||||
connection.ws.send(JSON.stringify({auth:"fail"}));
|
||||
connection.ws.close();
|
||||
}
|
||||
})
|
||||
}
|
||||
function generateSession(length) {
|
||||
var c = "ABCDEFGHIJKLMNOPQRSTUZWXYZabcdefghijklmnopqrstuvwxyz1234567890";
|
||||
var token = [];
|
||||
@@ -88,7 +97,7 @@ function CommsConnection(ws) {
|
||||
// handleRemoteSubscription(ws,msg.subscribe);
|
||||
}
|
||||
} else {
|
||||
var completeConnection = function(userScope,sendAck) {
|
||||
var completeConnection = function(userScope,session,sendAck) {
|
||||
try {
|
||||
if (!userScope || !Permissions.hasPermission(userScope,"status.read")) {
|
||||
ws.send(JSON.stringify({auth:"fail"}));
|
||||
@@ -96,6 +105,7 @@ function CommsConnection(ws) {
|
||||
} else {
|
||||
pendingAuth = false;
|
||||
addActiveConnection(self);
|
||||
self.token = msg.auth;
|
||||
if (sendAck) {
|
||||
ws.send(JSON.stringify({auth:"ok"}));
|
||||
}
|
||||
@@ -113,29 +123,29 @@ function CommsConnection(ws) {
|
||||
if (user) {
|
||||
self.user = user;
|
||||
log.audit({event: "comms.auth",user:self.user});
|
||||
completeConnection(client.scope,true);
|
||||
completeConnection(client.scope,msg.auth,true);
|
||||
} else {
|
||||
log.audit({event: "comms.auth.fail"});
|
||||
completeConnection(null,false);
|
||||
completeConnection(null,null,false);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
log.audit({event: "comms.auth.fail"});
|
||||
completeConnection(null,false);
|
||||
completeConnection(null,null,false);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
if (anonymousUser) {
|
||||
log.audit({event: "comms.auth",user:anonymousUser});
|
||||
self.user = anonymousUser;
|
||||
completeConnection(anonymousUser.permissions,false);
|
||||
completeConnection(anonymousUser.permissions,null,false);
|
||||
//TODO: duplicated code - pull non-auth message handling out
|
||||
if (msg.subscribe) {
|
||||
self.subscribe(msg.subscribe);
|
||||
}
|
||||
} else {
|
||||
log.audit({event: "comms.auth.fail"});
|
||||
completeConnection(null,false);
|
||||
completeConnection(null,null,false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -178,27 +188,27 @@ function start() {
|
||||
Users.default().then(function(_anonymousUser) {
|
||||
anonymousUser = _anonymousUser;
|
||||
var webSocketKeepAliveTime = settings.webSocketKeepAliveTime || 15000;
|
||||
var path = settings.httpAdminRoot || "/";
|
||||
path = (path.slice(0,1) != "/" ? "/":"") + path + (path.slice(-1) == "/" ? "":"/") + "comms";
|
||||
wsServer = new ws.Server({
|
||||
server:server,
|
||||
path:path,
|
||||
// Disable the deflate option due to this issue
|
||||
// https://github.com/websockets/ws/pull/632
|
||||
// that is fixed in the 1.x release of the ws module
|
||||
// that we cannot currently pickup as it drops node 0.10 support
|
||||
//perMessageDeflate: false
|
||||
});
|
||||
|
||||
var commsPath = settings.httpAdminRoot || "/";
|
||||
commsPath = (commsPath.slice(0,1) != "/" ? "/":"") + commsPath + (commsPath.slice(-1) == "/" ? "":"/") + "comms";
|
||||
wsServer = new ws.Server({ noServer: true });
|
||||
wsServer.on('connection',function(ws) {
|
||||
var commsConnection = new CommsConnection(ws);
|
||||
});
|
||||
|
||||
|
||||
wsServer.on('error', function(err) {
|
||||
log.warn(log._("comms.error-server",{message:err.toString()}));
|
||||
});
|
||||
|
||||
server.on('upgrade', function upgrade(request, socket, head) {
|
||||
const pathname = url.parse(request.url).pathname;
|
||||
if (pathname === commsPath) {
|
||||
wsServer.handleUpgrade(request, socket, head, function done(ws) {
|
||||
wsServer.emit('connection', ws, request);
|
||||
});
|
||||
}
|
||||
// Don't destroy the socket as other listeners may want to handle the
|
||||
// event.
|
||||
});
|
||||
|
||||
lastSentTime = Date.now();
|
||||
|
||||
heartbeatTimer = setInterval(function() {
|
||||
|
@@ -64,6 +64,11 @@ module.exports = {
|
||||
}
|
||||
});
|
||||
}
|
||||
if (settings.httpServerOptions) {
|
||||
for (var eOption in settings.httpServerOptions) {
|
||||
editorApp.set(eOption, settings.httpServerOptions[eOption]);
|
||||
}
|
||||
}
|
||||
editorApp.get("/",ensureRuntimeStarted,ui.ensureSlash,ui.editor);
|
||||
|
||||
editorApp.get("/icons",needsPermission("nodes.read"),nodes.getIcons,apiUtil.errorHandler);
|
||||
@@ -111,7 +116,7 @@ module.exports = {
|
||||
}
|
||||
},
|
||||
start: function() {
|
||||
var catalogPath = path.resolve(path.join(__dirname,"locales"));
|
||||
var catalogPath = path.resolve(path.join(path.dirname(require.resolve("@node-red/editor-client")),"locales"));
|
||||
return i18n.registerMessageCatalogs([
|
||||
{namespace: "editor", dir: catalogPath, file:"editor.json"},
|
||||
{namespace: "jsonata", dir: catalogPath, file:"jsonata.json"},
|
||||
|
@@ -21,6 +21,18 @@ var i18n = require("@node-red/util").i18n; // TODO: separate module
|
||||
|
||||
var runtimeAPI;
|
||||
|
||||
function loadResource(lang, namespace) {
|
||||
var catalog = i18n.i.getResourceBundle(lang, namespace);
|
||||
if (!catalog) {
|
||||
var parts = lang.split("-");
|
||||
if (parts.length == 2) {
|
||||
var new_lang = parts[0];
|
||||
return i18n.i.getResourceBundle(new_lang, namespace);
|
||||
}
|
||||
}
|
||||
return catalog;
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
init: function(_runtimeAPI) {
|
||||
runtimeAPI = _runtimeAPI;
|
||||
@@ -33,7 +45,7 @@ module.exports = {
|
||||
var prevLang = i18n.i.language;
|
||||
// Trigger a load from disk of the language if it is not the default
|
||||
i18n.i.changeLanguage(lang, function(){
|
||||
var catalog = i18n.i.getResourceBundle(lang, namespace);
|
||||
var catalog = loadResource(lang, namespace);
|
||||
res.json(catalog||{});
|
||||
});
|
||||
i18n.i.changeLanguage(prevLang);
|
||||
|
@@ -20,6 +20,58 @@ var apiUtils = require("../util");
|
||||
var runtimeAPI;
|
||||
var needsPermission = require("../auth").needsPermission;
|
||||
|
||||
function listProjects(req,res) {
|
||||
var opts = {
|
||||
user: req.user
|
||||
}
|
||||
runtimeAPI.projects.listProjects(opts).then(function(result) {
|
||||
res.json(result);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
});
|
||||
}
|
||||
function getProject(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id
|
||||
}
|
||||
runtimeAPI.projects.getProject(opts).then(function(data) {
|
||||
if (data) {
|
||||
res.json(data);
|
||||
} else {
|
||||
res.status(404).end();
|
||||
}
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
}
|
||||
function getProjectStatus(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id,
|
||||
remote: req.query.remote
|
||||
}
|
||||
runtimeAPI.projects.getStatus(opts).then(function(data){
|
||||
if (data) {
|
||||
res.json(data);
|
||||
} else {
|
||||
res.status(404).end();
|
||||
}
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
}
|
||||
function getProjectRemotes(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id
|
||||
}
|
||||
runtimeAPI.projects.getRemotes(opts).then(function(data) {
|
||||
res.json(data);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
}
|
||||
module.exports = {
|
||||
init: function(_runtimeAPI) {
|
||||
runtimeAPI = _runtimeAPI;
|
||||
@@ -40,16 +92,7 @@ module.exports = {
|
||||
// Projects
|
||||
|
||||
// List all projects
|
||||
app.get("/", needsPermission("projects.read"), function(req,res) {
|
||||
var opts = {
|
||||
user: req.user
|
||||
}
|
||||
runtimeAPI.projects.listProjects(opts).then(function(result) {
|
||||
res.json(result);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
});
|
||||
});
|
||||
app.get("/", needsPermission("projects.read"),listProjects);
|
||||
|
||||
// Create project
|
||||
app.post("/", needsPermission("projects.write"), function(req,res) {
|
||||
@@ -74,13 +117,13 @@ module.exports = {
|
||||
|
||||
if (req.body.active) {
|
||||
runtimeAPI.projects.setActiveProject(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl + '/');
|
||||
listProjects(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
} else if (req.body.initialise) {
|
||||
runtimeAPI.projects.initialiseProject(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl + '/'+ req.params.id);
|
||||
getProject(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -91,7 +134,7 @@ module.exports = {
|
||||
req.body.hasOwnProperty('files') ||
|
||||
req.body.hasOwnProperty('git')) {
|
||||
runtimeAPI.projects.updateProject(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl + '/'+ req.params.id);
|
||||
getProject(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -101,21 +144,7 @@ module.exports = {
|
||||
});
|
||||
|
||||
// Get project metadata
|
||||
app.get("/:id", needsPermission("projects.read"), function(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id
|
||||
}
|
||||
runtimeAPI.projects.getProject(opts).then(function(data) {
|
||||
if (data) {
|
||||
res.json(data);
|
||||
} else {
|
||||
res.status(404).end();
|
||||
}
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
});
|
||||
app.get("/:id", needsPermission("projects.read"), getProject);
|
||||
|
||||
// Delete project
|
||||
app.delete("/:id", needsPermission("projects.write"), function(req,res) {
|
||||
@@ -132,22 +161,7 @@ module.exports = {
|
||||
|
||||
|
||||
// Get project status - files, commit counts, branch info
|
||||
app.get("/:id/status", needsPermission("projects.read"), function(req,res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id,
|
||||
remote: req.query.remote
|
||||
}
|
||||
runtimeAPI.projects.getStatus(opts).then(function(data){
|
||||
if (data) {
|
||||
res.json(data);
|
||||
} else {
|
||||
res.status(404).end();
|
||||
}
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
});
|
||||
app.get("/:id/status", needsPermission("projects.read"), getProjectStatus);
|
||||
|
||||
|
||||
// Project file listing
|
||||
@@ -203,7 +217,7 @@ module.exports = {
|
||||
path: req.params[0]
|
||||
}
|
||||
runtimeAPI.projects.stageFile(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/status");
|
||||
getProjectStatus(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -217,7 +231,7 @@ module.exports = {
|
||||
path: req.body.files
|
||||
}
|
||||
runtimeAPI.projects.stageFile(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/status");
|
||||
getProjectStatus(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -231,7 +245,7 @@ module.exports = {
|
||||
message: req.body.message
|
||||
}
|
||||
runtimeAPI.projects.commit(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/status");
|
||||
getProjectStatus(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -245,7 +259,7 @@ module.exports = {
|
||||
path: req.params[0]
|
||||
}
|
||||
runtimeAPI.projects.unstageFile(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/status");
|
||||
getProjectStatus(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -258,7 +272,7 @@ module.exports = {
|
||||
id: req.params.id
|
||||
}
|
||||
runtimeAPI.projects.unstageFile(opts).then(function() {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/status");
|
||||
getProjectStatus(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -442,17 +456,7 @@ module.exports = {
|
||||
});
|
||||
|
||||
// Get a list of remotes
|
||||
app.get("/:id/remotes", needsPermission("projects.read"), function(req, res) {
|
||||
var opts = {
|
||||
user: req.user,
|
||||
id: req.params.id
|
||||
}
|
||||
runtimeAPI.projects.getRemotes(opts).then(function(data) {
|
||||
res.json(data);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
});
|
||||
app.get("/:id/remotes", needsPermission("projects.read"), getProjectRemotes);
|
||||
|
||||
// Add a remote
|
||||
app.post("/:id/remotes", needsPermission("projects.write"), function(req,res) {
|
||||
@@ -466,7 +470,7 @@ module.exports = {
|
||||
return;
|
||||
}
|
||||
runtimeAPI.projects.addRemote(opts).then(function(data) {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/remotes");
|
||||
getProjectRemotes(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
@@ -480,7 +484,7 @@ module.exports = {
|
||||
remote: req.params.remoteName
|
||||
}
|
||||
runtimeAPI.projects.removeRemote(opts).then(function(data) {
|
||||
res.redirect(303,req.baseUrl+"/"+opts.id+"/remotes");
|
||||
getProjectRemotes(req,res);
|
||||
}).catch(function(err) {
|
||||
apiUtils.rejectHandler(req,res,err);
|
||||
})
|
||||
|
@@ -17,6 +17,31 @@ var apiUtils = require("../util");
|
||||
var runtimeAPI;
|
||||
var sshkeys = require("./sshkeys");
|
||||
var theme = require("./theme");
|
||||
var clone = require("clone");
|
||||
|
||||
function extend(target, source) {
|
||||
var keys = Object.keys(source);
|
||||
var i = keys.length;
|
||||
while(i--) {
|
||||
var value = source[keys[i]]
|
||||
var type = typeof value;
|
||||
if (type === 'string' || type === 'number' || type === 'boolean' || Array.isArray(value)) {
|
||||
target[keys[i]] = value;
|
||||
} else if (value === null) {
|
||||
if (target.hasOwnProperty(keys[i])) {
|
||||
delete target[keys[i]];
|
||||
}
|
||||
} else {
|
||||
// Object
|
||||
if (target.hasOwnProperty(keys[i])) {
|
||||
target[keys[i]] = extend(target[keys[i]],value);
|
||||
} else {
|
||||
target[keys[i]] = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
return target;
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
init: function(_runtimeAPI) {
|
||||
@@ -30,7 +55,9 @@ module.exports = {
|
||||
runtimeAPI.settings.getRuntimeSettings(opts).then(function(result) {
|
||||
var themeSettings = theme.settings();
|
||||
if (themeSettings) {
|
||||
result.editorTheme = themeSettings;
|
||||
// result.editorTheme may already exist with the palette
|
||||
// disabled. Need to merge that into the receive settings
|
||||
result.editorTheme = extend(clone(themeSettings),result.editorTheme||{});
|
||||
}
|
||||
res.json(result);
|
||||
});
|
||||
|
@@ -57,7 +57,7 @@ module.exports = {
|
||||
}
|
||||
runtimeAPI.nodes.getIcon(opts).then(function(data) {
|
||||
if (data) {
|
||||
var contentType = mime.lookup(icon);
|
||||
var contentType = mime.getType(icon);
|
||||
res.set("Content-Type", contentType);
|
||||
res.send(data);
|
||||
} else {
|
||||
|
@@ -14,6 +14,16 @@
|
||||
* limitations under the License.
|
||||
**/
|
||||
|
||||
|
||||
/**
|
||||
* This module provides an Express application to serve the Node-RED editor.
|
||||
*
|
||||
* It implements the Node-RED HTTP Admin API the Editor uses to interact
|
||||
* with the Node-RED runtime.
|
||||
*
|
||||
* @namespace @node-red/editor-api
|
||||
*/
|
||||
|
||||
var express = require("express");
|
||||
var bodyParser = require("body-parser");
|
||||
var util = require('util');
|
||||
@@ -28,7 +38,16 @@ var adminApp;
|
||||
var server;
|
||||
var editor;
|
||||
|
||||
function init(_server,settings,storage,runtimeAPI) {
|
||||
|
||||
/**
|
||||
* Initialise the module.
|
||||
* @param {Object} settings The runtime settings
|
||||
* @param {HTTPServer} server An instance of HTTP Server
|
||||
* @param {Storage} storage An instance of Node-RED Storage
|
||||
* @param {Runtime} runtimeAPI An instance of Node-RED Runtime
|
||||
* @memberof @node-red/editor-api
|
||||
*/
|
||||
function init(settings,_server,storage,runtimeAPI) {
|
||||
server = _server;
|
||||
if (settings.httpAdminRoot !== false) {
|
||||
adminApp = express();
|
||||
@@ -80,6 +99,12 @@ function init(_server,settings,storage,runtimeAPI) {
|
||||
adminApp = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Start the module.
|
||||
* @return {Promise} resolves when the application is ready to handle requests
|
||||
* @memberof @node-red/editor-api
|
||||
*/
|
||||
function start() {
|
||||
if (editor) {
|
||||
return editor.start();
|
||||
@@ -87,6 +112,12 @@ function start() {
|
||||
return when.resolve();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Stop the module.
|
||||
* @return {Promise} resolves when the application is stopped
|
||||
* @memberof @node-red/editor-api
|
||||
*/
|
||||
function stop() {
|
||||
if (editor) {
|
||||
editor.stop();
|
||||
@@ -97,9 +128,18 @@ module.exports = {
|
||||
init: init,
|
||||
start: start,
|
||||
stop: stop,
|
||||
|
||||
/**
|
||||
* @memberof @node-red/editor-api
|
||||
* @mixes @node-red/editor-api_auth
|
||||
*/
|
||||
auth: {
|
||||
needsPermission: auth.needsPermission
|
||||
},
|
||||
get adminApp() { return adminApp; },
|
||||
get server() { return server; }
|
||||
/**
|
||||
* The Express app used to serve the Node-RED Editor
|
||||
* @type ExpressApplication
|
||||
* @memberof @node-red/editor-api
|
||||
*/
|
||||
get httpAdmin() { return adminApp; }
|
||||
};
|
||||
|
@@ -21,6 +21,8 @@ var i18n = require("@node-red/util").i18n; // TODO: separate module
|
||||
|
||||
module.exports = {
|
||||
errorHandler: function(err,req,res,next) {
|
||||
//TODO: why this when rejectHandler also?!
|
||||
|
||||
if (err.message === "request entity too large") {
|
||||
log.error(err);
|
||||
} else {
|
||||
@@ -39,7 +41,9 @@ module.exports = {
|
||||
return lang;
|
||||
},
|
||||
rejectHandler: function(req,res,err) {
|
||||
res.status(err.status||500).json({
|
||||
//TODO: why this when errorHandler also?!
|
||||
log.audit({event: "api.error",error:err.code||"unexpected_error",message:err.message||err.toString()},req);
|
||||
res.status(err.status||400).json({
|
||||
code: err.code||"unexpected_error",
|
||||
message: err.message||err.toString()
|
||||
});
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@node-red/editor",
|
||||
"version": "0.20.0-alpha.0",
|
||||
"name": "@node-red/editor-api",
|
||||
"version": "0.20.0-beta.4",
|
||||
"license": "Apache-2.0",
|
||||
"main": "./lib/index.js",
|
||||
"repository": {
|
||||
@@ -8,26 +8,30 @@
|
||||
"url": "https://github.com/node-red/node-red.git"
|
||||
},
|
||||
"contributors": [
|
||||
{ "name": "Nick O'Leary" },
|
||||
{ "name": "Dave Conway-Jones"}
|
||||
{
|
||||
"name": "Nick O'Leary"
|
||||
},
|
||||
{
|
||||
"name": "Dave Conway-Jones"
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"@node-red/util": "*",
|
||||
"@node-red/editor-client": "*",
|
||||
"@node-red/util": "0.20.0-beta.4",
|
||||
"@node-red/editor-client": "0.20.0-beta.4",
|
||||
"bcryptjs": "2.4.3",
|
||||
"body-parser": "1.18.3",
|
||||
"clone": "2.1.2",
|
||||
"cors": "2.8.4",
|
||||
"cors": "2.8.5",
|
||||
"express-session": "1.15.6",
|
||||
"express": "4.16.3",
|
||||
"express": "4.16.4",
|
||||
"memorystore": "1.6.0",
|
||||
"mime": "1.4.1",
|
||||
"mustache": "2.3.2",
|
||||
"mime": "2.4.0",
|
||||
"mustache": "3.0.1",
|
||||
"oauth2orize": "1.11.0",
|
||||
"passport-http-bearer": "1.0.1",
|
||||
"passport-oauth2-client-password": "0.1.2",
|
||||
"passport": "0.4.0",
|
||||
"when": "3.7.8",
|
||||
"ws": "1.1.5"
|
||||
"ws": "6.1.3"
|
||||
}
|
||||
}
|
||||
|
@@ -1 +1,2 @@
|
||||
src
|
||||
docs
|
||||
|
829
packages/node_modules/@node-red/editor-client/locales/de/editor.json
vendored
Executable file
829
packages/node_modules/@node-red/editor-client/locales/de/editor.json
vendored
Executable file
@@ -0,0 +1,829 @@
|
||||
{
|
||||
"common" : {
|
||||
"label" : {
|
||||
"name" : "Name",
|
||||
"ok" : "OK",
|
||||
"done" : "Fertig",
|
||||
"cancel" : "Abbrechen",
|
||||
"delete" : "Löschen",
|
||||
"close" : "Schließen",
|
||||
"load" : "Laden",
|
||||
"save" : "Speichern",
|
||||
"import" : "Import",
|
||||
"export" : "Exportieren",
|
||||
"back" : "Zurück",
|
||||
"next" : "Weiter",
|
||||
"clone" : "Projekt duplizieren",
|
||||
"cont" : "Weiter"
|
||||
}
|
||||
},
|
||||
"workspace" : {
|
||||
"defaultName" : "Flow __number__",
|
||||
"editFlow" : "Flow bearbeiten: __name__",
|
||||
"confirmDelete" : "Löschen bestätigen",
|
||||
"delete" : "Sind Sie wirklich sicher, dass Sie '__label__' löschen wollen?",
|
||||
"dropFlowHere" : "Hier können Sie den Flow fallen lassen.",
|
||||
"status" : "Status",
|
||||
"enabled" : "Aktiviert",
|
||||
"disabled" : "Inaktiviert",
|
||||
"info" : "Beschreibung",
|
||||
"tip" : "Beschreibung akzeptiert Markdown und wird auf der Registerkarte Info angezeigt."
|
||||
},
|
||||
"menu" : {
|
||||
"label" : {
|
||||
"view" : {
|
||||
"view" : "Ansicht",
|
||||
"grid" : "Gitter",
|
||||
"showGrid" : "Raster anzeigen",
|
||||
"snapGrid" : "Einrasten am Raster",
|
||||
"gridSize" : "Rastergröße",
|
||||
"textDir" : "Textrichtung",
|
||||
"defaultDir" : "Standard",
|
||||
"ltr" : "Links-nach-rechts",
|
||||
"rtl" : "Von rechts nach links",
|
||||
"auto" : "Kontextuell"
|
||||
},
|
||||
"sidebar" : {
|
||||
"show" : "Seitenleiste anzeigen"
|
||||
},
|
||||
"settings" : "Einstellungen",
|
||||
"userSettings" : "Benutzereinstellungen",
|
||||
"nodes" : "Knoten",
|
||||
"displayStatus" : "Knotenstatus anzeigen",
|
||||
"displayConfig" : "Konfigurationsknoten",
|
||||
"import" : "Import",
|
||||
"export" : "Exportieren",
|
||||
"search" : "Flows durchsuchen",
|
||||
"searchInput" : "durchsuchen Sie Ihre Flows",
|
||||
"clipboard" : "Zwischenablage",
|
||||
"library" : "Bibliothek",
|
||||
"examples" : "Beispiele",
|
||||
"subflows" : "Subflow",
|
||||
"createSubflow" : "Subflow erstellen",
|
||||
"selectionToSubflow" : "Auswahl für Subflow",
|
||||
"flows" : "Flows",
|
||||
"add" : "Hinzufügen",
|
||||
"rename" : "Umbenennen",
|
||||
"delete" : "Löschen",
|
||||
"keyboardShortcuts" : "Tastaturkurzbefehle",
|
||||
"login" : "Anmelden",
|
||||
"logout" : "Abmelden",
|
||||
"editPalette" : "Palette verwalten",
|
||||
"other" : "Sonstige",
|
||||
"showTips" : "Tipps anzeigen",
|
||||
"help" : "Node-RED-Website",
|
||||
"projects" : "Projekte",
|
||||
"projects-new" : "Neu",
|
||||
"projects-open" : "Öffnen",
|
||||
"projects-settings" : "Projekteinstellungen"
|
||||
}
|
||||
},
|
||||
"user" : {
|
||||
"loggedInAs" : "Angemeldet als __name__",
|
||||
"username" : "Benutzername",
|
||||
"password" : "Kennwort",
|
||||
"login" : "Anmelden",
|
||||
"loginFailed" : "Anmeldung fehlgeschlagen",
|
||||
"notAuthorized" : "Keine Berechtigung",
|
||||
"errors" : {
|
||||
"settings" : "Sie müssen angemeldet sein, um auf die Einstellungen zuzugreifen.",
|
||||
"deploy" : "Sie müssen angemeldet sein, um Änderungen implementieren zu können.",
|
||||
"notAuthorized" : "Sie müssen angemeldet sein, um diese Aktion ausführen zu können."
|
||||
}
|
||||
},
|
||||
"notification" : {
|
||||
"warning" : "<strong> Warnung </strong>: __message__",
|
||||
"warnings" : {
|
||||
"undeployedChanges" : "Knoten hat nicht implementierte Änderungen",
|
||||
"nodeActionDisabled" : "In Subflow inaktivierte Knotenaktionen",
|
||||
"missing-types" : "<p> Die Flows wurden aufgrund fehlender Knotentypen gestoppt. </p>",
|
||||
"restartRequired" : "Knoten-RED muss erneut gestartet werden, damit aufgerüstete Module aktiviert werden können",
|
||||
"credentials_load_failed" : "<p> Die Flows wurden gestoppt, da die Berechtigungsnachweise nicht entschlüsselt werden konnten. </p> <p> Die Datei mit dem Datenflowberechtigungsnachweis ist verschlüsselt, aber der Verschlüsselungsschlüssel des Projekts fehlt oder ist ungültig. </p>",
|
||||
"credentials_load_failed_reset" : "<p> Die Berechtigungsnachweise konnten nicht entschlüsselt werden </p> <p> Die Datei mit dem Flow-Berechtigungsnachweis ist verschlüsselt, aber der Chiffrierschlüssel des Projekts fehlt oder ist ungültig. </p> <p> Die Datei des Flow-Berechtigungsnachweises wird bei der nächsten Implementierung zurückgesetzt. Alle vorhandenen Datenflowberechtigungsnachweise werden gelöscht. </p>",
|
||||
"missing_flow_file" : "<p> Die Projektflowdatei wurde nicht gefunden. </p> <p> Das Projekt ist nicht mit einer Flow-Datei konfiguriert. </p>",
|
||||
"missing_package_file" : "<p> Die Projektpaketdatei wurde nicht gefunden. </p> <p> In dem Projekt fehlt eine Datei 'package.json'. </p>",
|
||||
"project_empty" : "<p> Das Projekt ist leer. </p> <p> Möchten Sie eine Standardgruppe von Projektdateien erstellen? <br/> Andernfalls müssen Sie Dateien außerhalb des Editors manuell zum Projekt hinzufügen. </p>",
|
||||
"project_not_found" : "<p> Das Projekt '__project__' wurde nicht gefunden. </p>",
|
||||
"git_merge_conflict" : "<p> Das automatische Zusammenführen von Änderungen ist fehlgeschlagen. </p> <p> Beheben Sie die nicht zusammengeführten Konflikte und schreiben Sie die Ergebnisse fest. </p>"
|
||||
},
|
||||
"error" : "<strong> Fehler </strong>: __message__",
|
||||
"errors" : {
|
||||
"lostConnection" : "Verbindung zum Server verloren, Verbindung wird erneut hergestellt ...",
|
||||
"lostConnectionReconnect" : "Verbindung zum Server verloren, Verbindung in __time__s wird wieder hergestellt.",
|
||||
"lostConnectionTry" : "Jetzt testen",
|
||||
"cannotAddSubflowToItself" : "Subflow kann nicht zu sich selbst hinzugefügt werden",
|
||||
"cannotAddCircularReference" : "Subflow kann nicht hinzugefügt werden-zirkuläre Referenz wurde erkannt",
|
||||
"unsupportedVersion" : "<p> Verwenden einer nicht unterstützten Version von Node.js </p> <p> Sie sollten ein Upgrade auf das neueste LTS-Release von Node.js durchführen. </p>",
|
||||
"failedToAppendNode" : "<p> Fehler beim Laden von '__module__' </p> <p> __error__ </p>"
|
||||
},
|
||||
"project" : {
|
||||
"change-branch" : "Wechseln Sie in die lokale Verzweigung '__project__'.",
|
||||
"merge-abort" : "Git-Zusammenführung abgebrochen",
|
||||
"loaded" : "Projekt '__project__' geladen",
|
||||
"updated" : "Projekt '__project__' aktualisiert",
|
||||
"pull" : "Projekt '__project__' erneut geladen",
|
||||
"revert" : "Projekt '__project__' erneut geladen",
|
||||
"merge-complete" : "Git-Zusammenführung abgeschlossen"
|
||||
},
|
||||
"label" : {
|
||||
"manage-project-dep" : "Projektabhängigkeiten verwalten",
|
||||
"setup-cred" : "Berechtigungsnachweise einrichten",
|
||||
"setup-project" : "Projektdateien konfigurieren",
|
||||
"create-default-package" : "Standardpaketdatei erstellen",
|
||||
"no-thanks" : "Nein danke",
|
||||
"create-default-project" : "Standardprojektdateien erstellen",
|
||||
"show-merge-conflicts" : "Zusammenführungskonflikte anzeigen"
|
||||
}
|
||||
},
|
||||
"clipboard" : {
|
||||
"nodes" : "Knoten",
|
||||
"selectNodes" : "Wählen Sie den Text oben aus, und kopieren Sie die Datei in die Zwischenablage.",
|
||||
"pasteNodes" : "Knoten hier einfügen",
|
||||
"importNodes" : "Knoten importieren",
|
||||
"exportNodes" : "Knoten in Zwischenablage exportieren",
|
||||
"importUnrecognised" : "Importierter Typ nicht erkannt:",
|
||||
"importUnrecognised_plural" : "Importierte Typen nicht erkannt:",
|
||||
"nodesExported" : "Knoten, die in die Zwischenablage exportiert wurden",
|
||||
"nodeCopied" : "__count__ Knoten kopiert",
|
||||
"nodeCopied_plural" : "__count__ Knoten kopiert",
|
||||
"invalidFlow" : "Ungültiger Nachrichtenflow: __message__",
|
||||
"export" : {
|
||||
"selected" : "Ausgewählte Knoten",
|
||||
"current" : "Aktueller Flow",
|
||||
"all" : "alle Flows",
|
||||
"compact" : "kompakt",
|
||||
"formatted" : "formatiert",
|
||||
"copy" : "In Zwischenablage exportieren"
|
||||
},
|
||||
"import" : {
|
||||
"import" : "Importieren in",
|
||||
"newFlow" : "neuer Flow"
|
||||
},
|
||||
"copyMessagePath" : "Pfad kopiert",
|
||||
"copyMessageValue" : "Wert kopiert",
|
||||
"copyMessageValue_truncated" : "Abgeschnittene Wert kopiert"
|
||||
},
|
||||
"deploy" : {
|
||||
"deploy" : "Implementieren",
|
||||
"full" : "Voll",
|
||||
"fullDesc" : "Implementiert alles im Arbeitsbereich",
|
||||
"modifiedFlows" : "Geänderte Flows",
|
||||
"modifiedFlowsDesc" : "Implementiert nur Flows, die geänderte Knoten enthalten.",
|
||||
"modifiedNodes" : "Geänderte Knoten",
|
||||
"modifiedNodesDesc" : "Implementiert nur Knoten, die sich geändert haben.",
|
||||
"successfulDeploy" : "Erfolgreich implementiert",
|
||||
"deployFailed" : "Implementieren fehlgeschlagen: __message__",
|
||||
"unusedConfigNodes" : "Sie haben einige nicht verwendete Konfigurationsknoten.",
|
||||
"unusedConfigNodesLink" : "Klicken Sie hier, um sie zu sehen",
|
||||
"errors" : {
|
||||
"noResponse" : "Keine Antwort vom Server"
|
||||
},
|
||||
"confirm" : {
|
||||
"button" : {
|
||||
"ignore" : "Ignorieren",
|
||||
"confirm" : "Implementieren bestätigen",
|
||||
"review" : "Änderungen prüfen",
|
||||
"cancel" : "Abbrechen",
|
||||
"merge" : "Zusammenführen",
|
||||
"overwrite" : "Ignorieren & implementieren"
|
||||
},
|
||||
"undeployedChanges" : "Sie haben nicht implementierte Änderungen.\n\nWenn Sie diese Seite verlassen, gehen diese Änderungen verloren.",
|
||||
"improperlyConfigured" : "Der Arbeitsbereich enthält einige Knoten, die nicht ordnungsgemäß konfiguriert sind:",
|
||||
"unknown" : "Der Arbeitsbereich enthält einige unbekannte Knotentypen:",
|
||||
"confirm" : "Sind Sie sicher, dass Sie implementieren möchten?",
|
||||
"doNotWarn" : "warnen Sie nicht noch einmal.",
|
||||
"conflict" : "Auf dem Server wird eine aktuellere Gruppe von Datenflüssen ausgeführt.",
|
||||
"backgroundUpdate" : "Die Datenflüsse auf dem Server wurden aktualisiert.",
|
||||
"conflictChecking" : "Überprüfen Sie, ob die Änderungen automatisch gemischt werden können.",
|
||||
"conflictAutoMerge" : "Die Änderungen enthalten keine Konflikte und können automatisch gemischt werden.",
|
||||
"conflictManualMerge" : "Zu den Änderungen gehören Konflikte, die aufgelöst werden müssen, bevor sie implementiert werden können.",
|
||||
"plusNMore" : "+ __count__ mehr"
|
||||
}
|
||||
},
|
||||
"diff" : {
|
||||
"unresolvedCount" : "__count__ unaufgelöster Konflikt",
|
||||
"unresolvedCount_plural" : "__count__ unaufgelöste Konflikte",
|
||||
"globalNodes" : "Globale Knoten",
|
||||
"flowProperties" : "Flow-Eigenschaften",
|
||||
"type" : {
|
||||
"added" : "hinzugefügt",
|
||||
"changed" : "geändert",
|
||||
"unchanged" : "unverändert",
|
||||
"deleted" : "gelöscht",
|
||||
"flowDeleted" : "Flow gelöscht",
|
||||
"flowAdded" : "Flow hinzugefügt",
|
||||
"movedTo" : "verschoben zu __id__",
|
||||
"movedFrom" : "verschoben von __id__"
|
||||
},
|
||||
"nodeCount" : "__count__, Knoten",
|
||||
"nodeCount_plural" : "__count__-Knoten",
|
||||
"local" : "Lokale Änderungen",
|
||||
"remote" : "Ferne Änderungen",
|
||||
"reviewChanges" : "Änderungen prüfen",
|
||||
"noBinaryFileShowed" : "Der Inhalt der Binärdatei kann nicht angezeigt",
|
||||
"viewCommitDiff" : "Änderungen festschreiben",
|
||||
"compareChanges" : "Änderungen vergleichen",
|
||||
"saveConflict" : "Konfliktlösung speichern",
|
||||
"conflictHeader" : "<span> __resolved__ </span> von <span> __unresolved__ </span> -Konflikten behoben",
|
||||
"commonVersionError" : "Allgemeine Version enthält keine gültige JSON-Datei:",
|
||||
"oldVersionError" : "Alte Version enthält keine gültige JSON-Datei:",
|
||||
"newVersionError" : "Neue Version enthält keine gültige JSON-Datei:"
|
||||
},
|
||||
"subflow" : {
|
||||
"editSubflow" : "Flowschablone bearbeiten: __name__",
|
||||
"edit" : "Flowsschablone bearbeiten",
|
||||
"subflowInstances" : "Es ist __count__ Instanz dieser Subflow-Vorlage vorhanden.",
|
||||
"subflowInstances_plural" : "Es gibt __count__ Instanzen dieser Subflow-Vorlage.",
|
||||
"editSubflowProperties" : "Eigenschaften bearbeiten",
|
||||
"input" : "Eingaben:",
|
||||
"output" : "Ausgaben:",
|
||||
"deleteSubflow" : "Subflow löschen",
|
||||
"info" : "Beschreibung",
|
||||
"category" : "Kategorie",
|
||||
"format" : "Markdown-Format",
|
||||
"errors" : {
|
||||
"noNodesSelected" : "<strong> Subflow kann nicht erstellt werden </strong>: Es wurden keine Knoten ausgewählt.",
|
||||
"multipleInputsToSelection" : "<strong> Subflow kann nicht erstellt werden </strong>: Mehrere Eingaben zur Auswahl"
|
||||
}
|
||||
},
|
||||
"editor" : {
|
||||
"configEdit" : "Bearbeiten",
|
||||
"configAdd" : "Hinzufügen",
|
||||
"configUpdate" : "Aktualisieren",
|
||||
"configDelete" : "Löschen",
|
||||
"nodesUse" : "__count__node verwendet diese Konfiguration",
|
||||
"nodesUse_plural" : "__count__ -Knoten verwenden diese Konfiguration",
|
||||
"addNewConfig" : "Neuen __type__config-Knoten hinzufügen",
|
||||
"editNode" : "__type__ Knoten bearbeiten",
|
||||
"editConfig" : "__type__config-Knoten bearbeiten",
|
||||
"addNewType" : "Neuen __type__ hinzufügen ...",
|
||||
"nodeProperties" : "Knoteneigenschaften",
|
||||
"portLabels" : "Knoteneinstellungen",
|
||||
"labelInputs" : "Eingänge",
|
||||
"labelOutputs" : "Ausgänge",
|
||||
"settingIcon" : "Symbol",
|
||||
"noDefaultLabel" : "keine",
|
||||
"defaultLabel" : "Standardbeschriftung verwenden",
|
||||
"searchIcons" : "Suchsymbole",
|
||||
"useDefault" : "Standardwert verwenden",
|
||||
"errors" : {
|
||||
"scopeChange" : "Wenn Sie den Geltungsbereich ändern, wird er für Knoten in anderen Nachrichtenflüssen, die ihn verwenden, nicht verfügbar sein."
|
||||
}
|
||||
},
|
||||
"keyboard" : {
|
||||
"title" : "Tastaturkurzbefehle",
|
||||
"keyboard" : "Tastatur",
|
||||
"filterActions" : "Filteraktionen",
|
||||
"shortcut" : "Direktaufruf",
|
||||
"scope" : "Bereich",
|
||||
"unassigned" : "Nicht zugeordnet",
|
||||
"global" : "global",
|
||||
"workspace" : "Arbeitsbereich",
|
||||
"selectAll" : "Alle Knoten auswählen",
|
||||
"selectAllConnected" : "Alle verbundenen Knoten auswählen",
|
||||
"addRemoveNode" : "Knoten aus Auswahl hinzufügen/entfernen",
|
||||
"editSelected" : "Ausgewählten Knoten bearbeiten",
|
||||
"deleteSelected" : "Ausgewählte Knoten oder ausgewählten Link löschen",
|
||||
"importNode" : "Knoten importieren",
|
||||
"exportNode" : "Knoten exportieren",
|
||||
"nudgeNode" : "Ausgewählte Knoten verschieben (1px)",
|
||||
"moveNode" : "Ausgewählte Knoten verschieben (20px)",
|
||||
"toggleSidebar" : "Seitenleiste ein-/ausschalten",
|
||||
"copyNode" : "Ausgewählte Knoten kopieren",
|
||||
"cutNode" : "Ausgewählte Knoten ausschneiden",
|
||||
"pasteNode" : "Knoten einfügen",
|
||||
"undoChange" : "Letzte Änderung rückgängig machen",
|
||||
"searchBox" : "Suchfeld öffnen",
|
||||
"managePalette" : "Palette verwalten"
|
||||
},
|
||||
"library" : {
|
||||
"openLibrary" : "Bibliothek öffnen ...",
|
||||
"saveToLibrary" : "In Bibliothek speichern ...",
|
||||
"typeLibrary" : "__type__, Bibliothek",
|
||||
"unnamedType" : "Unbenannt __type__",
|
||||
"exportToLibrary" : "Knoten in Bibliothek exportieren",
|
||||
"dialogSaveOverwrite" : "Ein __libraryType__ mit dem Namen __libraryName__ ist bereits vorhanden. Überschreiben?",
|
||||
"invalidFilename" : "Ungültiger Dateiname",
|
||||
"savedNodes" : "Gespeicherte Knoten",
|
||||
"savedType" : "Gespeichert __type__",
|
||||
"saveFailed" : "Speichern fehlgeschlagen: __message__",
|
||||
"filename" : "Name der Datei",
|
||||
"folder" : "Ordner",
|
||||
"filenamePlaceholder" : "Datei",
|
||||
"fullFilenamePlaceholder" : "a/b/Datei",
|
||||
"folderPlaceholder" : "a/b",
|
||||
"breadcrumb" : "Bibliothek"
|
||||
},
|
||||
"palette" : {
|
||||
"noInfo" : "Keine Informationen verfügbar",
|
||||
"filter" : "Filterknoten",
|
||||
"search" : "Suchmodule",
|
||||
"addCategory" : "Neu hinzufügen ...",
|
||||
"label" : {
|
||||
"subflows" : "untergeordnete Nachrichtenflüsse",
|
||||
"input" : "Eingabe",
|
||||
"output" : "Ausgabe",
|
||||
"function" : "Funktion",
|
||||
"social" : "Soziale",
|
||||
"storage" : "Speicher",
|
||||
"analysis" : "Analyse",
|
||||
"advanced" : "fortgeschritten"
|
||||
},
|
||||
"event" : {
|
||||
"nodeAdded" : "Knoten zur Palette hinzugefügt:",
|
||||
"nodeAdded_plural" : "Die Palette wurde der Palette hinzugefügt.",
|
||||
"nodeRemoved" : "Knoten aus Palette entfernt:",
|
||||
"nodeRemoved_plural" : "Knoten aus Palette entfernt:",
|
||||
"nodeEnabled" : "Knoten aktiviert:",
|
||||
"nodeEnabled_plural" : "Knoten aktiviert:",
|
||||
"nodeDisabled" : "Knoten inaktiviert:",
|
||||
"nodeDisabled_plural" : "Knoten inaktiviert:",
|
||||
"nodeUpgraded" : "Knotenmodul __module__ aktualisiert auf Version __version__"
|
||||
},
|
||||
"editor" : {
|
||||
"title" : "Palette verwalten",
|
||||
"palette" : "Palette",
|
||||
"times" : {
|
||||
"seconds" : "Vor Sekunden",
|
||||
"minutes" : "Minuten vor",
|
||||
"minutesV" : "__count__ Minuten",
|
||||
"hoursV" : "__count__ Stunde ago",
|
||||
"hoursV_plural" : "__count__hours ago",
|
||||
"daysV" : "__count__ Tag ago",
|
||||
"daysV_plural" : "__count__ Tage",
|
||||
"weeksV" : "__count__ Woche vor",
|
||||
"weeksV_plural" : "__count__wochen ago",
|
||||
"monthsV" : "__count__ Monat vor",
|
||||
"monthsV_plural" : "__count__ Monaten",
|
||||
"yearsV" : "__count__ Jahr",
|
||||
"yearsV_plural" : "__count__ Jahren",
|
||||
"yearMonthsV" : "____ Jahr, __count__ Monat",
|
||||
"yearMonthsV_plural" : "____ Jahr, __count__ Monaten",
|
||||
"yearsMonthsV" : "____ Jahre, __count__ Monat vor",
|
||||
"yearsMonthsV_plural" : "____ Jahre, __count__ Monaten"
|
||||
},
|
||||
"nodeCount" : "__label__, Knoten",
|
||||
"nodeCount_plural" : "__label__ Knoten",
|
||||
"moduleCount" : "__count__ Modul verfügbar",
|
||||
"moduleCount_plural" : "__count__-Module verfügbar",
|
||||
"inuse" : "im Gebrauch",
|
||||
"enableall" : "alle aktivieren",
|
||||
"disableall" : "Alle inaktivieren",
|
||||
"enable" : "aktivieren",
|
||||
"disable" : "inaktivieren",
|
||||
"remove" : "entfernen",
|
||||
"update" : "Update auf __version__",
|
||||
"updated" : "aktualisiert",
|
||||
"install" : "installieren",
|
||||
"installed" : "installiert",
|
||||
"loading" : "Kataloge werden geladen ...",
|
||||
"tab-nodes" : "Knoten",
|
||||
"tab-install" : "installieren",
|
||||
"sort" : "Sortierung:",
|
||||
"sortAZ" : "a-z",
|
||||
"sortRecent" : "kürzlich",
|
||||
"more" : "+ __count__ mehr",
|
||||
"errors" : {
|
||||
"catalogLoadFailed" : "<p> Fehler beim Laden des Knotenkatalogs. </p> <p> Weitere Informationen finden Sie in der Browserkonsole. </p>",
|
||||
"installFailed" : "<p> Installation fehlgeschlagen: __module__ </p> <p> __message__ </p> <p> Überprüfen Sie das Protokoll auf weitere Informationen. </p>",
|
||||
"removeFailed" : "<p> Entfernen fehlgeschlagen: __module__ </p> <p> __message__ </p> <p> Überprüfen Sie das Protokoll auf weitere Informationen. </p>",
|
||||
"updateFailed" : "<p> Aktualisierung fehlgeschlagen: __module__ </p> <p> __message__ </p> <p> Überprüfen Sie das Protokoll auf weitere Informationen. </p>",
|
||||
"enableFailed" : "<p> Fehlgeschlagene Aktivierung: __module__ </p> <p> __message__ </p> <p> Überprüfen Sie das Protokoll auf weitere Informationen. </p>",
|
||||
"disableFailed" : "<p> Inaktivieren fehlgeschlagen: __module__ </p> <p> __message__ </p> <p> Überprüfen Sie das Protokoll auf weitere Informationen. </p>"
|
||||
},
|
||||
"confirm" : {
|
||||
"install" : {
|
||||
"body" : "<p> Installieren von '__module__' </p> <p> Vor der Installation von lesen Sie bitte die Dokumentation des Knotens. Einige Knoten haben Abhängigkeiten, die nicht automatisch aufgelöst werden können und einen Neustart von 'Node-RED' erfordern. </p>",
|
||||
"title" : "Knoten installieren"
|
||||
},
|
||||
"remove" : {
|
||||
"body" : "<p> Entfernen von '__module__' </p> <p>-Der Knoten deinstalliert ihn aus Node-RED. Der Knoten kann weiterhin Ressourcen verwenden, bis Node-RED erneut gestartet wird. </p>",
|
||||
"title" : "Knoten entfernen"
|
||||
},
|
||||
"update" : {
|
||||
"body" : "<p> Aktualisieren von '__module__' </p> <p> Für die Aktualisierung des Knotens ist ein Neustart von 'Node-RED' erforderlich, damit die Aktualisierung abgeschlossen werden kann. Dies muss manuell geschehen. </p>",
|
||||
"title" : "Knoten aktualisieren"
|
||||
},
|
||||
"cannotUpdate" : {
|
||||
"body" : "Es ist eine Aktualisierung für diesen Knoten verfügbar, aber sie ist nicht an einer Position installiert, die vom Palettenmanager aktualisiert werden kann. <br/> <br/> Weitere Informationen zum Aktualisieren dieses Knotens finden Sie in der Dokumentation."
|
||||
},
|
||||
"button" : {
|
||||
"review" : "Knoteninformationen öffnen",
|
||||
"install" : "installieren",
|
||||
"remove" : "Entfernen",
|
||||
"update" : "Aktualisieren"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"sidebar" : {
|
||||
"info" : {
|
||||
"name" : "Knoteninformationen",
|
||||
"tabName" : "Name",
|
||||
"label" : "info",
|
||||
"node" : "Knoten",
|
||||
"type" : "Typ",
|
||||
"id" : "ID",
|
||||
"status" : "Status",
|
||||
"enabled" : "Aktiviert",
|
||||
"disabled" : "Inaktiviert",
|
||||
"subflow" : "Subflow",
|
||||
"instances" : "Exemplare",
|
||||
"properties" : "Eigenschaften",
|
||||
"info" : "Informationen",
|
||||
"blank" : "leer",
|
||||
"null" : "null",
|
||||
"showMore" : "Weitere anzeigen",
|
||||
"showLess" : "Weniger anzeigen",
|
||||
"flow" : "Flow",
|
||||
"selection" : "Auswahl",
|
||||
"nodes" : "__count__ Knoten",
|
||||
"flowDesc" : "Beschreibung des Flows",
|
||||
"subflowDesc" : "Beschreibung des Subflows",
|
||||
"nodeHelp" : "Knotenhilfe",
|
||||
"none" : "Keine",
|
||||
"arrayItems" : "__count__ items",
|
||||
"showTips" : "Sie können die Tipps in der Anzeige \"Einstellungen\" öffnen."
|
||||
},
|
||||
"config" : {
|
||||
"name" : "Konfigurationsknoten",
|
||||
"label" : "Konfiguration",
|
||||
"global" : "Bei allen Flows",
|
||||
"none" : "keine",
|
||||
"subflows" : "Subflows",
|
||||
"flows" : "Flows",
|
||||
"filterUnused" : "Nicht verwendet",
|
||||
"filterAll" : "alle",
|
||||
"filtered" : "__count__ verdeckt"
|
||||
},
|
||||
"context" : {
|
||||
"name" : "Kontextdaten",
|
||||
"label" : "Kontext",
|
||||
"none" : "keine ausgewählt",
|
||||
"refresh" : "Aktualisierung zum Laden",
|
||||
"empty" : "leer",
|
||||
"node" : "Knoten",
|
||||
"flow" : "Flow",
|
||||
"global" : "Global"
|
||||
},
|
||||
"palette" : {
|
||||
"name" : "Palettenverwaltung",
|
||||
"label" : "Palette"
|
||||
},
|
||||
"project" : {
|
||||
"label" : "Projekt",
|
||||
"name" : "Projekt",
|
||||
"description" : "Beschreibung",
|
||||
"dependencies" : "Abhängigkeiten",
|
||||
"settings" : "Einstellungen",
|
||||
"noSummaryAvailable" : "Keine Zusammenfassung verfügbar",
|
||||
"editDescription" : "Projektbeschreibung bearbeiten",
|
||||
"editDependencies" : "Projektabhängigkeiten bearbeiten",
|
||||
"editReadme" : "README.md bearbeiten",
|
||||
"projectSettings" : {
|
||||
"edit" : "bearbeiten",
|
||||
"none" : "Keine",
|
||||
"install" : "installieren",
|
||||
"removeFromProject" : "Aus Projekt entfernen",
|
||||
"addToProject" : "zu Projekt hinzufügen",
|
||||
"files" : "Dateien",
|
||||
"flow" : "Flow",
|
||||
"credentials" : "Berechtigungsnachweis",
|
||||
"invalidEncryptionKey" : "Ungültiger Chiffrierschlüssel",
|
||||
"encryptionEnabled" : "Verschlüsselung aktiviert",
|
||||
"encryptionDisabled" : "Verschlüsselung inaktiviert",
|
||||
"setTheEncryptionKey" : "Legen Sie den Verschlüsselungsschlüssel fest:",
|
||||
"resetTheEncryptionKey" : "Setzt den Verschlüsselungsschlüssel zurück:",
|
||||
"changeTheEncryptionKey" : "Ändern Sie den Verschlüsselungsschlüssel:",
|
||||
"currentKey" : "Aktueller Schlüssel",
|
||||
"newKey" : "Neuer Schlüssel",
|
||||
"credentialsAlert" : "Dadurch werden alle vorhandenen Berechtigungsnachweise gelöscht.",
|
||||
"versionControl" : "Versionssteuerung",
|
||||
"branches" : "Verzweigungen",
|
||||
"noBranches" : "Keine Verzweigungen",
|
||||
"deleteConfirm" : "Sind Sie sicher, dass Sie die lokale Verzweigung '__name__' löschen wollen? Dies kann nicht rückgängig gemacht werden.",
|
||||
"unmergedConfirm" : "Die lokale Verzweigung '__name__' enthält nicht zusammengeführte Änderungen, die verloren gehen. Sind Sie sicher, dass Sie ihn löschen möchten?",
|
||||
"deleteUnmergedBranch" : "Nicht zusammengeführte Verzweigung löschen",
|
||||
"gitRemotes" : "Git Remotes",
|
||||
"addRemote" : "ferne hinzufügen",
|
||||
"addRemote2" : "Ferne hinzufügen",
|
||||
"remoteName" : "Ferner Name",
|
||||
"nameRule" : "Darf nur A-Z 0-9 _ enthalten.",
|
||||
"url" : "URL",
|
||||
"urlRule" : "https://, ssh:// oder file://",
|
||||
"urlRule2" : "Geben Sie den Benutzernamen/das Kennwort nicht in die URL ein.",
|
||||
"noRemotes" : "Keine Remotes",
|
||||
"deleteRemoteConfrim" : "Sind Sie sicher, dass Sie den fernen '__name__' löschen möchten?",
|
||||
"deleteRemote" : "Ferne löschen"
|
||||
},
|
||||
"userSettings" : {
|
||||
"committerDetail" : "Committer-Details",
|
||||
"committerTip" : "Leer Wert für Systemstandardwert belassen",
|
||||
"userName" : "Benutzername",
|
||||
"email" : "E-Mail",
|
||||
"sshKeys" : "SSH-Schlüssel",
|
||||
"sshKeysTip" : "Ermöglicht es Ihnen, sichere Verbindungen zu fernen Git-Repositorys zu erstellen.",
|
||||
"add" : "Schlüssel hinzufügen",
|
||||
"addSshKey" : "SSH-Schlüssel hinzufügen",
|
||||
"addSshKeyTip" : "Ein neues öffentungs-/privates Schlüsselpaar generieren",
|
||||
"name" : "Name",
|
||||
"nameRule" : "Darf nur A-Z 0-9 _ enthalten.",
|
||||
"passphrase" : "Kennphrase",
|
||||
"passphraseShort" : "Kennphrase zu kurz",
|
||||
"optional" : "Optional",
|
||||
"cancel" : "Abbrechen",
|
||||
"generate" : "Schlüssel generieren",
|
||||
"noSshKeys" : "Keine SSH-Schlüssel",
|
||||
"copyPublicKey" : "Öffentlichen Schlüssel in Zwischenablage kopieren",
|
||||
"delete" : "Löschtaste",
|
||||
"gitConfig" : "Git-Konfiguration",
|
||||
"deleteConfirm" : "Sind Sie sicher, dass der SSH-Schlüssel __name__ gelöscht werden soll? Dies kann nicht rückgängig gemacht werden."
|
||||
},
|
||||
"versionControl" : {
|
||||
"unstagedChanges" : "Nicht zwischengespeicherte Änderungen",
|
||||
"stagedChanges" : "Gespeichte Änderungen",
|
||||
"resolveConflicts" : "Konflikte auflösen",
|
||||
"head" : "HEAD",
|
||||
"staged" : "Zwischengelagert",
|
||||
"unstaged" : "Nicht zwischengespeichert",
|
||||
"local" : "Lokal",
|
||||
"remote" : "Fern",
|
||||
"revert" : "Sind Sie sicher, dass die Änderungen auf '__file__' zurückgesetzt werden sollen? Dies kann nicht rückgängig gemacht werden.",
|
||||
"revertChanges" : "Änderungen zurücksetzen",
|
||||
"localChanges" : "Lokale Änderungen",
|
||||
"none" : "Keine",
|
||||
"conflictResolve" : "Alle Konflikte wurden aufgelöst. Festschreiben der Änderungen, um den Mischvorgang abzuschließen.",
|
||||
"localFiles" : "Lokale Dateien",
|
||||
"all" : "alle",
|
||||
"unmergedChanges" : "Nicht zusammengeführte Änderungen",
|
||||
"abortMerge" : "Zusammenführen abbrechen",
|
||||
"commit" : "Festschreiben",
|
||||
"changeToCommit" : "Änderungen beim Festschreiben",
|
||||
"commitPlaceholder" : "Geben Sie Ihre Festschreibungsnachricht",
|
||||
"cancelCapital" : "Abbrechen",
|
||||
"commitCapital" : "Festschreiben",
|
||||
"commitHistory" : "Protokoll festschreiben",
|
||||
"branch" : "Verzweigung:",
|
||||
"moreCommits" : " weitere Commit (s)",
|
||||
"changeLocalBranch" : "Lokale Verzweigung ändern",
|
||||
"createBranchPlaceholder" : "Verzweigung suchen oder erstellen",
|
||||
"upstream" : "Upstream",
|
||||
"localOverwrite" : "Sie haben lokale Änderungen, die überschrieben werden, indem Sie die Verzweigung ändern. Sie müssen diese Änderungen zuerst festschreiben oder rückgängig machen.",
|
||||
"manageRemoteBranch" : "Ferne Verzweigung verwalten",
|
||||
"unableToAccess" : "Zugriff auf fernes Repository nicht möglich",
|
||||
"retry" : "Retry",
|
||||
"setUpstreamBranch" : "Als vorgeschaltete Verzweigung festlegen",
|
||||
"createRemoteBranchPlaceholder" : "Ferne Verzweigung suchen oder erstellen",
|
||||
"trackedUpstreamBranch" : "Die erstellte Verzweigung wird als überwachte Upstream-Verzweigung festgelegt.",
|
||||
"selectUpstreamBranch" : "Die Verzweigung wird erstellt. Wählen Sie diese Option aus, um sie als überwachte Upstream-Verzweigung festzulegen",
|
||||
"pushFailed" : "Push ist fehlgeschlagen, da die ferne Commit-COMMs-COMMs (COMM Zuerst ziehen und mischen, dann erneut drücken.",
|
||||
"push" : "Push",
|
||||
"pull" : "Pull",
|
||||
"unablePull" : "<p> Ferne Änderungen können nicht gezogen werden. Die nicht zwischengespeicherten lokalen Änderungen werden überschrieben. </p> <p> Die Änderungen festschreiben und die Anforderung wiederholen. </p>",
|
||||
"showUnstagedChanges" : "Nicht zwischengespeicherte Änderungen anzeigen",
|
||||
"connectionFailed" : "Verbindung zum fernen Repository konnte nicht hergestellt werden: ",
|
||||
"pullUnrelatedHistory" : "<p> Das ferne Protokoll der Festschreibungen hat einen nicht zugehörigen Verlauf. </p> <p> Sind Sie sicher, dass Sie die Änderungen in Ihr lokales Repository ziehen möchten? </p>",
|
||||
"pullChanges" : "Änderungen extrahieren",
|
||||
"history" : "Verlauf",
|
||||
"daysAgo" : "__count__ Tag ago",
|
||||
"daysAgo_plural" : "__count__ Tage",
|
||||
"hoursAgo" : "__count__ Stunde ago",
|
||||
"hoursAgo_plural" : "__count__hours ago",
|
||||
"minsAgo" : "__count__ min ago",
|
||||
"minsAgo_plural" : "__count__ mins ago",
|
||||
"secondsAgo" : "Sekunden zurück",
|
||||
"notTracking" : "Ihre lokale Verzweigung verfolgt derzeit keine ferne Verzweigung.",
|
||||
"statusUnmergedChanged" : "In Ihrem Repository sind nicht zusammengeführte Änderungen vorhanden. Sie müssen die Konflikte beheben und das Ergebnis festschreiben.",
|
||||
"repositoryUpToDate" : "Ihr Repository ist auf dem neuesten Stand.",
|
||||
"commitsAhead" : "Ihr Repository ist __count__commit vor der fernen. Sie können diese Festschreibung jetzt übertragen.",
|
||||
"commitsAhead_plural" : "Ihr Repository ist __count__ ist vor der fernen Commits festgeschrieben. Sie können diese Commits jetzt verschieben.",
|
||||
"commitsBehind" : "Ihr Projektarchiv ist __count__ hinter der Fernbedienung. Sie können diese Festschreibung jetzt extrahieren.",
|
||||
"commitsBehind_plural" : "Ihr Repository ist __count__ ist hinter der Fernbedienung festgeschrieben. Sie können diese Commits jetzt extrahieren.",
|
||||
"commitsAheadAndBehind1" : "Ihr Projektarchiv ist __count__commit hinter und ",
|
||||
"commitsAheadAndBehind1_plural" : "Ihr Repository ist __count__ schreibt sich zurück und ",
|
||||
"commitsAheadAndBehind2" : "__count__ wird vor der fernen festgeschrieben. ",
|
||||
"commitsAheadAndBehind2_plural" : "__count__ schreibt vor der fernen Funktion fest. ",
|
||||
"commitsAheadAndBehind3" : "Sie müssen die ferne Festschreibung nach unten ziehen, bevor Sie sie drücken.",
|
||||
"commitsAheadAndBehind3_plural" : "Sie müssen die fernen Festschreibungen vor dem Pusdrücken zurückziehen."
|
||||
}
|
||||
}
|
||||
},
|
||||
"typedInput" : {
|
||||
"type" : {
|
||||
"str" : "Zeichenfolge",
|
||||
"num" : "Anzahl",
|
||||
"re" : "Regulärer Ausdruck",
|
||||
"bool" : "boolean",
|
||||
"json" : "JSON",
|
||||
"bin" : "Puffer",
|
||||
"date" : "Zeitmarke",
|
||||
"jsonata" : "Ausdruck",
|
||||
"env" : "env, Variable"
|
||||
}
|
||||
},
|
||||
"editableList" : {
|
||||
"add" : "hinzufügen"
|
||||
},
|
||||
"search" : {
|
||||
"empty" : "Keine Übereinstimmungen gefunden",
|
||||
"addNode" : "Knoten hinzufügen ..."
|
||||
},
|
||||
"expressionEditor" : {
|
||||
"functions" : "Funktionen",
|
||||
"functionReference" : "Funktionsreferenz",
|
||||
"insert" : "Einfügen",
|
||||
"title" : "JSONata-Ausdruckseditor",
|
||||
"test" : "Test",
|
||||
"data" : "Beispielnachricht",
|
||||
"result" : "Ergebnis",
|
||||
"format" : "Formatiere Ausdruck",
|
||||
"compatMode" : "Kompatibilitätsmodus aktiviert",
|
||||
"compatModeDesc" : "<h3> JSONata-Kompatibilitätsmodus </h3> <p> Der aktuelle Ausdruck scheint immer noch auf <code> msg </code> zu verweisen, so dass er im Kompatibilitätsmodus ausgewertet wird. Aktualisieren Sie den Ausdruck so, dass <code> msg </code> nicht verwendet wird, da dieser Modus in der Zukunft entfernt wird. </p> <p> Wenn die JSONata-Unterstützung zuerst zu Node-RED hinzugefügt wurde, ist der Ausdruck erforderlich, um auf das Objekt <code> msg </code> zu verweisen. Beispiel: <code> msg.payload </code> würde für den Zugriff auf die Nutzdaten verwendet. </p> <p> Das ist nicht mehr erforderlich, da der Ausdruck direkt anhand der Nachricht ausgewertet wird. Um auf die Nutzdaten zugreifen zu können, muss der Ausdruck nur <code> Nutzdaten </code> sein. </p>",
|
||||
"noMatch" : "Kein übereinstimmende Ergebnisse",
|
||||
"errors" : {
|
||||
"invalid-expr" : "Ungültiger JSONata-Ausdruck:\n __message__",
|
||||
"invalid-msg" : "Ungültiges Beispiel für JSON-Nachricht:\n __message__",
|
||||
"context-unsupported" : "Kontextfunktionen können nicht getestet werden\n $flowContext oder $globalContext",
|
||||
"eval" : "Fehler beim Auswerten des Ausdrucks\n __message__"
|
||||
}
|
||||
},
|
||||
"jsEditor" : {
|
||||
"title" : "JavaScript-Editor"
|
||||
},
|
||||
"jsonEditor" : {
|
||||
"title" : "JSON-Editor",
|
||||
"format" : "Formatiere JSON"
|
||||
},
|
||||
"markdownEditor" : {
|
||||
"title" : "Markdown-Editor"
|
||||
},
|
||||
"bufferEditor" : {
|
||||
"title" : "Puffereditor",
|
||||
"modeString" : "Als UTF-8-Zeichenfolge bearbeiten",
|
||||
"modeArray" : "Als JSON-Array bearbeiten",
|
||||
"modeDesc" : "<h3> Puffereditor </h3> <p> Der Puffertyp wird als JSON-Array mit Bytewerten gespeichert. Der Editor versucht, den eingegebenen Wert als JSON-Array zu parsen. Wenn es sich nicht um ein gültiges JSON handelt, wird es als UTF-8-Zeichenfolge behandelt und in ein Array der einzelnen Zeichencodepunkte konvertiert. </p> <p> Beispiel: Der Wert <code> Hello World </code> wird in das JSON-Array konvertiert: <pre> [ 72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100] </pre> </p>"
|
||||
},
|
||||
"projects" : {
|
||||
"config-git" : "Git-Client konfigurieren",
|
||||
"welcome" : {
|
||||
"hello" : "Hallo! Wir haben 'Projekte' in 'Node-RED' eingeführt.",
|
||||
"desc0" : "Dies ist eine neue Methode für die Verwaltung Ihrer Datenflowsdateien und die Versionssteuerung Ihrer Abläufe.",
|
||||
"desc1" : "Um zu beginnen, können Sie Ihr erstes Projekt erstellen oder ein vorhandenes Projekt aus einem Git-Repository klonen.",
|
||||
"desc2" : "Wenn Sie sich nicht sicher sind, können Sie das jetzt überspringen. Sie können immer noch Ihr erstes Projekt aus dem 'Projects' -Menü erstellen.",
|
||||
"create" : "Projekt erstellen",
|
||||
"clone" : "Repository klonen",
|
||||
"not-right-now" : "Jetzt nicht mehr"
|
||||
},
|
||||
"git-config" : {
|
||||
"setup" : "Konfigurieren Sie Ihren Versionssteuerungsclient.",
|
||||
"desc0" : "Node-RED verwendet das Open-Source-Tool Git für die Versionssteuerung. Es protokolliert Änderungen in Ihren Projektdateien und ermöglicht es Ihnen, sie in ferne Repositorys zu übertragen.",
|
||||
"desc1" : "Wenn Sie eine Reihe von Änderungen festschreiben, werden die Änderungen mit einem Benutzernamen und einer E-Mail-Adresse von GIT-Datensätzen vorgenommen. Der Benutzername kann alles sein, was Sie wollen-es muss nicht Ihr richtiger Name sein.",
|
||||
"desc2" : "Ihr Git-Client ist bereits mit den unten stehenden Details konfiguriert.",
|
||||
"desc3" : "Sie können diese Einstellungen später unter der Registerkarte \"Git config\" des Einstellungsdialogs ändern.",
|
||||
"username" : "Benutzername",
|
||||
"email" : "E-Mail"
|
||||
},
|
||||
"project-details" : {
|
||||
"create" : "Erstellen Sie Ihr Projekt.",
|
||||
"desc0" : "Ein Projekt wird als Git-Repository verwaltet. Es ist wesentlich einfacher, Ihre Abläufe mit anderen zu teilen und an ihnen zu arbeiten.",
|
||||
"desc1" : "Sie können mehrere Projekte erstellen und schnell zwischen den Projekten im Editor wechseln.",
|
||||
"desc2" : "Zu Beginn benötigt Ihr Projekt einen Namen und eine optionale Beschreibung.",
|
||||
"already-exists" : "Das Projekt ist bereits vorhanden",
|
||||
"must-contain" : "Darf nur A-Z 0-9 _ enthalten.",
|
||||
"project-name" : "Projektname",
|
||||
"desc" : "Beschreibung",
|
||||
"opt" : "Optional"
|
||||
},
|
||||
"clone-project" : {
|
||||
"clone" : "Projekt klonen",
|
||||
"desc0" : "Wenn Sie bereits über ein Git-Repository verfügen, das ein Projekt enthält, können Sie es klonen, um es zu starten.",
|
||||
"already-exists" : "Das Projekt ist bereits vorhanden",
|
||||
"must-contain" : "Darf nur A-Z 0-9 _ enthalten.",
|
||||
"project-name" : "Projektname",
|
||||
"no-info-in-url" : "Geben Sie den Benutzernamen/das Kennwort nicht in die URL ein.",
|
||||
"git-url" : "Git-Repository-URL",
|
||||
"protocols" : "https://, ssh:// oder file://",
|
||||
"auth-failed" : "Authentifizierung fehlgeschlagen",
|
||||
"username" : "Benutzername",
|
||||
"passwd" : "Kennwort",
|
||||
"ssh-key" : "SSH-Schlüssel",
|
||||
"passphrase" : "Kennphrase",
|
||||
"ssh-key-desc" : "Bevor Sie ein Repository über ssh klonen können, müssen Sie einen SSH-Schlüssel hinzufügen, um auf diesen zu zugreifen.",
|
||||
"ssh-key-add" : "Einen ssh-Schlüssel hinzufügen",
|
||||
"credential-key" : "Verschlüsselungsschlüssel für Berechtigungsnachweise",
|
||||
"cant-get-ssh-key" : "Fehler! Der ausgewählte SSH-Schlüsselpfad kann nicht abgerufen werden.",
|
||||
"already-exists2" : "bereits vorhanden",
|
||||
"git-error" : "Git-Fehler",
|
||||
"connection-failed" : "Verbindung fehlgeschlagen",
|
||||
"not-git-repo" : "Kein Git-Repository",
|
||||
"repo-not-found" : "Repository nicht gefunden"
|
||||
},
|
||||
"default-files" : {
|
||||
"create" : "Erstellen Sie Ihre Projektdateien.",
|
||||
"desc0" : "Ein Projekt enthält Ihre Flow-Dateien, eine README-Datei und eine package.json-Datei.",
|
||||
"desc1" : "Es kann alle anderen Dateien enthalten, die im Git-Repository verwaltet werden sollen.",
|
||||
"desc2" : "Ihre vorhandenen Flow- und Berechtigungsnachweisdateien werden in das Projekt kopiert.",
|
||||
"flow-file" : "Flow-Datei",
|
||||
"credentials-file" : "Berechtigungsnachweisdatei"
|
||||
},
|
||||
"encryption-config" : {
|
||||
"setup" : "Setup der Verschlüsselung Ihrer Berechtigungsnachweisdatei",
|
||||
"desc0" : "Die Datei mit den Datenflowsberechtigungsnachweisen kann verschlüsselt werden, um ihren Inhalt sicher zu halten.",
|
||||
"desc1" : "Wenn Sie diese Berechtigungsnachweise in einem öffentlichen Git-Repository speichern möchten, müssen Sie sie verschlüsseln, indem Sie einen geheimen Schlüsselausdruck bereitstellen.",
|
||||
"desc2" : "Die Datei mit den Datenflowberechtigungsnachweisen ist derzeit nicht verschlüsselt.",
|
||||
"desc3" : "Das heißt, ihr Inhalt, wie z. B. Kennwörter und Zugriffstokens, kann von jedem mit Zugriff auf die Datei gelesen werden.",
|
||||
"desc4" : "Wenn Sie diese Berechtigungsnachweise in einem öffentlichen Git-Repository speichern möchten, müssen Sie sie verschlüsseln, indem Sie einen geheimen Schlüsselausdruck bereitstellen.",
|
||||
"desc5" : "Ihre Datei mit den Datenflowberechtigungsnachweisen wird derzeit mit der Eigenschaft credentialSecret aus Ihrer Einstellungsdatei als Schlüssel verschlüsselt.",
|
||||
"desc6" : "Die Datei mit den Datenflowberechtigungsnachweisen wird derzeit mit einem vom System generierten Schlüssel verschlüsselt. Sie sollten einen neuen geheimen Schlüssel für dieses Projekt angeben.",
|
||||
"desc7" : "Der Schlüssel wird separat von den Projektdateien gespeichert. Sie müssen den Schlüssel angeben, damit dieses Projekt in einer anderen Instanz von Node-RED verwendet werden kann.",
|
||||
"credentials" : "Berechtigungsnachweis",
|
||||
"enable" : "Verschlüsselung aktivieren",
|
||||
"disable" : "Verschlüsselung inaktivieren",
|
||||
"disabled" : "inaktiviert",
|
||||
"copy" : "Vorhandenen Schlüssel kopieren",
|
||||
"use-custom" : "Angepasster Schlüssel verwenden",
|
||||
"desc8" : "Die Datei mit den Berechtigungsnachweisen wird nicht verschlüsselt, und ihr Inhalt kann leicht gelesen werden.",
|
||||
"create-project-files" : "Projektdateien erstellen",
|
||||
"create-project" : "Projekt erstellen",
|
||||
"already-exists" : "bereits vorhanden",
|
||||
"git-error" : "Git-Fehler",
|
||||
"git-auth-error" : "git-auth-Fehler"
|
||||
},
|
||||
"create-success" : {
|
||||
"success" : "Sie haben Ihr erstes Projekt erfolgreich erstellt!",
|
||||
"desc0" : "Sie können jetzt weiterhin Node-RED verwenden, wie Sie es immer haben.",
|
||||
"desc1" : "Auf der Registerkarte \"info\" in der Seitenleiste wird angezeigt, was Ihr aktuelles aktives Projekt ist. Die Schaltfläche neben dem Namen kann für den Zugriff auf die Sicht 'Projekteinstellungen' verwendet werden.",
|
||||
"desc2" : "Die Registerkarte 'Verlauf' in der Seitenleiste kann verwendet werden, um Dateien anzuzeigen, die sich in Ihrem Projekt geändert haben, und sie festzuschreiben. Es zeigt Ihnen eine vollständige Historie Ihrer Commits an und ermöglicht es Ihnen, Ihre Änderungen in ein fernes Repository zu übertragen."
|
||||
},
|
||||
"create" : {
|
||||
"projects" : "Projekte",
|
||||
"already-exists" : "Das Projekt ist bereits vorhanden",
|
||||
"must-contain" : "Darf nur A-Z 0-9 _ enthalten.",
|
||||
"no-info-in-url" : "Geben Sie den Benutzernamen/das Kennwort nicht in die URL ein.",
|
||||
"open" : "Projekt öffnen",
|
||||
"create" : "Projekt erstellen",
|
||||
"clone" : "Repository klonen",
|
||||
"project-name" : "Projektname",
|
||||
"desc" : "Beschreibung",
|
||||
"opt" : "Optional",
|
||||
"flow-file" : "Flow-Datei",
|
||||
"credentials" : "Berechtigungsnachweis",
|
||||
"enable-encryption" : "Verschlüsselung aktivieren",
|
||||
"disable-encryption" : "Verschlüsselung inaktivieren",
|
||||
"encryption-key" : "Chiffrierschlüssel",
|
||||
"desc0" : "Eine Phrase, mit der Sie Ihre Berechtigungsnachweise schützen",
|
||||
"desc1" : "Die Datei mit den Berechtigungsnachweisen wird nicht verschlüsselt, und ihr Inhalt kann leicht gelesen werden.",
|
||||
"git-url" : "Git-Repository-URL",
|
||||
"protocols" : "https://, ssh:// oder file://",
|
||||
"auth-failed" : "Authentifizierung fehlgeschlagen",
|
||||
"username" : "Benutzername",
|
||||
"password" : "Kennwort",
|
||||
"ssh-key" : "SSH-Schlüssel",
|
||||
"passphrase" : "Kennphrase",
|
||||
"desc2" : "Bevor Sie ein Repository über ssh klonen können, müssen Sie einen SSH-Schlüssel hinzufügen, um auf diesen zu zugreifen.",
|
||||
"add-ssh-key" : "Einen ssh-Schlüssel hinzufügen",
|
||||
"credentials-encryption-key" : "Verschlüsselungsschlüssel für Berechtigungsnachweise",
|
||||
"already-exists-2" : "bereits vorhanden",
|
||||
"git-error" : "Git-Fehler",
|
||||
"con-failed" : "Verbindung fehlgeschlagen",
|
||||
"not-git" : "Kein Git-Repository",
|
||||
"no-resource" : "Repository nicht gefunden",
|
||||
"cant-get-ssh-key-path" : "Fehler! Der ausgewählte SSH-Schlüsselpfad kann nicht abgerufen werden.",
|
||||
"unexpected_error" : "unerwarteter_Fehler"
|
||||
},
|
||||
"delete" : {
|
||||
"confirm" : "Sind Sie sicher, dass Sie dieses Projekt löschen möchten?"
|
||||
},
|
||||
"create-project-list" : {
|
||||
"search" : "Projekte durchsuchen",
|
||||
"current" : "aktuell"
|
||||
},
|
||||
"require-clean" : {
|
||||
"confirm" : "<p> Sie haben nicht implementierte Änderungen verloren, die verloren gehen. </p> <p> Möchten Sie fortfahren? </p>"
|
||||
},
|
||||
"send-req" : {
|
||||
"auth-req" : "Authentifizierung für Repository erforderlich",
|
||||
"username" : "Benutzername",
|
||||
"password" : "Kennwort",
|
||||
"passphrase" : "Kennphrase",
|
||||
"retry" : "Retry",
|
||||
"update-failed" : "Fehler beim Aktualisieren der Auth.",
|
||||
"unhandled" : "Nicht behandelte Fehlerantwort"
|
||||
},
|
||||
"create-branch-list" : {
|
||||
"invalid" : "Ungültige Verzweigung",
|
||||
"create" : "Verzweigung erstellen",
|
||||
"current" : "aktuell"
|
||||
},
|
||||
"create-default-file-set" : {
|
||||
"no-active" : "Standarddatei kann ohne aktives Projekt nicht erstellt werden",
|
||||
"no-empty" : "Für ein nicht leeres Projekt kann keine Standarddatei erstellt werden.",
|
||||
"git-error" : "Git-Fehler"
|
||||
},
|
||||
"errors" : {
|
||||
"no-username-email" : "Ihr Git-Client ist nicht mit einem Benutzernamen/einer E-Mail konfiguriert.",
|
||||
"unexpected" : "Es ist ein unerwarteter Fehler aufgetreten",
|
||||
"code" : "code"
|
||||
}
|
||||
}
|
||||
}
|
23
packages/node_modules/@node-red/editor-client/locales/de/infotips.json
vendored
Executable file
23
packages/node_modules/@node-red/editor-client/locales/de/infotips.json
vendored
Executable file
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"info" : {
|
||||
"tip0" : "Sie können die ausgewählten Knoten oder Verbindungen mit {{ core:delete-selection }} entfernen.",
|
||||
"tip1" : "Suche nach Knoten mit {{ core:search }}",
|
||||
"tip2" : "{{ core:toggle-sidebar }} schaltet die Ansicht dieser Seitenleiste ein.",
|
||||
"tip3" : "Sie können Ihre Palette von Knoten mit {{ core:manage-palette }} verwalten.",
|
||||
"tip4" : "Ihre Flow-Konfigurationsknoten werden in der Seitenleiste angezeigt. Es kann über das Menü oder mit {{ core:show-config-tab }} aufgerufen werden.",
|
||||
"tip5" : "Aktiviert oder inaktiviert diese Tipps von der Option in den Einstellungen",
|
||||
"tip6" : "Verschieben Sie die ausgewählten Knoten mit Hilfe der [left] [up] [down] und [right] Tasten. Halten Sie [Shift] gedrückt, um das Fenster weiter zu schieben",
|
||||
"tip7" : "Wenn Sie einen Knoten auf eine Verbindung ziehen, wird er in die Verbindung eingefügt.",
|
||||
"tip8" : "Die ausgewählten Knoten exportieren oder die aktuelle Registerkarte mit {{ core:show-export-dialog }}",
|
||||
"tip9" : "Importieren Sie einen Flow, indem Sie sein JSON in den Editor ziehen oder mit {{ core:show-import-dialog }}.",
|
||||
"tip10" : "[Umschalt] [Klicken] und ziehen Sie auf einen Knotenanschluss, um alle angeschlossenen Verbindungen oder nur die ausgewählte zu verschieben.",
|
||||
"tip11" : "Die Registerkarte \"Info\" mit {{ core:show-info-tab }} oder der Registerkarte \"Debug\" mit {{ core:show-debug-tab }} anzeigen",
|
||||
"tip12" : "[ctrl] [Klicken] in den Arbeitsbereich, um den Schnellhinzufügedialog zu öffnen.",
|
||||
"tip13" : "Halten Sie [ctrl] gedrückt, wenn Sie auf einem Knotenanschluss klicken, um eine Schnellverbindung zu aktivieren.",
|
||||
"tip14" : "Halten Sie [Umschalt] gedrückt, wenn Sie auf einen Knoten klicken, um auch alle verbundenen Knoten auszuwählen.",
|
||||
"tip15" : "Halten Sie [ctrl] gedrückt, wenn Sie auf einen Knoten klicken, um ihn aus der aktuellen Auswahl hinzuzufügen oder zu entfernen.",
|
||||
"tip16" : "Indexzungen wechseln mit {{ core:show-previous-tab }} und {{ core:show-next-tab }}",
|
||||
"tip17" : "Sie können die Änderungen im Editierrahmen des Knotens mit {{ core:confirm-edit-tray }} bestätigen oder sie mit {{ core:cancel-edit-tray }} abbrechen.",
|
||||
"tip18" : "Durch Drücken von {{ core:edit-selected-node }} wird der erste Knoten in der aktuellen Auswahl bearbeitet."
|
||||
}
|
||||
}
|
222
packages/node_modules/@node-red/editor-client/locales/de/jsonata.json
vendored
Executable file
222
packages/node_modules/@node-red/editor-client/locales/de/jsonata.json
vendored
Executable file
@@ -0,0 +1,222 @@
|
||||
{
|
||||
"$string" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Transformiert den Parameter *arg* in eine Zeichenfolge mit den folgenden Transformationsregeln:\n\n -Zeichenfolgen bleiben unverändert\n -Funktionen werden in eine leere Zeichenfolge konvertiert\n -Numerische Unendlichkeit und NaN lösen einen Fehler aus, da sie nicht als JSON-Nummer dargestellt werden können.\n -Alle anderen Werte werden mit Hilfe der Funktion 'JSON.stringify' in eine JSON-Zeichenfolge konvertiert."
|
||||
},
|
||||
"$length" : {
|
||||
"args" : "str",
|
||||
"desc" : "Gibt die Anzahl der Zeichen in der Zeichenfolge `str` zurück. Es wird ein Fehler ausgelöst, wenn `str` keine Zeichenfolge ist."
|
||||
},
|
||||
"$substring" : {
|
||||
"args" : "str, start [, länge]",
|
||||
"desc" : "Gibt eine Zeichenfolge zurück, die die Zeichen im ersten Parameter `str` beginnend bei Position `start` (Null-Offset) enthält. Wenn \"length\" angegeben ist, enthält die Unterzeichenfolge maximal \"Länge\" Zeichen. Wenn `start` negativ ist, gibt es die Anzahl der Zeichen am Ende von `str` an."
|
||||
},
|
||||
"$substringBefore" : {
|
||||
"args" : "str, chars",
|
||||
"desc" : "Gibt die Unterzeichenfolge vor dem ersten Auftreten der Zeichenfolge `chars` in `str` zurück. Falls `str` nicht `chars` enthält, gibt es `str` zurück."
|
||||
},
|
||||
"$substringAfter" : {
|
||||
"args" : "str, chars",
|
||||
"desc" : "Gibt die Unterzeichenfolge nach dem ersten Auftreten der Zeichenfolge `chars` in `str` zurück. Falls `str` nicht `chars` enthält, gibt es `str` zurück."
|
||||
},
|
||||
"$uppercase" : {
|
||||
"args" : "str",
|
||||
"desc" : "Gibt eine Zeichenfolge mit allen Zeichen von `str` zurück, die in Großbuchstaben konvertiert werden."
|
||||
},
|
||||
"$lowercase" : {
|
||||
"args" : "str",
|
||||
"desc" : "Gibt eine Zeichenfolge mit allen Zeichen von `str` in Kleinbuchstaben zurück."
|
||||
},
|
||||
"$trim" : {
|
||||
"args" : "str",
|
||||
"desc" : "Normalisiert und trimmt alle Leerzeichen in `str` durch Anwenden der folgenden Schritte:\n\n -Alle Tabulatorstopps, Wagenrückläufe und Zeilenvorschübe werden durch Leerzeichen ersetzt.\n-Zusammenhängende Folgen von Räumen werden auf einen einzigen Raum reduziert.\n-Trailing und führende Plätze werden entfernt.\n\n Wenn 'str' nicht angegeben ist (d. h. Diese Funktion wird ohne Argumente aufgerufen), dann wird der Kontextwert als Wert von `str` verwendet. Es wird ein Fehler ausgelöst, wenn `str` keine Zeichenfolge ist."
|
||||
},
|
||||
"$contains" : {
|
||||
"args" : "str, Muster",
|
||||
"desc" : "Gibt `true` zurück, wenn `str` durch `Muster` abgeglichen wird, sonst gibt es `false` zurück. Wenn 'str' nicht angegeben ist (d. h. Diese Funktion wird mit einem Argument aufgerufen), dann wird der Kontextwert als Wert von `str` verwendet. Der Parameter 'Muster' kann entweder eine Zeichenfolge oder ein regulärer Ausdruck sein."
|
||||
},
|
||||
"$split" : {
|
||||
"args" : "str [, Trennzeichen] [, Grenzwert]",
|
||||
"desc" : "Teilt den Parameter 'str' in einem Array mit Unterzeichenfolgen. Es ist ein Fehler, wenn `str` keine Zeichenfolge ist. Der optionale Parameter 'Trennzeichen' gibt die Zeichen in der `str` an, um die es entweder als Zeichenfolge oder als regulärer Ausdruck geteilt werden soll. Wenn 'Trennzeichen' nicht angegeben wird, wird die leere Zeichenfolge angenommen, und `str` wird in ein Array aus einzelnen Zeichen aufgeteilt. Es handelt sich um einen Fehler, wenn `Trennzeichen' keine Zeichenfolge ist. Der optionale Parameter 'Grenzwert' ist eine Zahl, die die maximale Anzahl von Unterzeichenfolgen angibt, die in das resultierende Array eingeschlossen werden sollen. Alle zusätzlichen Unterzeichenfolgen werden gelöscht. Wenn 'Grenzwert' nicht angegeben wird, wird ' str ` vollständig geteilt, wobei die Größe des resultierenden Arrays nicht begrenzt ist. Es handelt sich um einen Fehler, wenn `Grenzwert' keine nicht negative Zahl ist."
|
||||
},
|
||||
"$join" : {
|
||||
"args" : "array [, Trennzeichen]",
|
||||
"desc" : "Verkettet ein Array von Komponentenzeichenfolgen in eine einzelne verkettete Zeichenfolge mit jeder Komponentenzeichenfolge, die durch den optionalen Parameter 'separator' getrennt ist. Es ist ein Fehler, wenn die Eingabe `Array` ein Element enthält, das keine Zeichenfolge ist. Wenn 'Trennzeichen' nicht angegeben wird, wird davon ausgegangen, dass es sich um eine leere Zeichenfolge handelt, d. h. Zwischen den Komponentenzeichenfolgen ist kein Trennzeichen vorhanden. Es handelt sich um einen Fehler, wenn `Trennzeichen' keine Zeichenfolge ist."
|
||||
},
|
||||
"$match" : {
|
||||
"args" : "str, Muster [, Grenzwert]",
|
||||
"desc" : "Wendet die Zeichenfolge `str` an den regulären Ausdruck `Muster` an und gibt ein Array von Objekten zurück, wobei jedes Objekt Informationen zu jedem Vorkommen einer Übereinstimmung in `str` enthält."
|
||||
},
|
||||
"$replace" : {
|
||||
"args" : "str, Muster, Ersatz [, Grenzwert]",
|
||||
"desc" : "Findet Vorkommen von `Muster` in `str` und ersetzt sie durch `Ersatz`.\n\nDer optionale Parameter 'Grenzwert' ist die maximale Anzahl an Ersetzungen."
|
||||
},
|
||||
"$now" : {
|
||||
"args" : "",
|
||||
"desc" : "Generiert eine Zeitmarke im ISO-8601-kompatiblen Format und gibt sie als Zeichenfolge zurück."
|
||||
},
|
||||
"$base64encode" : {
|
||||
"args" : "Zeichenfolge",
|
||||
"desc" : "Konvertiert eine ASCII-Zeichenfolge in eine Basis-64-Darstellung. Jedes Zeichen in der Zeichenfolge wird als Byte mit binären Daten behandelt. Dies setzt voraus, dass alle Zeichen in der Zeichenfolge im Bereich von 0x00 bis 0xFF liegen, der alle Zeichen in URI-codierten Zeichenfolgen enthält. Unicode-Zeichen außerhalb dieses Bereichs werden nicht unterstützt."
|
||||
},
|
||||
"$base64decode" : {
|
||||
"args" : "Zeichenfolge",
|
||||
"desc" : "Konvertiert die Basis-64-codierten Byte in eine Zeichenfolge unter Verwendung einer UTF-8-Unicode-Codepage."
|
||||
},
|
||||
"$number" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Der Parameter 'arg' wird unter Verwendung der folgenden Regeln für das Casting in eine Zahl verwendet:\n\n -Zahlen bleiben unverändert\n -Zeichenfolgen, die eine Folge von Zeichen enthalten, die eine rechtliche JSON-Nummer darstellen, werden in diese Zahl konvertiert.\n -Alle anderen Werte bewirken, dass ein Fehler ausgelöst wird."
|
||||
},
|
||||
"$abs" : {
|
||||
"args" : "Anzahl",
|
||||
"desc" : "Gibt den absoluten Wert des Parameters 'Zahl' zurück."
|
||||
},
|
||||
"$floor" : {
|
||||
"args" : "Anzahl",
|
||||
"desc" : "Gibt den Wert von 'Zahl' auf die nächste ganze Zahl zurück, die kleiner oder gleich 'Zahl' ist."
|
||||
},
|
||||
"$ceil" : {
|
||||
"args" : "Anzahl",
|
||||
"desc" : "Gibt den Wert von 'Zahl' auf die nächste ganze Zahl zurück, die größer oder gleich 'Zahl' ist."
|
||||
},
|
||||
"$round" : {
|
||||
"args" : "Zahl [, Genauigkeit]",
|
||||
"desc" : "Gibt den Wert des Parameters `Zahl` zurück, der auf die Anzahl der Dezimalstellen gerundet wird, die durch den optionalen Parameter 'Genauigkeit' angegeben wird."
|
||||
},
|
||||
"$power" : {
|
||||
"args" : "Basis, Exponent",
|
||||
"desc" : "Gibt den Wert von `Basis` potenziert mit `Exponent` zurück."
|
||||
},
|
||||
"$sqrt" : {
|
||||
"args" : "Zahl",
|
||||
"desc" : "Gibt die Quadratwurzel des Werts des Parameters 'Zahl' zurück."
|
||||
},
|
||||
"$random" : {
|
||||
"args" : "",
|
||||
"desc" : "Gibt eine Pseudozufallszahl größer-gleich null und kleiner als eins zurück."
|
||||
},
|
||||
"$millis" : {
|
||||
"args" : "",
|
||||
"desc" : "Gibt die Anzahl der Millisekunden seit der Unix-Epoche (1. Januar 1970 (UTC)) als Zahl zurück. Alle Invocationen von `$millis ()` innerhalb einer Auswertung eines Ausdrucks geben alle denselben Wert zurück."
|
||||
},
|
||||
"$sum" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt die arithmetische Summe eines `Array` von Zahlen zurück. Es ist ein Fehler, wenn die Eingabe `Array` ein Element enthält, das keine Zahl ist."
|
||||
},
|
||||
"$max" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt die maximale Anzahl in einem `Array` von Zahlen zurück. Es ist ein Fehler, wenn die Eingabe `Array` ein Element enthält, das keine Zahl ist."
|
||||
},
|
||||
"$min" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt die minimale Zahl in einem `Array` von Zahlen zurück. Es ist ein Fehler, wenn die Eingabe `Array` ein Element enthält, das keine Zahl ist."
|
||||
},
|
||||
"$average" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt den Mittelwert eines `Array` von Zahlen zurück. Es ist ein Fehler, wenn die Eingabe `Array` ein Element enthält, das keine Zahl ist."
|
||||
},
|
||||
"$boolean" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Castet das Argument mit den folgenden Regeln in einen Booleschen Wert:\n\n -` Boolean ': nicht geändert\n -` string `: leer: `false`\n -` string `: nicht leer: `true`\n -` Zahl `: ` 0 `: ` falsch `\n -` Zahl `: Nicht-Null: `true`\n -` null `: `false`\n -` array `: leer: `false`\n -` array `: enthält ein Mitglied, das auf `true` setzt: `true`\n -` array `: alle Member werden in `false` umgesetzt: `false`\n -` object `: empty: `false`\n -` object `: non-empty: `true`\n -` Funktion `: ` falsch `"
|
||||
},
|
||||
"$not" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Gibt den Booleschen Wert NOT für das Argument zurück. `arg` wird zuerst in einen Booleschen Wert umgesetzt."
|
||||
},
|
||||
"$exists" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Gibt den Booleschen Wert 'true' zurück, wenn der Ausdruck `arg` als Wert ausgewertet wird, oder 'false', wenn der Ausdruck nicht mit einem anderen Ausdruck übereinstimmt (z. B. ein Pfad zu einer nicht vorhandenen Feldreferenz)."
|
||||
},
|
||||
"$count" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt die Anzahl der Elemente in dem Array zurück."
|
||||
},
|
||||
"$append" : {
|
||||
"args" : "Array, Array",
|
||||
"desc" : "Hängen Sie zwei Arrays an."
|
||||
},
|
||||
"$sort" : {
|
||||
"args" : "array [, Funktion]",
|
||||
"desc" : "Gibt ein Array zurück, das alle Werte im Parameter 'array' enthält, aber in der Reihenfolge sortiert wird.\n\nWenn ein Vergleichsoperator 'function' angegeben wird, muss es sich um eine Funktion handeln, die zwei Parameter benötigt:\n\n` Funktion (links, rechts) `\n\nDiese Funktion wird durch den Sortieralgorithmus aufgerufen, um zwei Werte links und rechts zu vergleichen. Wenn der Wert von links nach dem Wert von rechts in der gewünschten Sortierreihenfolge platziert werden soll, muss die Funktion den Booleschen Wert 'true' zurückgeben, um einen Auslagerungsspeicher anzuzeigen. Andernfalls muss 'false' zurückgegeben werden."
|
||||
},
|
||||
"$reverse" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt ein Array zurück, das alle Werte aus dem Parameter 'array' enthält, aber in umgekehrter Reihenfolge."
|
||||
},
|
||||
"$shuffle" : {
|
||||
"args" : "Array",
|
||||
"desc" : "Gibt ein Array zurück, das alle Werte aus dem Parameter ` array ` enthält, aber in zufälliger Reihenfolge geschattiert ist."
|
||||
},
|
||||
"$zip" : {
|
||||
"args" : "Array, ...",
|
||||
"desc" : "Gibt ein konvolviertes (gezipptes) Array zurück, das gruppierte Arrays von Werten aus den Argumenten ` array1 ` ... ` arrayN ' aus Index 0, 1, 2 ... enthält."
|
||||
},
|
||||
"$keys" : {
|
||||
"args" : "Objekt",
|
||||
"desc" : "Gibt ein Array zurück, das die Schlüssel in dem Objekt enthält. Wenn es sich bei dem Argument um ein Array von Objekten handelt, enthält das zurückgegebene Array eine deduplizierte Liste aller Schlüssel in allen Objekten."
|
||||
},
|
||||
"$lookup" : {
|
||||
"args" : "Objekt, Schlüssel",
|
||||
"desc" : "Gibt den Wert zurück, der dem Schlüssel im Objekt zugeordnet ist. Wenn es sich bei dem ersten Argument um ein Array von Objekten handelt, werden alle Objekte im Array durchsucht, und die Werte, die mit allen Vorkommen des Schlüssels verknüpft sind, werden zurückgegeben."
|
||||
},
|
||||
"$spread" : {
|
||||
"args" : "Objekt",
|
||||
"desc" : "Teilt ein Objekt, das Schlüssel/Wert-Paare enthält, in ein Array von Objekten, von denen jedes ein einzelnes Schlüssel/Wert-Paar aus dem Eingabeobjekt hat. Wenn es sich bei dem Parameter um ein Array von Objekten handelt, enthält die resultierende Feldgruppe ein Objekt für jedes Schlüssel/Wert-Paar in jedem Objekt in der angegebenen Feldgruppe."
|
||||
},
|
||||
"$merge" : {
|
||||
"args" : "array <object>",
|
||||
"desc" : "Mischt ein Array von ` Objekten ` in ein einzelnes ` Objekt `, das alle Schlüssel/Wert-Paare aus jedem der Objekte in dem Eingabe-Array enthält. Wenn eines der Eingabeobjekte denselben Schlüssel enthält, enthält das zurückgegebene Objekt den Wert des letzten Objekts in der Feldgruppe. Es handelt sich um einen Fehler, wenn das Eingabe-Array ein Element enthält, das kein Objekt ist."
|
||||
},
|
||||
"$sift" : {
|
||||
"args" : "Objekt, Funktion",
|
||||
"desc" : "Gibt ein Objekt zurück, das nur die Schlüssel/Wert-Paare aus dem Parameter 'object' enthält, die die Prädikat ` funktion ' erfüllen, die als zweiter Parameter übergeben wird.\n\nDie Funktion ` function `, die als zweiter Parameter angegeben wird, muss die folgende Signatur aufweisen:\n\n` function (value [, key [, object]]) `"
|
||||
},
|
||||
"$each" : {
|
||||
"args" : "Objekt, Funktion",
|
||||
"desc" : "Gibt ein Array zurück, das die Werte enthält, die von der Funktion ` function ` zurückgegeben werden, wenn sie auf jedes Schlüssel/Wert-Paar im ` object ` angewendet werden."
|
||||
},
|
||||
"$map" : {
|
||||
"args" : "Array, Funktion",
|
||||
"desc" : "Gibt ein Array zurück, das die Ergebnisse der Anwendung des Parameters ` function ` auf jeden Wert im Parameter 'array' enthält.\n\nDie Funktion ` function `, die als zweiter Parameter angegeben wird, muss die folgende Signatur aufweisen:\n\n` function (value [, index [, array]]) `"
|
||||
},
|
||||
"$filter" : {
|
||||
"args" : "Array, Funktion",
|
||||
"desc" : "Gibt ein Array zurück, das nur die Werte im Parameter 'array' enthält, die das Prädikat ` funktion ` erfüllen.\n\nDie Funktion ` function `, die als zweiter Parameter angegeben wird, muss die folgende Signatur aufweisen:\n\n` function (value [, index [, array]]) `"
|
||||
},
|
||||
"$reduce" : {
|
||||
"args" : "array, function [, init]",
|
||||
"desc" : "Gibt einen aggregierten Wert zurück, der aus der Anwendung des Parameters ` function 'nacheinander auf jeden Wert in' array ` in Kombination mit dem Ergebnis der vorherigen Anwendung der Funktion angewendet wurde.\n\nDie Funktion muss zwei Argumente akzeptieren und verhält sich wie ein Infix-Operator zwischen jedem Wert innerhalb des ` Array `.\n\nDer optionale Parameter 'init' wird als Anfangswert in der Aggregation verwendet."
|
||||
},
|
||||
"$flowContext" : {
|
||||
"args" : "Zeichenfolge [, Zeichenfolge]",
|
||||
"desc" : "Ruft eine Flusskontexteigenschaft ab.\n\nDies ist eine definierte Funktion vom Typ \"Node-RED\"."
|
||||
},
|
||||
"$globalContext" : {
|
||||
"args" : "Zeichenfolge [, Zeichenfolge]",
|
||||
"desc" : "Ruft eine globale Kontexteigenschaft ab.\n\nDies ist eine definierte Funktion vom Typ \"Node-RED\"."
|
||||
},
|
||||
"$pad" : {
|
||||
"args" : "string, width [, char]",
|
||||
"desc" : "Gibt eine Kopie der ` Zeichenfolge ` mit zusätzlichen Aufenthalten zurück, falls erforderlich, so dass die Gesamtzahl der Zeichen mindestens der absolute Wert des Parameters 'width' ist.\n\nWenn ` width ` eine positive Zahl ist, wird die Zeichenfolge nach rechts aufgefüllt. Wenn sie negativ ist, wird sie nach links geplisften.\n\nDas optionale Argument 'char' gibt die Padding-Zeichen an, die verwendet werden sollen. Wenn keine Angabe gemacht wird, wird standardmäßig der Wert für das Leerzeichen angenommen."
|
||||
},
|
||||
"$fromMillis" : {
|
||||
"args" : "Anzahl",
|
||||
"desc" : "Konvertieren Sie eine Zahl, die Millisekunden seit der Unix-Epoche (1. Januar 1970 (UTC)) in eine Zeitmarkenzeichenfolge im ISO 8601-Format darstellt."
|
||||
},
|
||||
"$formatNumber" : {
|
||||
"args" : "Zahl, Bild [, Optionen]",
|
||||
"desc" : "Transformiere die `Zahl` an eine Zeichenfolge und formatiert sie in eine dezimale Darstellung, wie in der 'Bild' -Zeichenfolge angegeben.\n\n Das Verhalten dieser Funktion ist mit der XPath/XQuery-Funktion fn:formatnummer konsistent, wie sie in der XPath F&O 3.1-Spezifikation definiert ist. Der Parameter für die Bildzeichenfolge definiert, wie die Zahl formatiert ist und hat die gleiche Syntax wie fn:format-number.\n\nDas optionale dritte Argument ` Optionen ` wird verwendet, um die standardmäßigen länderspezifischen Formatierungszeichen, wie z. B. das Dezimaltrennzeichen, zu überschreiben. Wenn dieses Argument angegeben wird, muss es sich um ein Objekt handeln, das Name/Wert-Paare enthält, die im Abschnitt mit dem Dezimalformat der XPath F&O 3.1-Spezifikation angegeben sind."
|
||||
},
|
||||
"$formatBase" : {
|
||||
"args" : "Zahl [, Radix]",
|
||||
"desc" : "Transformiere die `Zahl` in eine Zeichenfolge und formatiert sie in eine ganze Zahl, die in der durch das `radix` -Argument angegebenen Zahlenbasis dargestellt wird. Wenn 'radix' nicht angegeben wird, wird standardmäßig die Basis 10 verwendet. 'radix` kann zwischen 2 und 36 liegen, andernfalls wird ein Fehler ausgelöst."
|
||||
},
|
||||
"$toMillis" : {
|
||||
"args" : "Zeitmarke",
|
||||
"desc" : "Konvertieren Sie eine Zeichenfolge `Zeitmarke' im ISO 8601-Format in die Anzahl der Millisekunden seit der Unix-Epoche (1. Januar 1970 (UTC)) als Zahl. Es wird ein Fehler ausgelöst, wenn die Zeichenfolge nicht das richtige Format hat."
|
||||
},
|
||||
"$env" : {
|
||||
"args" : "arg",
|
||||
"desc" : "Gibt den Wert einer Umgebungsvariablen zurück.\n\nDies ist eine definierte Funktion vom Typ \"Node-RED\"."
|
||||
}
|
||||
}
|
101
packages/node_modules/@node-red/editor-api/lib/editor/locales/en-US/editor.json → packages/node_modules/@node-red/editor-client/locales/en-US/editor.json
vendored
Normal file → Executable file
101
packages/node_modules/@node-red/editor-api/lib/editor/locales/en-US/editor.json → packages/node_modules/@node-red/editor-client/locales/en-US/editor.json
vendored
Normal file → Executable file
@@ -23,11 +23,11 @@
|
||||
"confirmDelete": "Confirm delete",
|
||||
"delete": "Are you sure you want to delete '__label__'?",
|
||||
"dropFlowHere": "Drop the flow here",
|
||||
"addFlow": "Add Flow",
|
||||
"status": "Status",
|
||||
"enabled": "Enabled",
|
||||
"disabled":"Disabled",
|
||||
"info": "Description",
|
||||
"tip": "Description accepts Markdown and will appear in the Info tab."
|
||||
"info": "Description"
|
||||
},
|
||||
"menu": {
|
||||
"label": {
|
||||
@@ -46,6 +46,9 @@
|
||||
"sidebar": {
|
||||
"show": "Show sidebar"
|
||||
},
|
||||
"palette": {
|
||||
"show": "Show palette"
|
||||
},
|
||||
"settings": "Settings",
|
||||
"userSettings": "User Settings",
|
||||
"nodes": "Nodes",
|
||||
@@ -75,9 +78,16 @@
|
||||
"projects": "Projects",
|
||||
"projects-new": "New",
|
||||
"projects-open": "Open",
|
||||
"projects-settings": "Project Settings"
|
||||
"projects-settings": "Project Settings",
|
||||
"showNodeLabelDefault": "Show label of newly added nodes"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"toggle-navigator": "Toggle navigator",
|
||||
"zoom-out": "Zoom out",
|
||||
"zoom-reset": "Reset zoom",
|
||||
"zoom-in": "Zoom in"
|
||||
},
|
||||
"user": {
|
||||
"loggedInAs": "Logged in as __name__",
|
||||
"username": "Username",
|
||||
@@ -95,9 +105,10 @@
|
||||
"warning": "<strong>Warning</strong>: __message__",
|
||||
"warnings": {
|
||||
"undeployedChanges": "node has undeployed changes",
|
||||
"nodeActionDisabled": "node actions disabled within subflow",
|
||||
"nodeActionDisabled": "node actions disabled",
|
||||
"nodeActionDisabledSubflow": "node actions disabled within subflow",
|
||||
"missing-types": "<p>Flows stopped due to missing node types.</p>",
|
||||
"safe-mode":"<p>Flows stopped in safe mode.</p><p>You can modify your flows and deploy the changes to restart.",
|
||||
"safe-mode":"<p>Flows stopped in safe mode.</p><p>You can modify your flows and deploy the changes to restart.</p>",
|
||||
"restartRequired": "Node-RED must be restarted to enable upgraded modules",
|
||||
"credentials_load_failed": "<p>Flows stopped as the credentials could not be decrypted.</p><p>The flow credential file is encrypted, but the project's encryption key is missing or invalid.</p>",
|
||||
"credentials_load_failed_reset":"<p>Credentials could not be decrypted</p><p>The flow credential file is encrypted, but the project's encryption key is missing or invalid.</p><p>The flow credential file will be reset on the next deployment. Any existing flow credentials will be cleared.</p>",
|
||||
@@ -107,7 +118,6 @@
|
||||
"project_not_found": "<p>Project '__project__' not found.</p>",
|
||||
"git_merge_conflict": "<p>Automatic merging of changes failed.</p><p>Fix the unmerged conflicts then commit the results.</p>"
|
||||
},
|
||||
|
||||
"error": "<strong>Error</strong>: __message__",
|
||||
"errors": {
|
||||
"lostConnection": "Lost connection to server, reconnecting...",
|
||||
@@ -124,7 +134,7 @@
|
||||
"loaded": "Project '__project__' loaded",
|
||||
"updated": "Project '__project__' updated",
|
||||
"pull": "Project '__project__' reloaded",
|
||||
"revert": "Project '__project__' reloaded",
|
||||
"revert": "Project '__project__' reverted",
|
||||
"merge-complete": "Git merge completed"
|
||||
},
|
||||
"label": {
|
||||
@@ -139,13 +149,24 @@
|
||||
},
|
||||
"clipboard": {
|
||||
"nodes": "Nodes",
|
||||
"node": "__count__ node",
|
||||
"node_plural": "__count__ nodes",
|
||||
"configNode": "__count__ configuration node",
|
||||
"configNode_plural": "__count__ configuration nodes",
|
||||
"flow": "__count__ flow",
|
||||
"flow_plural": "__count__ flows",
|
||||
"subflow": "__count__ subflow",
|
||||
"subflow_plural": "__count__ subflows",
|
||||
"selectNodes": "Select the text above and copy to the clipboard.",
|
||||
"pasteNodes": "Paste nodes here",
|
||||
"pasteNodes": "Paste flow json or",
|
||||
"selectFile": "select a file to import",
|
||||
"importNodes": "Import nodes",
|
||||
"exportNodes": "Export nodes to clipboard",
|
||||
"exportNodes": "Export nodes",
|
||||
"download": "Download",
|
||||
"importUnrecognised": "Imported unrecognised type:",
|
||||
"importUnrecognised_plural": "Imported unrecognised types:",
|
||||
"nodesExported": "Nodes exported to clipboard",
|
||||
"nodesImported": "Imported:",
|
||||
"nodeCopied": "__count__ node copied",
|
||||
"nodeCopied_plural": "__count__ nodes copied",
|
||||
"invalidFlow": "Invalid flow: __message__",
|
||||
@@ -159,7 +180,13 @@
|
||||
},
|
||||
"import": {
|
||||
"import": "Import to",
|
||||
"newFlow": "new flow"
|
||||
"newFlow": "new flow",
|
||||
"errors": {
|
||||
"notArray": "Input not a JSON Array",
|
||||
"itemNotObject": "Input not a valid flow - item __index__ not a node object",
|
||||
"missingId": "Input not a valid flow - item __index__ missing 'id' property",
|
||||
"missingType": "Input not a valid flow - item __index__ missing 'type' property"
|
||||
}
|
||||
},
|
||||
"copyMessagePath": "Path copied",
|
||||
"copyMessageValue": "Value copied",
|
||||
@@ -205,6 +232,10 @@
|
||||
"plusNMore": "+ __count__ more"
|
||||
}
|
||||
},
|
||||
"eventLog": {
|
||||
"title": "Event log",
|
||||
"view": "View log"
|
||||
},
|
||||
"diff": {
|
||||
"unresolvedCount": "__count__ unresolved conflict",
|
||||
"unresolvedCount_plural": "__count__ unresolved conflicts",
|
||||
@@ -245,7 +276,6 @@
|
||||
"deleteSubflow": "delete subflow",
|
||||
"info": "Description",
|
||||
"category": "Category",
|
||||
"format":"markdown format",
|
||||
"errors": {
|
||||
"noNodesSelected": "<strong>Cannot create subflow</strong>: no nodes selected",
|
||||
"multipleInputsToSelection": "<strong>Cannot create subflow</strong>: multiple inputs to selection"
|
||||
@@ -263,7 +293,8 @@
|
||||
"editConfig": "Edit __type__ config node",
|
||||
"addNewType": "Add new __type__...",
|
||||
"nodeProperties": "node properties",
|
||||
"portLabels": "node settings",
|
||||
"label": "Label",
|
||||
"portLabels": "Port labels",
|
||||
"labelInputs": "Inputs",
|
||||
"labelOutputs": "Outputs",
|
||||
"settingIcon": "Icon",
|
||||
@@ -272,6 +303,8 @@
|
||||
"searchIcons": "Search icons",
|
||||
"useDefault": "use default",
|
||||
"description": "Description",
|
||||
"show": "Show",
|
||||
"hide": "Hide",
|
||||
"errors": {
|
||||
"scopeChange": "Changing the scope will make it unavailable to nodes in other flows that use it"
|
||||
}
|
||||
@@ -295,6 +328,7 @@
|
||||
"nudgeNode": "Move selected nodes (1px)",
|
||||
"moveNode": "Move selected nodes (20px)",
|
||||
"toggleSidebar": "Toggle sidebar",
|
||||
"togglePalette": "Toggle palette",
|
||||
"copyNode": "Copy selected nodes",
|
||||
"cutNode": "Cut selected nodes",
|
||||
"pasteNode": "Paste nodes",
|
||||
@@ -335,6 +369,10 @@
|
||||
"analysis": "analysis",
|
||||
"advanced": "advanced"
|
||||
},
|
||||
"actions": {
|
||||
"collapse-all": "Collapse all categories",
|
||||
"expand-all": "Expand all categories"
|
||||
},
|
||||
"event": {
|
||||
"nodeAdded": "Node added to palette:",
|
||||
"nodeAdded_plural": "Nodes added to palette",
|
||||
@@ -382,6 +420,8 @@
|
||||
"updated": "updated",
|
||||
"install": "install",
|
||||
"installed": "installed",
|
||||
"conflict": "conflict",
|
||||
"conflictTip": "<p>This module cannot be installed as it includes a<br/>node type that has already been installed</p><p>Conflicts with <code>__module__</code></p>",
|
||||
"loading": "Loading catalogues...",
|
||||
"tab-nodes": "Nodes",
|
||||
"tab-install": "Install",
|
||||
@@ -420,7 +460,6 @@
|
||||
"update": "Update"
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
},
|
||||
"sidebar": {
|
||||
@@ -430,6 +469,7 @@
|
||||
"label": "info",
|
||||
"node": "Node",
|
||||
"type": "Type",
|
||||
"module": "Module",
|
||||
"id": "ID",
|
||||
"status": "Status",
|
||||
"enabled": "Enabled",
|
||||
@@ -462,7 +502,6 @@
|
||||
"flows": "flows",
|
||||
"filterUnused":"unused",
|
||||
"filterAll":"all",
|
||||
"deleteUnused":"Delete unused",
|
||||
"filtered": "__count__ hidden"
|
||||
},
|
||||
"context": {
|
||||
@@ -473,7 +512,8 @@
|
||||
"empty": "empty",
|
||||
"node": "Node",
|
||||
"flow": "Flow",
|
||||
"global": "Global"
|
||||
"global": "Global",
|
||||
"deleteConfirm": "Are you sure you want to delete this item?"
|
||||
},
|
||||
"palette": {
|
||||
"name": "Palette management",
|
||||
@@ -489,7 +529,9 @@
|
||||
"editDescription": "Edit project description",
|
||||
"editDependencies": "Edit project dependencies",
|
||||
"editReadme": "Edit README.md",
|
||||
"showProjectSettings": "Show project settings",
|
||||
"projectSettings": {
|
||||
"title": "Project Settings",
|
||||
"edit": "edit",
|
||||
"none": "None",
|
||||
"install": "install",
|
||||
@@ -551,6 +593,11 @@
|
||||
"versionControl": {
|
||||
"unstagedChanges": "Unstaged changes",
|
||||
"stagedChanges": "Staged changes",
|
||||
"unstageChange": "Unstage change",
|
||||
"stageChange": "Stage change",
|
||||
"unstageAllChange": "Unstage all changes",
|
||||
"stageAllChange": "Stage all changes",
|
||||
"commitChanges": "Commit changes",
|
||||
"resolveConflicts": "Resolve conflicts",
|
||||
"head": "HEAD",
|
||||
"staged": "Staged",
|
||||
@@ -614,7 +661,9 @@
|
||||
"commitsAheadAndBehind2": "__count__ commit ahead of the remote. ",
|
||||
"commitsAheadAndBehind2_plural": "__count__ commits ahead of the remote. ",
|
||||
"commitsAheadAndBehind3": "You must pull the remote commit down before pushing.",
|
||||
"commitsAheadAndBehind3_plural": "You must pull the remote commits down before pushing."
|
||||
"commitsAheadAndBehind3_plural": "You must pull the remote commits down before pushing.",
|
||||
"refreshCommitHistory": "Refresh commit history",
|
||||
"refreshChanges": "Refresh changes"
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -665,7 +714,20 @@
|
||||
"format": "format JSON"
|
||||
},
|
||||
"markdownEditor": {
|
||||
"title": "Markdown editor"
|
||||
"title": "Markdown editor",
|
||||
"format": "Formatted with markdown",
|
||||
"heading1": "Heading 1",
|
||||
"heading2": "Heading 2",
|
||||
"heading3": "Heading 3",
|
||||
"bold": "Bold",
|
||||
"italic": "Italic",
|
||||
"code": "Code",
|
||||
"ordered-list": "Ordered list",
|
||||
"unordered-list": "Unordered list",
|
||||
"quote": "Quote",
|
||||
"link": "Link",
|
||||
"horizontal-rule": "Horizontal rule",
|
||||
"toggle-preview": "Toggle preview"
|
||||
},
|
||||
"bufferEditor": {
|
||||
"title": "Buffer editor",
|
||||
@@ -835,5 +897,10 @@
|
||||
"unexpected": "An unexpected error occurred",
|
||||
"code": "code"
|
||||
}
|
||||
},
|
||||
"editor-tab": {
|
||||
"properties": "Properties",
|
||||
"description": "Description",
|
||||
"appearance": "Appearance"
|
||||
}
|
||||
}
|
14
packages/node_modules/@node-red/editor-api/lib/editor/locales/en-US/jsonata.json → packages/node_modules/@node-red/editor-client/locales/en-US/jsonata.json
vendored
Normal file → Executable file
14
packages/node_modules/@node-red/editor-api/lib/editor/locales/en-US/jsonata.json → packages/node_modules/@node-red/editor-client/locales/en-US/jsonata.json
vendored
Normal file → Executable file
@@ -115,7 +115,6 @@
|
||||
"args": "array",
|
||||
"desc": "Returns the mean value of an `array` of numbers. It is an error if the input `array` contains an item which isn't a number."
|
||||
},
|
||||
|
||||
"$boolean": {
|
||||
"args": "arg",
|
||||
"desc": "Casts the argument to a Boolean using the following rules:\n\n - `Boolean` : unchanged\n - `string`: empty : `false`\n - `string`: non-empty : `true`\n - `number`: `0` : `false`\n - `number`: non-zero : `true`\n - `null` : `false`\n - `array`: empty : `false`\n - `array`: contains a member that casts to `true` : `true`\n - `array`: all members cast to `false` : `false`\n - `object`: empty : `false`\n - `object`: non-empty : `true`\n - `function` : `false`"
|
||||
@@ -219,5 +218,18 @@
|
||||
"$env": {
|
||||
"args": "arg",
|
||||
"desc": "Returns the value of an environment variable.\n\nThis is a Node-RED defined function."
|
||||
},
|
||||
"$eval": {
|
||||
"args": "expr [, context]",
|
||||
"desc": "Parses and evaluates the string `expr` which contains literal JSON or a JSONata expression using the current context as the context for evaluation."
|
||||
},
|
||||
"$formatInteger": {
|
||||
"args": "number, picture",
|
||||
"desc": "Casts the `number` to a string and formats it to an integer representation as specified by the `picture` string. The picture string parameter defines how the number is formatted and has the same syntax as `fn:format-integer` from the XPath F&O 3.1 specification."
|
||||
},
|
||||
"$parseInteger": {
|
||||
"args": "string, picture",
|
||||
"desc": "Parses the contents of the `string` parameter to an integer (as a JSON number) using the format specified by the `picture` string. The `picture` string parameter has the same format as `$formatInteger`."
|
||||
|
||||
}
|
||||
}
|
131
packages/node_modules/@node-red/editor-api/lib/editor/locales/ja/editor.json → packages/node_modules/@node-red/editor-client/locales/ja/editor.json
vendored
Normal file → Executable file
131
packages/node_modules/@node-red/editor-api/lib/editor/locales/ja/editor.json → packages/node_modules/@node-red/editor-client/locales/ja/editor.json
vendored
Normal file → Executable file
@@ -23,11 +23,11 @@
|
||||
"confirmDelete": "削除の確認",
|
||||
"delete": "本当に '__label__' を削除しますか?",
|
||||
"dropFlowHere": "ここにフローをドロップしてください",
|
||||
"addFlow": "フローの追加",
|
||||
"status": "状態",
|
||||
"enabled": "有効",
|
||||
"disabled": "無効",
|
||||
"info": "詳細",
|
||||
"tip": "マークダウン形式で記述した「詳細」は「情報タブ」に表示されます。"
|
||||
"info": "詳細"
|
||||
},
|
||||
"menu": {
|
||||
"label": {
|
||||
@@ -46,6 +46,9 @@
|
||||
"sidebar": {
|
||||
"show": "サイドバーを表示"
|
||||
},
|
||||
"palette": {
|
||||
"show": "パレットを表示"
|
||||
},
|
||||
"settings": "設定",
|
||||
"userSettings": "ユーザ設定",
|
||||
"nodes": "ノード",
|
||||
@@ -75,9 +78,16 @@
|
||||
"projects": "プロジェクト",
|
||||
"projects-new": "新規",
|
||||
"projects-open": "開く",
|
||||
"projects-settings": "設定"
|
||||
"projects-settings": "設定",
|
||||
"showNodeLabelDefault": "追加したノードのラベルを表示する"
|
||||
}
|
||||
},
|
||||
"actions": {
|
||||
"toggle-navigator": "ナビゲータの表示/非表示を切替",
|
||||
"zoom-out": "縮小",
|
||||
"zoom-reset": "拡大/縮小を初期化",
|
||||
"zoom-in": "拡大"
|
||||
},
|
||||
"user": {
|
||||
"loggedInAs": "__name__ としてログインしました",
|
||||
"username": "ユーザ名",
|
||||
@@ -95,8 +105,10 @@
|
||||
"warning": "<strong>警告</strong>: __message__",
|
||||
"warnings": {
|
||||
"undeployedChanges": "ノードの変更をデプロイしていません",
|
||||
"nodeActionDisabled": "ノードのアクションは、サブフロー内で無効になっています",
|
||||
"nodeActionDisabled": "ノードのアクションは無効になっています",
|
||||
"nodeActionDisabledSubflow": "ノードのアクションは、サブフロー内で無効になっています",
|
||||
"missing-types": "不明なノードが存在するため、フローを停止しました。詳細はログを確認してください。",
|
||||
"safe-mode": "<p>セーフモードでフローを停止しました</p><p>フローを変更し、再起動するために変更をデプロイできます</p>",
|
||||
"restartRequired": "更新されたモジュールを有効化するため、Node-REDを再起動する必要があります",
|
||||
"credentials_load_failed": "<p>認証情報を復号できないため、フローを停止しました</p><p>フローの認証情報ファイルは暗号化されています。しかし、プロジェクトの暗号鍵が存在しない、または不正です</p>",
|
||||
"credentials_load_failed_reset": "<p>認証情報を復号できません</p><p>フローの認証情報ファイルは暗号化されています。しかし、プロジェクトの暗号鍵が存在しない、または不正です。</p><p>次回のデプロイでフローの認証情報ファイルがリセットされます。既存フローの認証情報は削除されます。</p>",
|
||||
@@ -113,7 +125,7 @@
|
||||
"lostConnectionTry": "すぐに接続",
|
||||
"cannotAddSubflowToItself": "サブフロー自身を追加できません",
|
||||
"cannotAddCircularReference": "循環参照を検出したため、サブフローを追加できません",
|
||||
"unsupportedVersion": "サポートされていないバージョンのNode.jsを使用しています。<br/>最新のNode.js LTSに更新してください。",
|
||||
"unsupportedVersion": "<p>サポートされていないバージョンのNode.jsを使用しています。</p><p><br/>最新のNode.js LTSに更新してください。</p>",
|
||||
"failedToAppendNode": "<p>'__module__'がロードできませんでした。</p><p>__error__</p>"
|
||||
},
|
||||
"project": {
|
||||
@@ -122,7 +134,7 @@
|
||||
"loaded": "プロジェクト'__project__'をロードしました",
|
||||
"updated": "プロジェクト'__project__'を更新しました",
|
||||
"pull": "プロジェクト'__project__'を再ロードしました",
|
||||
"revert": "プロジェクト'__project__'を再ロードしました",
|
||||
"revert": "プロジェクト'__project__'を取り消しました",
|
||||
"merge-complete": "Gitマージが完了しました"
|
||||
},
|
||||
"label": {
|
||||
@@ -137,13 +149,24 @@
|
||||
},
|
||||
"clipboard": {
|
||||
"nodes": "ノード",
|
||||
"node": "__count__ 個のノード",
|
||||
"node_plural": "__count__ 個のノード",
|
||||
"configNode": "__count__ 個の設定ノード",
|
||||
"configNode_plural": "__count__ 個の設定ノード",
|
||||
"flow": "__count__ 個のフロー",
|
||||
"flow_plural": "__count__ 個のフロー",
|
||||
"subflow": "__count__ 個のサブフロー",
|
||||
"subflow_plural": "__count__ 個のサブフロー",
|
||||
"selectNodes": "上のテキストを選択し、クリップボードへコピーしてください",
|
||||
"pasteNodes": "JSON形式のフローデータを貼り付けてください",
|
||||
"selectFile": "読み込むファイルを選択してください",
|
||||
"importNodes": "フローをクリップボートから読み込み",
|
||||
"exportNodes": "フローをクリップボードへ書き出し",
|
||||
"download": "ダウンロード",
|
||||
"importUnrecognised": "認識できない型が読み込まれました:",
|
||||
"importUnrecognised_plural": "認識できない型が読み込まれました:",
|
||||
"nodesExported": "クリップボードへフローを書き出しました",
|
||||
"nodesImported": "読み込みました:",
|
||||
"nodeCopied": "__count__ 個のノードをコピーしました",
|
||||
"nodeCopied_plural": "__count__ 個のノードをコピーしました",
|
||||
"invalidFlow": "不正なフロー: __message__",
|
||||
@@ -157,7 +180,13 @@
|
||||
},
|
||||
"import": {
|
||||
"import": "読み込み先",
|
||||
"newFlow": "新規のタブ"
|
||||
"newFlow": "新規のタブ",
|
||||
"errors": {
|
||||
"notArray": "JSON形式の配列ではありません",
|
||||
"itemNotObject": "不正なフロー - __index__ 番目の要素はノードオブジェクトではありません",
|
||||
"missingId": "不正なフロー - __index__ 番目の要素に'id'プロパティがありません",
|
||||
"missingType": "不正なフロー - __index__ 番目の要素に'type'プロパティがありません"
|
||||
}
|
||||
},
|
||||
"copyMessagePath": "パスをコピーしました",
|
||||
"copyMessageValue": "値をコピーしました",
|
||||
@@ -171,7 +200,10 @@
|
||||
"modifiedFlowsDesc": "変更したノードを含むフローのみデプロイ",
|
||||
"modifiedNodes": "変更したノード",
|
||||
"modifiedNodesDesc": "変更したノードのみデプロイ",
|
||||
"restartFlows": "フローを再起動",
|
||||
"restartFlowsDesc": "デプロイされた現在のフローを再起動",
|
||||
"successfulDeploy": "デプロイが成功しました",
|
||||
"successfulRestart": "フローの再起動が成功しました",
|
||||
"deployFailed": "デプロイが失敗しました: __message__",
|
||||
"unusedConfigNodes": "使われていない「ノードの設定」があります。",
|
||||
"unusedConfigNodesLink": "設定を参照する",
|
||||
@@ -192,7 +224,7 @@
|
||||
"unknown": "ワークスペースに未知の型のノードがあります。",
|
||||
"confirm": "このままデプロイしても良いですか?",
|
||||
"doNotWarn": "この警告を再度表示しない",
|
||||
"conflict": "フローを編集している間に、他のブラウザがフローをデプロイしました。デプロイを継続すると、他のブラウザがデプロイしたフローが削除されます。",
|
||||
"conflict": "フローを編集している間に、他のブラウザがフローをデプロイしました。",
|
||||
"backgroundUpdate": "サーバ上のフローが更新されました",
|
||||
"conflictChecking": "変更を自動的にマージしてよいか確認してください。",
|
||||
"conflictAutoMerge": "変更の衝突がないため、自動的にマージできます。",
|
||||
@@ -200,6 +232,10 @@
|
||||
"plusNMore": "さらに __count__ 個"
|
||||
}
|
||||
},
|
||||
"eventLog": {
|
||||
"title": "イベントログ",
|
||||
"view": "ログを確認"
|
||||
},
|
||||
"diff": {
|
||||
"unresolvedCount": "未解決の衝突 __count__",
|
||||
"unresolvedCount_plural": "未解決の衝突 __count__",
|
||||
@@ -240,7 +276,6 @@
|
||||
"deleteSubflow": "サブフローを削除",
|
||||
"info": "詳細",
|
||||
"category": "カテゴリ",
|
||||
"format": "マークダウン形式",
|
||||
"errors": {
|
||||
"noNodesSelected": "<strong>サブフローを作成できません</strong>: ノードが選択されていません",
|
||||
"multipleInputsToSelection": "<strong>サブフローを作成できません</strong>: 複数の入力が選択されています"
|
||||
@@ -258,15 +293,18 @@
|
||||
"editConfig": "__type__ ノードの設定を編集",
|
||||
"addNewType": "新規に __type__ を追加...",
|
||||
"nodeProperties": "プロパティ",
|
||||
"portLabels": "設定",
|
||||
"label": "ラベル",
|
||||
"portLabels": "ポートラベル",
|
||||
"labelInputs": "入力",
|
||||
"labelOutputs": "出力",
|
||||
"settingIcon": "アイコン",
|
||||
"noDefaultLabel": "なし",
|
||||
"defaultLabel": "既定の名前を使用",
|
||||
"defaultLabel": "既定のラベルを使用",
|
||||
"searchIcons": "アイコンを検索",
|
||||
"useDefault": "デフォルトを使用",
|
||||
"useDefault": "デフォルトを使用",
|
||||
"description": "詳細",
|
||||
"show": "表示",
|
||||
"hide": "非表示",
|
||||
"errors": {
|
||||
"scopeChange": "スコープの変更は、他のフローで使われているノードを無効にします"
|
||||
}
|
||||
@@ -289,7 +327,8 @@
|
||||
"exportNode": "フローの書き出し",
|
||||
"nudgeNode": "選択したノードを移動(移動量小)",
|
||||
"moveNode": "選択したノードを移動(移動量大)",
|
||||
"toggleSidebar": "サイドバーの表示非表示",
|
||||
"toggleSidebar": "サイドバーの表示/非表示",
|
||||
"togglePalette": "パレットの表示/非表示",
|
||||
"copyNode": "選択したノードをコピー",
|
||||
"cutNode": "選択したノードを切り取り",
|
||||
"pasteNode": "ノードを貼り付け",
|
||||
@@ -330,6 +369,10 @@
|
||||
"analysis": "分析",
|
||||
"advanced": "その他"
|
||||
},
|
||||
"actions": {
|
||||
"collapse-all": "全カテゴリを折畳む",
|
||||
"expand-all": "全カテゴリを展開"
|
||||
},
|
||||
"event": {
|
||||
"nodeAdded": "ノードをパレットへ追加しました:",
|
||||
"nodeAdded_plural": "ノードをパレットへ追加しました",
|
||||
@@ -377,6 +420,8 @@
|
||||
"updated": "更新済",
|
||||
"install": "ノードを追加",
|
||||
"installed": "追加しました",
|
||||
"conflict": "競合",
|
||||
"conflictTip": "<p>インストール済みのノードの種別と競合しているため<br/>ノードをインストールできません</p><p>競合: <code>__module__</code></p>",
|
||||
"loading": "カタログを読み込み中",
|
||||
"tab-nodes": "現在のノード",
|
||||
"tab-install": "ノードを追加",
|
||||
@@ -385,28 +430,28 @@
|
||||
"sortRecent": "日付順",
|
||||
"more": "+ さらに __count__ 個",
|
||||
"errors": {
|
||||
"catalogLoadFailed": "ノードのカタログの読み込みに失敗しました。<br>詳細はブラウザのコンソールを確認してください。",
|
||||
"installFailed": "追加処理が失敗しました: __module__<br>__message__<br>詳細はログを確認してください。",
|
||||
"removeFailed": "削除処理が失敗しました: __module__<br>__message__<br>詳細はログを確認してください。",
|
||||
"updateFailed": "更新処理が失敗しました: __module__<br>__message__<br>詳細はログを確認してください。",
|
||||
"enableFailed": "有効化処理が失敗しました: __module__<br>__message__<br>詳細はログを確認してください。",
|
||||
"disableFailed": "無効化処理が失敗しました: __module__<br>__message__<br>詳細はログを確認してください。"
|
||||
"catalogLoadFailed": "<p>ノードのカタログの読み込みに失敗しました。</p><p>詳細はブラウザのコンソールを確認してください。</p>",
|
||||
"installFailed": "<p.追加処理が失敗しました: __module__</p><p>__message__</p><p>詳細はログを確認してください。</p>",
|
||||
"removeFailed": "<p>削除処理が失敗しました: __module__</p><p>__message__</p><p>詳細はログを確認してください。</p>",
|
||||
"updateFailed": "<p>更新処理が失敗しました: __module__</p><p>__message__</p><p>詳細はログを確認してください。</p>",
|
||||
"enableFailed": "<p>有効化処理が失敗しました: __module__</p><p>__message__</p><p>詳細はログを確認してください。</p>",
|
||||
"disableFailed": "<p>無効化処理が失敗しました: __module__</p><p>__message__</p><p>詳細はログを確認してください。</p>"
|
||||
},
|
||||
"confirm": {
|
||||
"install": {
|
||||
"body": "ノードを追加する前に、ドキュメントを確認してください。ノードによっては、モジュールの依存関係を自動的に解決できない場合や、Node-REDの再起動が必要となる場合があります。",
|
||||
"body": "<p>__module__ をインストールします。</p><p>ノードを追加する前に、ドキュメントを確認してください。ノードによっては、モジュールの依存関係を自動的に解決できない場合や、Node-REDの再起動が必要となる場合があります。</p>",
|
||||
"title": "ノードを追加"
|
||||
},
|
||||
"remove": {
|
||||
"body": "Node-REDからノードを削除します。ノードはNode-REDが再起動されるまで、リソースを使い続けます。",
|
||||
"body": "<p>__module__ を削除します。</p><p>Node-REDからノードを削除します。ノードはNode-REDが再起動されるまで、リソースを使い続ける可能性があります。</p>",
|
||||
"title": "ノードを削除"
|
||||
},
|
||||
"update": {
|
||||
"body": "更新を完了するには手動でNode-REDを再起動する必要があります。",
|
||||
"body": "<p>__module__ を更新します。</p><p>更新を完了するには手動でNode-REDを再起動する必要があります。</p>",
|
||||
"title": "ノードの更新"
|
||||
},
|
||||
"cannotUpdate": {
|
||||
"body": "ノードの更新があります。「パレットの管理」の画面では更新されません。ドキュメントを参照し、ノードの更新手順を確認してください。"
|
||||
"body": "ノードの更新があります。「パレットの管理」の画面では更新されません。<br/><br/>ドキュメントを参照し、ノードの更新手順を確認してください。"
|
||||
},
|
||||
"button": {
|
||||
"review": "ノードの情報を参照",
|
||||
@@ -424,6 +469,7 @@
|
||||
"label": "情報",
|
||||
"node": "ノード",
|
||||
"type": "型",
|
||||
"module": "モジュール",
|
||||
"id": "ID",
|
||||
"status": "状態",
|
||||
"enabled": "有効",
|
||||
@@ -432,6 +478,7 @@
|
||||
"instances": "インスタンス",
|
||||
"properties": "プロパティ",
|
||||
"info": "情報",
|
||||
"desc": "詳細",
|
||||
"blank": "ブランク",
|
||||
"null": "ヌル",
|
||||
"showMore": "さらに表示",
|
||||
@@ -465,7 +512,8 @@
|
||||
"empty": "データが存在しません",
|
||||
"node": "Node",
|
||||
"flow": "Flow",
|
||||
"global": "Global"
|
||||
"global": "Global",
|
||||
"deleteConfirm": "データを削除しても良いですか?"
|
||||
},
|
||||
"palette": {
|
||||
"name": "パレットの管理",
|
||||
@@ -481,7 +529,9 @@
|
||||
"editDescription": "プロジェクトの詳細を編集",
|
||||
"editDependencies": "プロジェクトの依存関係を編集",
|
||||
"editReadme": "README.mdを編集",
|
||||
"showProjectSettings": "プロジェクト設定を表示",
|
||||
"projectSettings": {
|
||||
"title": "プロジェクト設定",
|
||||
"edit": "編集",
|
||||
"none": "なし",
|
||||
"install": "インストール",
|
||||
@@ -543,6 +593,11 @@
|
||||
"versionControl": {
|
||||
"unstagedChanges": "ステージングされていない変更",
|
||||
"stagedChanges": "ステージングされた変更",
|
||||
"unstageChange": "ステージングした変更の取り消し",
|
||||
"stageChange": "変更をステージング",
|
||||
"unstageAllChange": "ステージングした全ての変更の取り消し",
|
||||
"stageAllChange": "全ての変更をステージング",
|
||||
"commitChanges": "変更をコミット",
|
||||
"resolveConflicts": "コンフリクトの解決",
|
||||
"head": "最新",
|
||||
"staged": "ステージング",
|
||||
@@ -606,7 +661,9 @@
|
||||
"commitsAheadAndBehind2": "__count__コミット進んでいます。 ",
|
||||
"commitsAheadAndBehind2_plural": "__count__コミット進んでいます。 ",
|
||||
"commitsAheadAndBehind3": "プッシュする前にリモートのコミットをプルしてください。",
|
||||
"commitsAheadAndBehind3_plural": "プッシュする前にリモートのコミットをプルしてください。"
|
||||
"commitsAheadAndBehind3_plural": "プッシュする前にリモートのコミットをプルしてください。",
|
||||
"refreshCommitHistory": "コミット履歴を更新",
|
||||
"refreshChanges": "変更を更新"
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -657,7 +714,20 @@
|
||||
"format": "JSONフォーマット"
|
||||
},
|
||||
"markdownEditor": {
|
||||
"title": "マークダウンエディタ"
|
||||
"title": "マークダウンエディタ",
|
||||
"format": "マークダウン形式で記述",
|
||||
"heading1": "見出しレベル1",
|
||||
"heading2": "見出しレベル2",
|
||||
"heading3": "見出しレベル3",
|
||||
"bold": "太字",
|
||||
"italic": "斜体",
|
||||
"code": "コード",
|
||||
"ordered-list": "箇条書き(番号付き)",
|
||||
"unordered-list": "箇条書き",
|
||||
"quote": "引用",
|
||||
"link": "リンク",
|
||||
"horizontal-rule": "区切り線",
|
||||
"toggle-preview": "プレビュー表示切替え"
|
||||
},
|
||||
"bufferEditor": {
|
||||
"title": "バッファエディタ",
|
||||
@@ -721,7 +791,7 @@
|
||||
"repo-not-found": "リポジトリが見つかりません"
|
||||
},
|
||||
"default-files": {
|
||||
"create": "プロジェクト関連ファアイルの作成",
|
||||
"create": "プロジェクト関連ファイルの作成",
|
||||
"desc0": "プロジェクトはフローファイル、README、package.jsonを含みます。",
|
||||
"desc1": "その他、Gitリポジトリで管理したいファイルを含めても構いません。",
|
||||
"desc2": "既存のフローと認証情報ファイルをプロジェクトにコピーします。",
|
||||
@@ -737,7 +807,7 @@
|
||||
"desc4": "認証情報を公開Gitリポジトリに保存する際には、秘密キーフレーズによって暗号化します。",
|
||||
"desc5": "フロー認証情報ファイルはsettingsファイルのcredentialSecretプロパティで暗号化されています。",
|
||||
"desc6": "フロー認証情報ファイルはシステムが生成したキーによって暗号化されています。このプロジェクト用に新しい秘密キーを指定してください。",
|
||||
"desc7": "キーはプロジェクトファイルとば別に保存されます。他のNode-REDでこのプロジェクトを利用するには、このプロジェクトのキーが必要です。",
|
||||
"desc7": "キーはプロジェクトファイルとは別に保存されます。他のNode-REDでこのプロジェクトを利用するには、このプロジェクトのキーが必要です。",
|
||||
"credentials": "認証情報",
|
||||
"enable": "暗号化を有効にする",
|
||||
"disable": "暗号化を無効にする",
|
||||
@@ -827,5 +897,10 @@
|
||||
"unexpected": "予期しないエラーが発生しました",
|
||||
"code": "コード"
|
||||
}
|
||||
},
|
||||
"editor-tab": {
|
||||
"properties": "プロパティ",
|
||||
"description": "説明",
|
||||
"appearance": "外観"
|
||||
}
|
||||
}
|
@@ -22,8 +22,7 @@
|
||||
"status": "状态",
|
||||
"enabled": "有效",
|
||||
"disabled": "无效",
|
||||
"info": "详细描述",
|
||||
"tip": "详细描述支持Markdown轻量级标记语言,并将出现在信息标签中。"
|
||||
"info": "详细描述"
|
||||
},
|
||||
"menu": {
|
||||
"label": {
|
||||
@@ -86,7 +85,7 @@
|
||||
"warning": "<strong>警告</strong>: __message__",
|
||||
"warnings": {
|
||||
"undeployedChanges": "节点中存在未部署的更改",
|
||||
"nodeActionDisabled": "节点动作在子流程中被禁用",
|
||||
"nodeActionDisabledSubflow": "节点动作在子流程中被禁用",
|
||||
"missing-types": "流程由于缺少节点类型而停止。请检查日志的详细信息",
|
||||
"restartRequired": "Node-RED必须重新启动,以启用升级的模块"
|
||||
},
|
||||
@@ -191,7 +190,6 @@
|
||||
"output": "输出:",
|
||||
"deleteSubflow": "删除子流程",
|
||||
"info": "详细描述",
|
||||
"format": "标记格式",
|
||||
"errors": {
|
||||
"noNodesSelected": "<strong>无法创建子流程</strong>: 未选择节点",
|
||||
"multipleInputsToSelection": "<strong>无法创建子流程</strong>: 多个输入到了选择"
|
@@ -1,14 +1,18 @@
|
||||
{
|
||||
"name": "@node-red/editor-client",
|
||||
"version": "0.20.0-alpha.0",
|
||||
"license": "Apache-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/node-red/node-red.git"
|
||||
},
|
||||
"contributors": [
|
||||
{ "name": "Nick O'Leary" },
|
||||
{ "name": "Dave Conway-Jones"}
|
||||
],
|
||||
"main": "./lib/index.js"
|
||||
"name": "@node-red/editor-client",
|
||||
"version": "0.20.0-beta.4",
|
||||
"license": "Apache-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/node-red/node-red.git"
|
||||
},
|
||||
"contributors": [
|
||||
{
|
||||
"name": "Nick O'Leary"
|
||||
},
|
||||
{
|
||||
"name": "Dave Conway-Jones"
|
||||
}
|
||||
],
|
||||
"main": "./lib/index.js"
|
||||
}
|
||||
|
50
packages/node_modules/@node-red/editor-client/src/ace/README.md
vendored
Normal file
50
packages/node_modules/@node-red/editor-client/src/ace/README.md
vendored
Normal file
@@ -0,0 +1,50 @@
|
||||
How to build the custom ACE modes for Node-RED
|
||||
----------------------------------------------
|
||||
|
||||
Node-RED includes custom JSONata and JavaScript modes.
|
||||
|
||||
|
||||
## JSONata
|
||||
|
||||
The `ace/mode/jsonata` mode is maintained under `editor-client/src/vendor/jsonata`.
|
||||
Those files are edited in place and copied into the build by Grunt.
|
||||
|
||||
## JavaScript
|
||||
|
||||
The `ace/mode/nrjavascript` mode is used exclusively by the Function node. It
|
||||
inherits almost entirely from the normal JavaScript mode. The one key difference
|
||||
is that it wraps the code with a Function before parsing. This is required to
|
||||
avoid some false-flagged errors.
|
||||
|
||||
The source of the mode is under `editor-client/src/ace/mode`. If those files are
|
||||
modified in anyway, they *must* be manually built to generate the files under
|
||||
`editor-client/src/ace/bin` and checked in. Those files are the ones the Grunt
|
||||
built copies out in the Node-RED build.
|
||||
|
||||
### Building the mode files
|
||||
|
||||
|
||||
#### Setup build environment
|
||||
|
||||
cd /tmp/
|
||||
git clone https://github.com/ajaxorg/ace.git
|
||||
cd ace
|
||||
npm install
|
||||
|
||||
#### Copy mode src files into build environment
|
||||
|
||||
cd <node-red-source-directory
|
||||
cp packages/node_modules/@node-red/editor-client/src/ace/mode/* \
|
||||
/tmp/ace/lib/ace/mode/
|
||||
|
||||
#### Run the build
|
||||
|
||||
cd /tmp/ace
|
||||
node ./Makefile.dryice.js -m -nc
|
||||
|
||||
#### Copy the built versions back
|
||||
|
||||
cp build/src-min-noconflict/*-nrjavascript.js \
|
||||
<node-red-source-directory>/packages/node_modules/@node-red/editor-client/src/ace/bin/
|
||||
cp build/src-min-noconflict/snippets/nrjavascript.js \
|
||||
<node-red-source-directory>/packages/node_modules/@node-red/editor-client/src/ace/bin/snippets/
|
9
packages/node_modules/@node-red/editor-client/src/ace/bin/mode-nrjavascript.js
vendored
Normal file
9
packages/node_modules/@node-red/editor-client/src/ace/bin/mode-nrjavascript.js
vendored
Normal file
File diff suppressed because one or more lines are too long
9
packages/node_modules/@node-red/editor-client/src/ace/bin/snippets/nrjavascript.js
vendored
Normal file
9
packages/node_modules/@node-red/editor-client/src/ace/bin/snippets/nrjavascript.js
vendored
Normal file
@@ -0,0 +1,9 @@
|
||||
ace.define("ace/snippets/nrjavascript",[],function(e,t,n){"use strict";t.snippetText=undefined,t.scope="nrjavascript"});
|
||||
(function() {
|
||||
ace.require(["ace/snippets/nrjavascript"], function(m) {
|
||||
if (typeof module == "object" && typeof exports == "object" && module) {
|
||||
module.exports = m;
|
||||
}
|
||||
});
|
||||
})();
|
||||
|
1
packages/node_modules/@node-red/editor-client/src/ace/bin/worker-nrjavascript.js
vendored
Normal file
1
packages/node_modules/@node-red/editor-client/src/ace/bin/worker-nrjavascript.js
vendored
Normal file
File diff suppressed because one or more lines are too long
49
packages/node_modules/@node-red/editor-client/src/ace/mode/nrjavascript.js
vendored
Normal file
49
packages/node_modules/@node-red/editor-client/src/ace/mode/nrjavascript.js
vendored
Normal file
@@ -0,0 +1,49 @@
|
||||
/**
|
||||
* 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.
|
||||
**/
|
||||
define(function(require, exports, module) {
|
||||
"use strict";
|
||||
|
||||
var oop = require("../lib/oop");
|
||||
var JavaScriptMode = require("./javascript").Mode;
|
||||
var WorkerClient = require("../worker/worker_client").WorkerClient;
|
||||
|
||||
var Mode = function() {
|
||||
// Inherit everything from the standard JavaScript mode
|
||||
JavaScriptMode.call(this);
|
||||
};
|
||||
oop.inherits(Mode, JavaScriptMode);
|
||||
|
||||
(function() {
|
||||
// Insert our custom worker
|
||||
this.createWorker = function(session) {
|
||||
var worker = new WorkerClient(["ace"], "ace/mode/nrjavascript_worker", "NRJavaScriptWorker");
|
||||
worker.attachToDocument(session.getDocument());
|
||||
|
||||
worker.on("annotate", function(results) {
|
||||
session.setAnnotations(results.data);
|
||||
});
|
||||
|
||||
worker.on("terminate", function() {
|
||||
session.clearAnnotations();
|
||||
});
|
||||
|
||||
return worker;
|
||||
};
|
||||
|
||||
this.$id = "ace/mode/nrjavascript";
|
||||
}).call(Mode.prototype);
|
||||
exports.Mode = Mode;
|
||||
});
|
189
packages/node_modules/@node-red/editor-client/src/ace/mode/nrjavascript_worker.js
vendored
Normal file
189
packages/node_modules/@node-red/editor-client/src/ace/mode/nrjavascript_worker.js
vendored
Normal file
@@ -0,0 +1,189 @@
|
||||
/* ***** BEGIN LICENSE BLOCK *****
|
||||
* Distributed under the BSD license:
|
||||
*
|
||||
* Copyright (c) 2010, Ajax.org B.V.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* * Neither the name of Ajax.org B.V. nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY
|
||||
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
|
||||
define(function(require, exports, module) {
|
||||
"use strict";
|
||||
|
||||
var oop = require("../lib/oop");
|
||||
var Mirror = require("../worker/mirror").Mirror;
|
||||
var lint = require("./javascript/jshint").JSHINT;
|
||||
|
||||
function startRegex(arr) {
|
||||
return RegExp("^(" + arr.join("|") + ")");
|
||||
}
|
||||
|
||||
var disabledWarningsRe = startRegex([
|
||||
"Bad for in variable '(.+)'.",
|
||||
'Missing "use strict"'
|
||||
]);
|
||||
var errorsRe = startRegex([
|
||||
"Unexpected",
|
||||
"Expected ",
|
||||
"Confusing (plus|minus)",
|
||||
"\\{a\\} unterminated regular expression",
|
||||
"Unclosed ",
|
||||
"Unmatched ",
|
||||
"Unbegun comment",
|
||||
"Bad invocation",
|
||||
"Missing space after",
|
||||
"Missing operator at"
|
||||
]);
|
||||
var infoRe = startRegex([
|
||||
"Expected an assignment",
|
||||
"Bad escapement of EOL",
|
||||
"Unexpected comma",
|
||||
"Unexpected space",
|
||||
"Missing radix parameter.",
|
||||
"A leading decimal point can",
|
||||
"\\['{a}'\\] is better written in dot notation.",
|
||||
"'{a}' used out of scope"
|
||||
]);
|
||||
|
||||
var NRJavaScriptWorker = exports.NRJavaScriptWorker = function(sender) {
|
||||
Mirror.call(this, sender);
|
||||
this.setTimeout(500);
|
||||
this.setOptions();
|
||||
};
|
||||
|
||||
oop.inherits(NRJavaScriptWorker, Mirror);
|
||||
|
||||
(function() {
|
||||
this.setOptions = function(options) {
|
||||
this.options = options || {
|
||||
// undef: true,
|
||||
// unused: true,
|
||||
esnext: true,
|
||||
moz: true,
|
||||
devel: true,
|
||||
browser: true,
|
||||
node: true,
|
||||
laxcomma: true,
|
||||
laxbreak: true,
|
||||
lastsemic: true,
|
||||
onevar: false,
|
||||
passfail: false,
|
||||
maxerr: 100,
|
||||
expr: true,
|
||||
multistr: true,
|
||||
globalstrict: true
|
||||
};
|
||||
this.doc.getValue() && this.deferredUpdate.schedule(100);
|
||||
};
|
||||
|
||||
this.changeOptions = function(newOptions) {
|
||||
oop.mixin(this.options, newOptions);
|
||||
this.doc.getValue() && this.deferredUpdate.schedule(100);
|
||||
};
|
||||
|
||||
this.isValidJS = function(str) {
|
||||
try {
|
||||
// evaluated code can only create variables in this function
|
||||
eval("throw 0;" + str);
|
||||
} catch(e) {
|
||||
if (e === 0)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
this.onUpdate = function() {
|
||||
var value = this.doc.getValue();
|
||||
value = value.replace(/^#!.*\n/, "\n");
|
||||
if (!value)
|
||||
return this.sender.emit("annotate", []);
|
||||
|
||||
// [Node-RED] wrap the code in a function
|
||||
value = "async function __nodered__(msg) {\n"+value+"\n}";
|
||||
|
||||
var errors = [];
|
||||
// jshint reports many false errors
|
||||
// report them as error only if code is actually invalid
|
||||
var maxErrorLevel = this.isValidJS(value) ? "warning" : "error";
|
||||
|
||||
// var start = new Date();
|
||||
lint(value, this.options, this.options.globals);
|
||||
var results = lint.errors;
|
||||
|
||||
var errorAdded = false;
|
||||
for (var i = 0; i < results.length; i++) {
|
||||
var error = results[i];
|
||||
if (!error)
|
||||
continue;
|
||||
var raw = error.raw;
|
||||
var type = "warning";
|
||||
|
||||
if (raw == "Missing semicolon.") {
|
||||
var str = error.evidence.substr(error.character);
|
||||
str = str.charAt(str.search(/\S/));
|
||||
if (maxErrorLevel == "error" && str && /[\w\d{(['"]/.test(str)) {
|
||||
error.reason = 'Missing ";" before statement';
|
||||
type = "error";
|
||||
} else {
|
||||
type = "info";
|
||||
}
|
||||
}
|
||||
else if (disabledWarningsRe.test(raw)) {
|
||||
continue;
|
||||
}
|
||||
else if (infoRe.test(raw)) {
|
||||
type = "info";
|
||||
}
|
||||
else if (errorsRe.test(raw)) {
|
||||
errorAdded = true;
|
||||
type = maxErrorLevel;
|
||||
}
|
||||
else if (raw == "'{a}' is not defined.") {
|
||||
type = "warning";
|
||||
}
|
||||
else if (raw == "'{a}' is defined but never used.") {
|
||||
type = "info";
|
||||
}
|
||||
|
||||
errors.push({
|
||||
// [Node-RED] offset the row for the added line
|
||||
row: error.line-2,
|
||||
column: error.character-1,
|
||||
text: error.reason,
|
||||
type: type,
|
||||
raw: raw
|
||||
});
|
||||
|
||||
if (errorAdded) {
|
||||
// break;
|
||||
}
|
||||
}
|
||||
// console.log("lint time: " + (new Date() - start));
|
||||
|
||||
this.sender.emit("annotate", errors);
|
||||
};
|
||||
|
||||
}).call(NRJavaScriptWorker.prototype);
|
||||
|
||||
});
|
@@ -75,29 +75,39 @@ RED.comms = (function() {
|
||||
}
|
||||
ws.onmessage = function(event) {
|
||||
var message = JSON.parse(event.data);
|
||||
for (var m = 0; m < message.length; m++) {
|
||||
var msg = message[m];
|
||||
if (pendingAuth && msg.auth) {
|
||||
if (msg.auth === "ok") {
|
||||
if (message.auth) {
|
||||
if (pendingAuth) {
|
||||
if (message.auth === "ok") {
|
||||
pendingAuth = false;
|
||||
completeConnection();
|
||||
} else if (msg.auth === "fail") {
|
||||
} else if (message.auth === "fail") {
|
||||
// anything else is an error...
|
||||
active = false;
|
||||
RED.user.login({updateMenu:true},function() {
|
||||
connectWS();
|
||||
})
|
||||
}
|
||||
} else if (message.auth === "fail") {
|
||||
// Our current session has expired
|
||||
active = false;
|
||||
RED.user.login({updateMenu:true},function() {
|
||||
connectWS();
|
||||
})
|
||||
}
|
||||
else if (msg.topic) {
|
||||
for (var t in subscriptions) {
|
||||
if (subscriptions.hasOwnProperty(t)) {
|
||||
var re = new RegExp("^"+t.replace(/([\[\]\?\(\)\\\\$\^\*\.|])/g,"\\$1").replace(/\+/g,"[^/]+").replace(/\/#$/,"(\/.*)?")+"$");
|
||||
if (re.test(msg.topic)) {
|
||||
var subscribers = subscriptions[t];
|
||||
if (subscribers) {
|
||||
for (var i=0;i<subscribers.length;i++) {
|
||||
subscribers[i](msg.topic,msg.data);
|
||||
} else {
|
||||
// Otherwise, 'message' is an array of actual comms messages
|
||||
for (var m = 0; m < message.length; m++) {
|
||||
var msg = message[m];
|
||||
if (msg.topic) {
|
||||
for (var t in subscriptions) {
|
||||
if (subscriptions.hasOwnProperty(t)) {
|
||||
var re = new RegExp("^"+t.replace(/([\[\]\?\(\)\\\\$\^\*\.|])/g,"\\$1").replace(/\+/g,"[^/]+").replace(/\/#$/,"(\/.*)?")+"$");
|
||||
if (re.test(msg.topic)) {
|
||||
var subscribers = subscriptions[t];
|
||||
if (subscribers) {
|
||||
for (var i=0;i<subscribers.length;i++) {
|
||||
subscribers[i](msg.topic,msg.data);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -132,10 +142,10 @@ RED.comms = (function() {
|
||||
connectWS();
|
||||
} else {
|
||||
var msg = RED._("notification.errors.lostConnectionReconnect",{time: connectCountdown})+' <a href="#">'+ RED._("notification.errors.lostConnectionTry")+'</a>';
|
||||
errornotification.update(msg);
|
||||
errornotification.update(msg,{silent:true});
|
||||
$(errornotification).find("a").click(function(e) {
|
||||
e.preventDefault();
|
||||
errornotification.update(RED._("notification.errors.lostConnection"));
|
||||
errornotification.update(RED._("notification.errors.lostConnection"),{silent:true});
|
||||
clearInterval(connectCountdownTimer);
|
||||
connectWS();
|
||||
})
|
||||
|
831
packages/node_modules/@node-red/editor-client/src/js/font-awesome.js
vendored
Normal file
831
packages/node_modules/@node-red/editor-client/src/js/font-awesome.js
vendored
Normal file
@@ -0,0 +1,831 @@
|
||||
/**
|
||||
* 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.nodes.fontAwesome = (function() {
|
||||
|
||||
var iconMap = {
|
||||
"fa-address-book-o": "\uf2ba",
|
||||
"fa-address-book": "\uf2b9",
|
||||
"fa-address-card-o": "\uf2bc",
|
||||
"fa-address-card": "\uf2bb",
|
||||
"fa-adjust": "\uf042",
|
||||
"fa-align-center": "\uf037",
|
||||
"fa-align-justify": "\uf039",
|
||||
"fa-align-left": "\uf036",
|
||||
"fa-align-right": "\uf038",
|
||||
"fa-ambulance": "\uf0f9",
|
||||
"fa-american-sign-language-interpreting": "\uf2a3",
|
||||
"fa-anchor": "\uf13d",
|
||||
"fa-angle-double-down": "\uf103",
|
||||
"fa-angle-double-left": "\uf100",
|
||||
"fa-angle-double-right": "\uf101",
|
||||
"fa-angle-double-up": "\uf102",
|
||||
"fa-angle-down": "\uf107",
|
||||
"fa-angle-left": "\uf104",
|
||||
"fa-angle-right": "\uf105",
|
||||
"fa-angle-up": "\uf106",
|
||||
"fa-archive": "\uf187",
|
||||
"fa-area-chart": "\uf1fe",
|
||||
"fa-arrow-circle-down": "\uf0ab",
|
||||
"fa-arrow-circle-left": "\uf0a8",
|
||||
"fa-arrow-circle-o-down": "\uf01a",
|
||||
"fa-arrow-circle-o-left": "\uf190",
|
||||
"fa-arrow-circle-o-right": "\uf18e",
|
||||
"fa-arrow-circle-o-up": "\uf01b",
|
||||
"fa-arrow-circle-right": "\uf0a9",
|
||||
"fa-arrow-circle-up": "\uf0aa",
|
||||
"fa-arrow-down": "\uf063",
|
||||
"fa-arrow-left": "\uf060",
|
||||
"fa-arrow-right": "\uf061",
|
||||
"fa-arrow-up": "\uf062",
|
||||
"fa-arrows-alt": "\uf0b2",
|
||||
"fa-arrows-h": "\uf07e",
|
||||
"fa-arrows-v": "\uf07d",
|
||||
"fa-arrows": "\uf047",
|
||||
"fa-asl-interpreting": "\uf2a3",
|
||||
"fa-assistive-listening-systems": "\uf2a2",
|
||||
"fa-asterisk": "\uf069",
|
||||
"fa-at": "\uf1fa",
|
||||
"fa-audio-description": "\uf29e",
|
||||
"fa-automobile": "\uf1b9",
|
||||
"fa-backward": "\uf04a",
|
||||
"fa-balance-scale": "\uf24e",
|
||||
"fa-ban": "\uf05e",
|
||||
"fa-bank": "\uf19c",
|
||||
"fa-bar-chart-o": "\uf080",
|
||||
"fa-bar-chart": "\uf080",
|
||||
"fa-barcode": "\uf02a",
|
||||
"fa-bars": "\uf0c9",
|
||||
"fa-bath": "\uf2cd",
|
||||
"fa-bathtub": "\uf2cd",
|
||||
"fa-battery-0": "\uf244",
|
||||
"fa-battery-1": "\uf243",
|
||||
"fa-battery-2": "\uf242",
|
||||
"fa-battery-3": "\uf241",
|
||||
"fa-battery-4": "\uf240",
|
||||
"fa-battery-empty": "\uf244",
|
||||
"fa-battery-full": "\uf240",
|
||||
"fa-battery-half": "\uf242",
|
||||
"fa-battery-quarter": "\uf243",
|
||||
"fa-battery-three-quarters": "\uf241",
|
||||
"fa-battery": "\uf240",
|
||||
"fa-bed": "\uf236",
|
||||
"fa-beer": "\uf0fc",
|
||||
"fa-bell-o": "\uf0a2",
|
||||
"fa-bell-slash-o": "\uf1f7",
|
||||
"fa-bell-slash": "\uf1f6",
|
||||
"fa-bell": "\uf0f3",
|
||||
"fa-bicycle": "\uf206",
|
||||
"fa-binoculars": "\uf1e5",
|
||||
"fa-birthday-cake": "\uf1fd",
|
||||
"fa-blind": "\uf29d",
|
||||
"fa-bold": "\uf032",
|
||||
"fa-bolt": "\uf0e7",
|
||||
"fa-bomb": "\uf1e2",
|
||||
"fa-book": "\uf02d",
|
||||
"fa-bookmark-o": "\uf097",
|
||||
"fa-bookmark": "\uf02e",
|
||||
"fa-braille": "\uf2a1",
|
||||
"fa-briefcase": "\uf0b1",
|
||||
"fa-bug": "\uf188",
|
||||
"fa-building-o": "\uf0f7",
|
||||
"fa-building": "\uf1ad",
|
||||
"fa-bullhorn": "\uf0a1",
|
||||
"fa-bullseye": "\uf140",
|
||||
"fa-bus": "\uf207",
|
||||
"fa-cab": "\uf1ba",
|
||||
"fa-calculator": "\uf1ec",
|
||||
"fa-calendar-check-o": "\uf274",
|
||||
"fa-calendar-minus-o": "\uf272",
|
||||
"fa-calendar-o": "\uf133",
|
||||
"fa-calendar-plus-o": "\uf271",
|
||||
"fa-calendar-times-o": "\uf273",
|
||||
"fa-calendar": "\uf073",
|
||||
"fa-camera-retro": "\uf083",
|
||||
"fa-camera": "\uf030",
|
||||
"fa-car": "\uf1b9",
|
||||
"fa-caret-down": "\uf0d7",
|
||||
"fa-caret-left": "\uf0d9",
|
||||
"fa-caret-right": "\uf0da",
|
||||
"fa-caret-square-o-down": "\uf150",
|
||||
"fa-caret-square-o-left": "\uf191",
|
||||
"fa-caret-square-o-right": "\uf152",
|
||||
"fa-caret-square-o-up": "\uf151",
|
||||
"fa-caret-up": "\uf0d8",
|
||||
"fa-cart-arrow-down": "\uf218",
|
||||
"fa-cart-plus": "\uf217",
|
||||
"fa-cc": "\uf20a",
|
||||
"fa-certificate": "\uf0a3",
|
||||
"fa-chain-broken": "\uf127",
|
||||
"fa-chain": "\uf0c1",
|
||||
"fa-check-circle-o": "\uf05d",
|
||||
"fa-check-circle": "\uf058",
|
||||
"fa-check-square-o": "\uf046",
|
||||
"fa-check-square": "\uf14a",
|
||||
"fa-check": "\uf00c",
|
||||
"fa-chevron-circle-down": "\uf13a",
|
||||
"fa-chevron-circle-left": "\uf137",
|
||||
"fa-chevron-circle-right": "\uf138",
|
||||
"fa-chevron-circle-up": "\uf139",
|
||||
"fa-chevron-down": "\uf078",
|
||||
"fa-chevron-left": "\uf053",
|
||||
"fa-chevron-right": "\uf054",
|
||||
"fa-chevron-up": "\uf077",
|
||||
"fa-child": "\uf1ae",
|
||||
"fa-circle-o-notch": "\uf1ce",
|
||||
"fa-circle-o": "\uf10c",
|
||||
"fa-circle-thin": "\uf1db",
|
||||
"fa-circle": "\uf111",
|
||||
"fa-clipboard": "\uf0ea",
|
||||
"fa-clock-o": "\uf017",
|
||||
"fa-clone": "\uf24d",
|
||||
"fa-close": "\uf00d",
|
||||
"fa-cloud-download": "\uf0ed",
|
||||
"fa-cloud-upload": "\uf0ee",
|
||||
"fa-cloud": "\uf0c2",
|
||||
"fa-cny": "\uf157",
|
||||
"fa-code-fork": "\uf126",
|
||||
"fa-code": "\uf121",
|
||||
"fa-coffee": "\uf0f4",
|
||||
"fa-cog": "\uf013",
|
||||
"fa-cogs": "\uf085",
|
||||
"fa-columns": "\uf0db",
|
||||
"fa-comment-o": "\uf0e5",
|
||||
"fa-comment": "\uf075",
|
||||
"fa-commenting-o": "\uf27b",
|
||||
"fa-commenting": "\uf27a",
|
||||
"fa-comments-o": "\uf0e6",
|
||||
"fa-comments": "\uf086",
|
||||
"fa-compass": "\uf14e",
|
||||
"fa-compress": "\uf066",
|
||||
"fa-copy": "\uf0c5",
|
||||
"fa-copyright": "\uf1f9",
|
||||
"fa-creative-commons": "\uf25e",
|
||||
"fa-credit-card-alt": "\uf283",
|
||||
"fa-credit-card": "\uf09d",
|
||||
"fa-crop": "\uf125",
|
||||
"fa-crosshairs": "\uf05b",
|
||||
"fa-cube": "\uf1b2",
|
||||
"fa-cubes": "\uf1b3",
|
||||
"fa-cut": "\uf0c4",
|
||||
"fa-cutlery": "\uf0f5",
|
||||
"fa-dashboard": "\uf0e4",
|
||||
"fa-database": "\uf1c0",
|
||||
"fa-deaf": "\uf2a4",
|
||||
"fa-deafness": "\uf2a4",
|
||||
"fa-dedent": "\uf03b",
|
||||
"fa-desktop": "\uf108",
|
||||
"fa-diamond": "\uf219",
|
||||
"fa-dollar": "\uf155",
|
||||
"fa-dot-circle-o": "\uf192",
|
||||
"fa-download": "\uf019",
|
||||
"fa-drivers-license-o": "\uf2c3",
|
||||
"fa-drivers-license": "\uf2c2",
|
||||
"fa-edit": "\uf044",
|
||||
"fa-eject": "\uf052",
|
||||
"fa-ellipsis-h": "\uf141",
|
||||
"fa-ellipsis-v": "\uf142",
|
||||
"fa-envelope-o": "\uf003",
|
||||
"fa-envelope-open-o": "\uf2b7",
|
||||
"fa-envelope-open": "\uf2b6",
|
||||
"fa-envelope-square": "\uf199",
|
||||
"fa-envelope": "\uf0e0",
|
||||
"fa-eraser": "\uf12d",
|
||||
"fa-eur": "\uf153",
|
||||
"fa-euro": "\uf153",
|
||||
"fa-exchange": "\uf0ec",
|
||||
"fa-exclamation-circle": "\uf06a",
|
||||
"fa-exclamation-triangle": "\uf071",
|
||||
"fa-exclamation": "\uf12a",
|
||||
"fa-expand": "\uf065",
|
||||
"fa-external-link-square": "\uf14c",
|
||||
"fa-external-link": "\uf08e",
|
||||
"fa-eye-slash": "\uf070",
|
||||
"fa-eye": "\uf06e",
|
||||
"fa-eyedropper": "\uf1fb",
|
||||
"fa-fast-backward": "\uf049",
|
||||
"fa-fast-forward": "\uf050",
|
||||
"fa-fax": "\uf1ac",
|
||||
"fa-feed": "\uf09e",
|
||||
"fa-female": "\uf182",
|
||||
"fa-fighter-jet": "\uf0fb",
|
||||
"fa-file-archive-o": "\uf1c6",
|
||||
"fa-file-audio-o": "\uf1c7",
|
||||
"fa-file-code-o": "\uf1c9",
|
||||
"fa-file-excel-o": "\uf1c3",
|
||||
"fa-file-image-o": "\uf1c5",
|
||||
"fa-file-movie-o": "\uf1c8",
|
||||
"fa-file-o": "\uf016",
|
||||
"fa-file-pdf-o": "\uf1c1",
|
||||
"fa-file-photo-o": "\uf1c5",
|
||||
"fa-file-picture-o": "\uf1c5",
|
||||
"fa-file-powerpoint-o": "\uf1c4",
|
||||
"fa-file-sound-o": "\uf1c7",
|
||||
"fa-file-text-o": "\uf0f6",
|
||||
"fa-file-text": "\uf15c",
|
||||
"fa-file-video-o": "\uf1c8",
|
||||
"fa-file-word-o": "\uf1c2",
|
||||
"fa-file-zip-o": "\uf1c6",
|
||||
"fa-file": "\uf15b",
|
||||
"fa-files-o": "\uf0c5",
|
||||
"fa-film": "\uf008",
|
||||
"fa-filter": "\uf0b0",
|
||||
"fa-fire-extinguisher": "\uf134",
|
||||
"fa-fire": "\uf06d",
|
||||
"fa-flag-checkered": "\uf11e",
|
||||
"fa-flag-o": "\uf11d",
|
||||
"fa-flag": "\uf024",
|
||||
"fa-flash": "\uf0e7",
|
||||
"fa-flask": "\uf0c3",
|
||||
"fa-floppy-o": "\uf0c7",
|
||||
"fa-folder-o": "\uf114",
|
||||
"fa-folder-open-o": "\uf115",
|
||||
"fa-folder-open": "\uf07c",
|
||||
"fa-folder": "\uf07b",
|
||||
"fa-font": "\uf031",
|
||||
"fa-forward": "\uf04e",
|
||||
"fa-frown-o": "\uf119",
|
||||
"fa-futbol-o": "\uf1e3",
|
||||
"fa-gamepad": "\uf11b",
|
||||
"fa-gavel": "\uf0e3",
|
||||
"fa-gbp": "\uf154",
|
||||
"fa-gear": "\uf013",
|
||||
"fa-gears": "\uf085",
|
||||
"fa-genderless": "\uf22d",
|
||||
"fa-gift": "\uf06b",
|
||||
"fa-glass": "\uf000",
|
||||
"fa-globe": "\uf0ac",
|
||||
"fa-graduation-cap": "\uf19d",
|
||||
"fa-group": "\uf0c0",
|
||||
"fa-h-square": "\uf0fd",
|
||||
"fa-hand-grab-o": "\uf255",
|
||||
"fa-hand-lizard-o": "\uf258",
|
||||
"fa-hand-o-down": "\uf0a7",
|
||||
"fa-hand-o-left": "\uf0a5",
|
||||
"fa-hand-o-right": "\uf0a4",
|
||||
"fa-hand-o-up": "\uf0a6",
|
||||
"fa-hand-paper-o": "\uf256",
|
||||
"fa-hand-peace-o": "\uf25b",
|
||||
"fa-hand-pointer-o": "\uf25a",
|
||||
"fa-hand-rock-o": "\uf255",
|
||||
"fa-hand-scissors-o": "\uf257",
|
||||
"fa-hand-spock-o": "\uf259",
|
||||
"fa-hand-stop-o": "\uf256",
|
||||
"fa-handshake-o": "\uf2b5",
|
||||
"fa-hard-of-hearing": "\uf2a4",
|
||||
"fa-hashtag": "\uf292",
|
||||
"fa-hdd-o": "\uf0a0",
|
||||
"fa-header": "\uf1dc",
|
||||
"fa-headphones": "\uf025",
|
||||
"fa-heart-o": "\uf08a",
|
||||
"fa-heart": "\uf004",
|
||||
"fa-heartbeat": "\uf21e",
|
||||
"fa-history": "\uf1da",
|
||||
"fa-home": "\uf015",
|
||||
"fa-hospital-o": "\uf0f8",
|
||||
"fa-hotel": "\uf236",
|
||||
"fa-hourglass-1": "\uf251",
|
||||
"fa-hourglass-2": "\uf252",
|
||||
"fa-hourglass-3": "\uf253",
|
||||
"fa-hourglass-end": "\uf253",
|
||||
"fa-hourglass-half": "\uf252",
|
||||
"fa-hourglass-o": "\uf250",
|
||||
"fa-hourglass-start": "\uf251",
|
||||
"fa-hourglass": "\uf254",
|
||||
"fa-i-cursor": "\uf246",
|
||||
"fa-id-badge": "\uf2c1",
|
||||
"fa-id-card-o": "\uf2c3",
|
||||
"fa-id-card": "\uf2c2",
|
||||
"fa-ils": "\uf20b",
|
||||
"fa-image": "\uf03e",
|
||||
"fa-inbox": "\uf01c",
|
||||
"fa-indent": "\uf03c",
|
||||
"fa-industry": "\uf275",
|
||||
"fa-info-circle": "\uf05a",
|
||||
"fa-info": "\uf129",
|
||||
"fa-inr": "\uf156",
|
||||
"fa-institution": "\uf19c",
|
||||
"fa-intersex": "\uf224",
|
||||
"fa-italic": "\uf033",
|
||||
"fa-jpy": "\uf157",
|
||||
"fa-key": "\uf084",
|
||||
"fa-keyboard-o": "\uf11c",
|
||||
"fa-krw": "\uf159",
|
||||
"fa-language": "\uf1ab",
|
||||
"fa-laptop": "\uf109",
|
||||
"fa-leaf": "\uf06c",
|
||||
"fa-legal": "\uf0e3",
|
||||
"fa-lemon-o": "\uf094",
|
||||
"fa-level-down": "\uf149",
|
||||
"fa-level-up": "\uf148",
|
||||
"fa-life-bouy": "\uf1cd",
|
||||
"fa-life-buoy": "\uf1cd",
|
||||
"fa-life-ring": "\uf1cd",
|
||||
"fa-life-saver": "\uf1cd",
|
||||
"fa-lightbulb-o": "\uf0eb",
|
||||
"fa-line-chart": "\uf201",
|
||||
"fa-link": "\uf0c1",
|
||||
"fa-list-alt": "\uf022",
|
||||
"fa-list-ol": "\uf0cb",
|
||||
"fa-list-ul": "\uf0ca",
|
||||
"fa-list": "\uf03a",
|
||||
"fa-location-arrow": "\uf124",
|
||||
"fa-lock": "\uf023",
|
||||
"fa-long-arrow-down": "\uf175",
|
||||
"fa-long-arrow-left": "\uf177",
|
||||
"fa-long-arrow-right": "\uf178",
|
||||
"fa-long-arrow-up": "\uf176",
|
||||
"fa-low-vision": "\uf2a8",
|
||||
"fa-magic": "\uf0d0",
|
||||
"fa-magnet": "\uf076",
|
||||
"fa-mail-forward": "\uf064",
|
||||
"fa-mail-reply-all": "\uf122",
|
||||
"fa-mail-reply": "\uf112",
|
||||
"fa-male": "\uf183",
|
||||
"fa-map-marker": "\uf041",
|
||||
"fa-map-o": "\uf278",
|
||||
"fa-map-pin": "\uf276",
|
||||
"fa-map-signs": "\uf277",
|
||||
"fa-map": "\uf279",
|
||||
"fa-mars-double": "\uf227",
|
||||
"fa-mars-stroke-h": "\uf22b",
|
||||
"fa-mars-stroke-v": "\uf22a",
|
||||
"fa-mars-stroke": "\uf229",
|
||||
"fa-mars": "\uf222",
|
||||
"fa-medkit": "\uf0fa",
|
||||
"fa-meh-o": "\uf11a",
|
||||
"fa-mercury": "\uf223",
|
||||
"fa-microchip": "\uf2db",
|
||||
"fa-microphone-slash": "\uf131",
|
||||
"fa-microphone": "\uf130",
|
||||
"fa-minus-circle": "\uf056",
|
||||
"fa-minus-square-o": "\uf147",
|
||||
"fa-minus-square": "\uf146",
|
||||
"fa-minus": "\uf068",
|
||||
"fa-mobile-phone": "\uf10b",
|
||||
"fa-mobile": "\uf10b",
|
||||
"fa-money": "\uf0d6",
|
||||
"fa-moon-o": "\uf186",
|
||||
"fa-mortar-board": "\uf19d",
|
||||
"fa-motorcycle": "\uf21c",
|
||||
"fa-mouse-pointer": "\uf245",
|
||||
"fa-music": "\uf001",
|
||||
"fa-navicon": "\uf0c9",
|
||||
"fa-neuter": "\uf22c",
|
||||
"fa-newspaper-o": "\uf1ea",
|
||||
"fa-object-group": "\uf247",
|
||||
"fa-object-ungroup": "\uf248",
|
||||
"fa-outdent": "\uf03b",
|
||||
"fa-paint-brush": "\uf1fc",
|
||||
"fa-paper-plane-o": "\uf1d9",
|
||||
"fa-paper-plane": "\uf1d8",
|
||||
"fa-paperclip": "\uf0c6",
|
||||
"fa-paragraph": "\uf1dd",
|
||||
"fa-paste": "\uf0ea",
|
||||
"fa-pause-circle-o": "\uf28c",
|
||||
"fa-pause-circle": "\uf28b",
|
||||
"fa-pause": "\uf04c",
|
||||
"fa-paw": "\uf1b0",
|
||||
"fa-pencil-square-o": "\uf044",
|
||||
"fa-pencil-square": "\uf14b",
|
||||
"fa-pencil": "\uf040",
|
||||
"fa-percent": "\uf295",
|
||||
"fa-phone-square": "\uf098",
|
||||
"fa-phone": "\uf095",
|
||||
"fa-photo": "\uf03e",
|
||||
"fa-picture-o": "\uf03e",
|
||||
"fa-pie-chart": "\uf200",
|
||||
"fa-plane": "\uf072",
|
||||
"fa-play-circle-o": "\uf01d",
|
||||
"fa-play-circle": "\uf144",
|
||||
"fa-play": "\uf04b",
|
||||
"fa-plug": "\uf1e6",
|
||||
"fa-plus-circle": "\uf055",
|
||||
"fa-plus-square-o": "\uf196",
|
||||
"fa-plus-square": "\uf0fe",
|
||||
"fa-plus": "\uf067",
|
||||
"fa-podcast": "\uf2ce",
|
||||
"fa-power-off": "\uf011",
|
||||
"fa-print": "\uf02f",
|
||||
"fa-puzzle-piece": "\uf12e",
|
||||
"fa-qrcode": "\uf029",
|
||||
"fa-question-circle-o": "\uf29c",
|
||||
"fa-question-circle": "\uf059",
|
||||
"fa-question": "\uf128",
|
||||
"fa-quote-left": "\uf10d",
|
||||
"fa-quote-right": "\uf10e",
|
||||
"fa-random": "\uf074",
|
||||
"fa-recycle": "\uf1b8",
|
||||
"fa-refresh": "\uf021",
|
||||
"fa-registered": "\uf25d",
|
||||
"fa-remove": "\uf00d",
|
||||
"fa-reorder": "\uf0c9",
|
||||
"fa-repeat": "\uf01e",
|
||||
"fa-reply-all": "\uf122",
|
||||
"fa-reply": "\uf112",
|
||||
"fa-retweet": "\uf079",
|
||||
"fa-rmb": "\uf157",
|
||||
"fa-road": "\uf018",
|
||||
"fa-rocket": "\uf135",
|
||||
"fa-rotate-left": "\uf0e2",
|
||||
"fa-rotate-right": "\uf01e",
|
||||
"fa-rouble": "\uf158",
|
||||
"fa-rss-square": "\uf143",
|
||||
"fa-rss": "\uf09e",
|
||||
"fa-rub": "\uf158",
|
||||
"fa-ruble": "\uf158",
|
||||
"fa-rupee": "\uf156",
|
||||
"fa-s15": "\uf2cd",
|
||||
"fa-save": "\uf0c7",
|
||||
"fa-scissors": "\uf0c4",
|
||||
"fa-search-minus": "\uf010",
|
||||
"fa-search-plus": "\uf00e",
|
||||
"fa-search": "\uf002",
|
||||
"fa-send-o": "\uf1d9",
|
||||
"fa-send": "\uf1d8",
|
||||
"fa-server": "\uf233",
|
||||
"fa-share-square-o": "\uf045",
|
||||
"fa-share-square": "\uf14d",
|
||||
"fa-share": "\uf064",
|
||||
"fa-shekel": "\uf20b",
|
||||
"fa-sheqel": "\uf20b",
|
||||
"fa-shield": "\uf132",
|
||||
"fa-ship": "\uf21a",
|
||||
"fa-shopping-bag": "\uf290",
|
||||
"fa-shopping-basket": "\uf291",
|
||||
"fa-shopping-cart": "\uf07a",
|
||||
"fa-shower": "\uf2cc",
|
||||
"fa-sign-in": "\uf090",
|
||||
"fa-sign-language": "\uf2a7",
|
||||
"fa-sign-out": "\uf08b",
|
||||
"fa-signal": "\uf012",
|
||||
"fa-signing": "\uf2a7",
|
||||
"fa-sitemap": "\uf0e8",
|
||||
"fa-sliders": "\uf1de",
|
||||
"fa-smile-o": "\uf118",
|
||||
"fa-snowflake-o": "\uf2dc",
|
||||
"fa-soccer-ball-o": "\uf1e3",
|
||||
"fa-sort-alpha-asc": "\uf15d",
|
||||
"fa-sort-alpha-desc": "\uf15e",
|
||||
"fa-sort-amount-asc": "\uf160",
|
||||
"fa-sort-amount-desc": "\uf161",
|
||||
"fa-sort-asc": "\uf0de",
|
||||
"fa-sort-desc": "\uf0dd",
|
||||
"fa-sort-down": "\uf0dd",
|
||||
"fa-sort-numeric-asc": "\uf162",
|
||||
"fa-sort-numeric-desc": "\uf163",
|
||||
"fa-sort-up": "\uf0de",
|
||||
"fa-sort": "\uf0dc",
|
||||
"fa-space-shuttle": "\uf197",
|
||||
"fa-spinner": "\uf110",
|
||||
"fa-spoon": "\uf1b1",
|
||||
"fa-square-o": "\uf096",
|
||||
"fa-square": "\uf0c8",
|
||||
"fa-star-half-empty": "\uf123",
|
||||
"fa-star-half-full": "\uf123",
|
||||
"fa-star-half-o": "\uf123",
|
||||
"fa-star-half": "\uf089",
|
||||
"fa-star-o": "\uf006",
|
||||
"fa-star": "\uf005",
|
||||
"fa-step-backward": "\uf048",
|
||||
"fa-step-forward": "\uf051",
|
||||
"fa-stethoscope": "\uf0f1",
|
||||
"fa-sticky-note-o": "\uf24a",
|
||||
"fa-sticky-note": "\uf249",
|
||||
"fa-stop-circle-o": "\uf28e",
|
||||
"fa-stop-circle": "\uf28d",
|
||||
"fa-stop": "\uf04d",
|
||||
"fa-street-view": "\uf21d",
|
||||
"fa-strikethrough": "\uf0cc",
|
||||
"fa-subscript": "\uf12c",
|
||||
"fa-subway": "\uf239",
|
||||
"fa-suitcase": "\uf0f2",
|
||||
"fa-sun-o": "\uf185",
|
||||
"fa-superscript": "\uf12b",
|
||||
"fa-support": "\uf1cd",
|
||||
"fa-table": "\uf0ce",
|
||||
"fa-tablet": "\uf10a",
|
||||
"fa-tachometer": "\uf0e4",
|
||||
"fa-tag": "\uf02b",
|
||||
"fa-tags": "\uf02c",
|
||||
"fa-tasks": "\uf0ae",
|
||||
"fa-taxi": "\uf1ba",
|
||||
"fa-television": "\uf26c",
|
||||
"fa-terminal": "\uf120",
|
||||
"fa-text-height": "\uf034",
|
||||
"fa-text-width": "\uf035",
|
||||
"fa-th-large": "\uf009",
|
||||
"fa-th-list": "\uf00b",
|
||||
"fa-th": "\uf00a",
|
||||
"fa-thermometer-0": "\uf2cb",
|
||||
"fa-thermometer-1": "\uf2ca",
|
||||
"fa-thermometer-2": "\uf2c9",
|
||||
"fa-thermometer-3": "\uf2c8",
|
||||
"fa-thermometer-4": "\uf2c7",
|
||||
"fa-thermometer-empty": "\uf2cb",
|
||||
"fa-thermometer-full": "\uf2c7",
|
||||
"fa-thermometer-half": "\uf2c9",
|
||||
"fa-thermometer-quarter": "\uf2ca",
|
||||
"fa-thermometer-three-quarters": "\uf2c8",
|
||||
"fa-thermometer": "\uf2c7",
|
||||
"fa-thumb-tack": "\uf08d",
|
||||
"fa-thumbs-down": "\uf165",
|
||||
"fa-thumbs-o-down": "\uf088",
|
||||
"fa-thumbs-o-up": "\uf087",
|
||||
"fa-thumbs-up": "\uf164",
|
||||
"fa-ticket": "\uf145",
|
||||
"fa-times-circle-o": "\uf05c",
|
||||
"fa-times-circle": "\uf057",
|
||||
"fa-times-rectangle-o": "\uf2d4",
|
||||
"fa-times-rectangle": "\uf2d3",
|
||||
"fa-times": "\uf00d",
|
||||
"fa-tint": "\uf043",
|
||||
"fa-toggle-down": "\uf150",
|
||||
"fa-toggle-left": "\uf191",
|
||||
"fa-toggle-off": "\uf204",
|
||||
"fa-toggle-on": "\uf205",
|
||||
"fa-toggle-right": "\uf152",
|
||||
"fa-toggle-up": "\uf151",
|
||||
"fa-trademark": "\uf25c",
|
||||
"fa-train": "\uf238",
|
||||
"fa-transgender-alt": "\uf225",
|
||||
"fa-transgender": "\uf224",
|
||||
"fa-trash-o": "\uf014",
|
||||
"fa-trash": "\uf1f8",
|
||||
"fa-tree": "\uf1bb",
|
||||
"fa-trophy": "\uf091",
|
||||
"fa-truck": "\uf0d1",
|
||||
"fa-try": "\uf195",
|
||||
"fa-tty": "\uf1e4",
|
||||
"fa-turkish-lira": "\uf195",
|
||||
"fa-tv": "\uf26c",
|
||||
"fa-umbrella": "\uf0e9",
|
||||
"fa-underline": "\uf0cd",
|
||||
"fa-undo": "\uf0e2",
|
||||
"fa-universal-access": "\uf29a",
|
||||
"fa-university": "\uf19c",
|
||||
"fa-unlink": "\uf127",
|
||||
"fa-unlock-alt": "\uf13e",
|
||||
"fa-unlock": "\uf09c",
|
||||
"fa-unsorted": "\uf0dc",
|
||||
"fa-upload": "\uf093",
|
||||
"fa-usd": "\uf155",
|
||||
"fa-user-circle-o": "\uf2be",
|
||||
"fa-user-circle": "\uf2bd",
|
||||
"fa-user-md": "\uf0f0",
|
||||
"fa-user-o": "\uf2c0",
|
||||
"fa-user-plus": "\uf234",
|
||||
"fa-user-secret": "\uf21b",
|
||||
"fa-user-times": "\uf235",
|
||||
"fa-user": "\uf007",
|
||||
"fa-users": "\uf0c0",
|
||||
"fa-vcard-o": "\uf2bc",
|
||||
"fa-vcard": "\uf2bb",
|
||||
"fa-venus-double": "\uf226",
|
||||
"fa-venus-mars": "\uf228",
|
||||
"fa-venus": "\uf221",
|
||||
"fa-video-camera": "\uf03d",
|
||||
"fa-volume-control-phone": "\uf2a0",
|
||||
"fa-volume-down": "\uf027",
|
||||
"fa-volume-off": "\uf026",
|
||||
"fa-volume-up": "\uf028",
|
||||
"fa-warning": "\uf071",
|
||||
"fa-wheelchair-alt": "\uf29b",
|
||||
"fa-wheelchair": "\uf193",
|
||||
"fa-wifi": "\uf1eb",
|
||||
"fa-window-close-o": "\uf2d4",
|
||||
"fa-window-close": "\uf2d3",
|
||||
"fa-window-maximize": "\uf2d0",
|
||||
"fa-window-minimize": "\uf2d1",
|
||||
"fa-window-restore": "\uf2d2",
|
||||
"fa-won": "\uf159",
|
||||
"fa-wrench": "\uf0ad",
|
||||
"fa-yen": "\uf157"
|
||||
};
|
||||
|
||||
var brandIconMap = {
|
||||
"fa-500px": "\uf26e",
|
||||
"fa-adn": "\uf170",
|
||||
"fa-amazon": "\uf270",
|
||||
"fa-android": "\uf17b",
|
||||
"fa-angellist": "\uf209",
|
||||
"fa-apple": "\uf179",
|
||||
"fa-bandcamp": "\uf2d5",
|
||||
"fa-behance-square": "\uf1b5",
|
||||
"fa-behance": "\uf1b4",
|
||||
"fa-bitbucket-square": "\uf172",
|
||||
"fa-bitbucket": "\uf171",
|
||||
"fa-bitcoin": "\uf15a",
|
||||
"fa-black-tie": "\uf27e",
|
||||
"fa-bluetooth-b": "\uf294",
|
||||
"fa-bluetooth": "\uf293",
|
||||
"fa-btc": "\uf15a",
|
||||
"fa-buysellads": "\uf20d",
|
||||
"fa-cc-amex": "\uf1f3",
|
||||
"fa-cc-diners-club": "\uf24c",
|
||||
"fa-cc-discover": "\uf1f2",
|
||||
"fa-cc-jcb": "\uf24b",
|
||||
"fa-cc-mastercard": "\uf1f1",
|
||||
"fa-cc-paypal": "\uf1f4",
|
||||
"fa-cc-stripe": "\uf1f5",
|
||||
"fa-cc-visa": "\uf1f0",
|
||||
"fa-chrome": "\uf268",
|
||||
"fa-codepen": "\uf1cb",
|
||||
"fa-codiepie": "\uf284",
|
||||
"fa-connectdevelop": "\uf20e",
|
||||
"fa-contao": "\uf26d",
|
||||
"fa-css3": "\uf13c",
|
||||
"fa-dashcube": "\uf210",
|
||||
"fa-delicious": "\uf1a5",
|
||||
"fa-deviantart": "\uf1bd",
|
||||
"fa-digg": "\uf1a6",
|
||||
"fa-dribbble": "\uf17d",
|
||||
"fa-dropbox": "\uf16b",
|
||||
"fa-drupal": "\uf1a9",
|
||||
"fa-edge": "\uf282",
|
||||
"fa-eercast": "\uf2da",
|
||||
"fa-empire": "\uf1d1",
|
||||
"fa-envira": "\uf299",
|
||||
"fa-etsy": "\uf2d7",
|
||||
"fa-expeditedssl": "\uf23e",
|
||||
"fa-fa": "\uf2b4",
|
||||
"fa-facebook-f": "\uf09a",
|
||||
"fa-facebook-official": "\uf230",
|
||||
"fa-facebook-square": "\uf082",
|
||||
"fa-facebook": "\uf09a",
|
||||
"fa-firefox": "\uf269",
|
||||
"fa-first-order": "\uf2b0",
|
||||
"fa-flickr": "\uf16e",
|
||||
"fa-font-awesome": "\uf2b4",
|
||||
"fa-fonticons": "\uf280",
|
||||
"fa-fort-awesome": "\uf286",
|
||||
"fa-forumbee": "\uf211",
|
||||
"fa-foursquare": "\uf180",
|
||||
"fa-free-code-camp": "\uf2c5",
|
||||
"fa-ge": "\uf1d1",
|
||||
"fa-get-pocket": "\uf265",
|
||||
"fa-gg-circle": "\uf261",
|
||||
"fa-gg": "\uf260",
|
||||
"fa-git-square": "\uf1d2",
|
||||
"fa-git": "\uf1d3",
|
||||
"fa-github-alt": "\uf113",
|
||||
"fa-github-square": "\uf092",
|
||||
"fa-github": "\uf09b",
|
||||
"fa-gitlab": "\uf296",
|
||||
"fa-gittip": "\uf184",
|
||||
"fa-glide-g": "\uf2a6",
|
||||
"fa-glide": "\uf2a5",
|
||||
"fa-google-plus-circle": "\uf2b3",
|
||||
"fa-google-plus-official": "\uf2b3",
|
||||
"fa-google-plus-square": "\uf0d4",
|
||||
"fa-google-plus": "\uf0d5",
|
||||
"fa-google-wallet": "\uf1ee",
|
||||
"fa-google": "\uf1a0",
|
||||
"fa-gratipay": "\uf184",
|
||||
"fa-grav": "\uf2d6",
|
||||
"fa-hacker-news": "\uf1d4",
|
||||
"fa-houzz": "\uf27c",
|
||||
"fa-html5": "\uf13b",
|
||||
"fa-imdb": "\uf2d8",
|
||||
"fa-instagram": "\uf16d",
|
||||
"fa-internet-explorer": "\uf26b",
|
||||
"fa-ioxhost": "\uf208",
|
||||
"fa-joomla": "\uf1aa",
|
||||
"fa-jsfiddle": "\uf1cc",
|
||||
"fa-lastfm-square": "\uf203",
|
||||
"fa-lastfm": "\uf202",
|
||||
"fa-leanpub": "\uf212",
|
||||
"fa-linkedin-square": "\uf08c",
|
||||
"fa-linkedin": "\uf0e1",
|
||||
"fa-linode": "\uf2b8",
|
||||
"fa-linux": "\uf17c",
|
||||
"fa-maxcdn": "\uf136",
|
||||
"fa-meanpath": "\uf20c",
|
||||
"fa-medium": "\uf23a",
|
||||
"fa-meetup": "\uf2e0",
|
||||
"fa-mixcloud": "\uf289",
|
||||
"fa-modx": "\uf285",
|
||||
"fa-odnoklassniki-square": "\uf264",
|
||||
"fa-odnoklassniki": "\uf263",
|
||||
"fa-opencart": "\uf23d",
|
||||
"fa-openid": "\uf19b",
|
||||
"fa-opera": "\uf26a",
|
||||
"fa-optin-monster": "\uf23c",
|
||||
"fa-pagelines": "\uf18c",
|
||||
"fa-paypal": "\uf1ed",
|
||||
"fa-pied-piper-alt": "\uf1a8",
|
||||
"fa-pied-piper-pp": "\uf1a7",
|
||||
"fa-pied-piper": "\uf2ae",
|
||||
"fa-pinterest-p": "\uf231",
|
||||
"fa-pinterest-square": "\uf0d3",
|
||||
"fa-pinterest": "\uf0d2",
|
||||
"fa-product-hunt": "\uf288",
|
||||
"fa-qq": "\uf1d6",
|
||||
"fa-quora": "\uf2c4",
|
||||
"fa-ra": "\uf1d0",
|
||||
"fa-ravelry": "\uf2d9",
|
||||
"fa-rebel": "\uf1d0",
|
||||
"fa-reddit-alien": "\uf281",
|
||||
"fa-reddit-square": "\uf1a2",
|
||||
"fa-reddit": "\uf1a1",
|
||||
"fa-renren": "\uf18b",
|
||||
"fa-resistance": "\uf1d0",
|
||||
"fa-safari": "\uf267",
|
||||
"fa-scribd": "\uf28a",
|
||||
"fa-sellsy": "\uf213",
|
||||
"fa-share-alt-square": "\uf1e1",
|
||||
"fa-share-alt": "\uf1e0",
|
||||
"fa-shirtsinbulk": "\uf214",
|
||||
"fa-simplybuilt": "\uf215",
|
||||
"fa-skyatlas": "\uf216",
|
||||
"fa-skype": "\uf17e",
|
||||
"fa-slack": "\uf198",
|
||||
"fa-slideshare": "\uf1e7",
|
||||
"fa-snapchat-ghost": "\uf2ac",
|
||||
"fa-snapchat-square": "\uf2ad",
|
||||
"fa-snapchat": "\uf2ab",
|
||||
"fa-soundcloud": "\uf1be",
|
||||
"fa-spotify": "\uf1bc",
|
||||
"fa-stack-exchange": "\uf18d",
|
||||
"fa-stack-overflow": "\uf16c",
|
||||
"fa-steam-square": "\uf1b7",
|
||||
"fa-steam": "\uf1b6",
|
||||
"fa-stumbleupon-circle": "\uf1a3",
|
||||
"fa-stumbleupon": "\uf1a4",
|
||||
"fa-superpowers": "\uf2dd",
|
||||
"fa-telegram": "\uf2c6",
|
||||
"fa-tencent-weibo": "\uf1d5",
|
||||
"fa-themeisle": "\uf2b2",
|
||||
"fa-trello": "\uf181",
|
||||
"fa-tripadvisor": "\uf262",
|
||||
"fa-tumblr-square": "\uf174",
|
||||
"fa-tumblr": "\uf173",
|
||||
"fa-twitch": "\uf1e8",
|
||||
"fa-twitter-square": "\uf081",
|
||||
"fa-twitter": "\uf099",
|
||||
"fa-usb": "\uf287",
|
||||
"fa-viacoin": "\uf237",
|
||||
"fa-viadeo-square": "\uf2aa",
|
||||
"fa-viadeo": "\uf2a9",
|
||||
"fa-vimeo-square": "\uf194",
|
||||
"fa-vimeo": "\uf27d",
|
||||
"fa-vine": "\uf1ca",
|
||||
"fa-vk": "\uf189",
|
||||
"fa-wechat": "\uf1d7",
|
||||
"fa-weibo": "\uf18a",
|
||||
"fa-weixin": "\uf1d7",
|
||||
"fa-whatsapp": "\uf232",
|
||||
"fa-wikipedia-w": "\uf266",
|
||||
"fa-windows": "\uf17a",
|
||||
"fa-wordpress": "\uf19a",
|
||||
"fa-wpbeginner": "\uf297",
|
||||
"fa-wpexplorer": "\uf2de",
|
||||
"fa-wpforms": "\uf298",
|
||||
"fa-xing-square": "\uf169",
|
||||
"fa-xing": "\uf168",
|
||||
"fa-y-combinator-square": "\uf1d4",
|
||||
"fa-y-combinator": "\uf23b",
|
||||
"fa-yahoo": "\uf19e",
|
||||
"fa-yc-square": "\uf1d4",
|
||||
"fa-yc": "\uf23b",
|
||||
"fa-yelp": "\uf1e9",
|
||||
"fa-yoast": "\uf2b1",
|
||||
"fa-youtube-play": "\uf16a",
|
||||
"fa-youtube-square": "\uf166",
|
||||
"fa-youtube": "\uf167",
|
||||
};
|
||||
|
||||
var iconList = [];
|
||||
var isUsed = {};
|
||||
Object.keys(iconMap).forEach(function(icon) {
|
||||
var unicode = iconMap[icon];
|
||||
// skip icons with a same unicode
|
||||
if (isUsed[unicode] !== true) {
|
||||
iconList.push(icon);
|
||||
isUsed[unicode] = true;
|
||||
}
|
||||
});
|
||||
isUsed = undefined;
|
||||
|
||||
return {
|
||||
getIconUnicode: function(name) {
|
||||
return iconMap[name] || brandIconMap[name];
|
||||
},
|
||||
getIconList: function() {
|
||||
return iconList;
|
||||
},
|
||||
}
|
||||
})();
|
@@ -91,12 +91,15 @@ RED.history = (function() {
|
||||
} else if (ev.t == "delete") {
|
||||
if (ev.workspaces) {
|
||||
for (i=0;i<ev.workspaces.length;i++) {
|
||||
RED.nodes.addWorkspace(ev.workspaces[i]);
|
||||
RED.workspaces.add(ev.workspaces[i]);
|
||||
RED.nodes.addWorkspace(ev.workspaces[i],ev.workspaces[i]._index);
|
||||
RED.workspaces.add(ev.workspaces[i],undefined,ev.workspaces[i]._index);
|
||||
delete ev.workspaces[i]._index;
|
||||
}
|
||||
}
|
||||
if (ev.subflow && ev.subflow.subflow) {
|
||||
RED.nodes.addSubflow(ev.subflow.subflow);
|
||||
if (ev.subflows) {
|
||||
for (i=0;i<ev.subflows.length;i++) {
|
||||
RED.nodes.addSubflow(ev.subflows[i]);
|
||||
}
|
||||
}
|
||||
if (ev.subflowInputs && ev.subflowInputs.length > 0) {
|
||||
subflow = RED.nodes.subflow(ev.subflowInputs[0].z);
|
||||
@@ -259,6 +262,8 @@ RED.history = (function() {
|
||||
} else if (ev.t == "createSubflow") {
|
||||
if (ev.nodes) {
|
||||
RED.nodes.filterNodes({z:ev.subflow.subflow.id}).forEach(function(n) {
|
||||
n.x += ev.subflow.offsetX;
|
||||
n.y += ev.subflow.offsetY;
|
||||
n.z = ev.activeWorkspace;
|
||||
n.dirty = true;
|
||||
});
|
||||
@@ -293,6 +298,7 @@ RED.history = (function() {
|
||||
});
|
||||
|
||||
RED.nodes.dirty(ev.dirty);
|
||||
RED.view.select(null);
|
||||
RED.view.redraw(true);
|
||||
RED.palette.refresh();
|
||||
RED.workspaces.refresh();
|
||||
|
@@ -30,12 +30,18 @@ RED.i18n = (function() {
|
||||
defaultNs: "editor"
|
||||
},
|
||||
fallbackLng: ['en-US'],
|
||||
useCookie: false
|
||||
useCookie: false,
|
||||
returnObjectTrees: true
|
||||
},function() {
|
||||
done();
|
||||
});
|
||||
RED["_"] = function() {
|
||||
return i18n.t.apply(null,arguments);
|
||||
var v = i18n.t.apply(null,arguments);
|
||||
if (typeof v === 'string') {
|
||||
return v;
|
||||
} else {
|
||||
return arguments[0];
|
||||
}
|
||||
}
|
||||
|
||||
},
|
||||
|
35
packages/node_modules/@node-red/editor-client/src/js/jquery-addons.js
vendored
Normal file
35
packages/node_modules/@node-red/editor-client/src/js/jquery-addons.js
vendored
Normal file
@@ -0,0 +1,35 @@
|
||||
/**
|
||||
* 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.
|
||||
**/
|
||||
|
||||
|
||||
/**
|
||||
* Trigger enabled/disabled events when element.prop("disabled",false/true) is
|
||||
* called.
|
||||
* Used by RED.popover to hide a popover when the trigger element is disabled
|
||||
* as a disabled element doesn't emit mouseleave
|
||||
*/
|
||||
jQuery.propHooks.disabled = {
|
||||
set: function (element, value) {
|
||||
if (element.disabled !== value) {
|
||||
element.disabled = value;
|
||||
if (value) {
|
||||
$(element).trigger('disabled');
|
||||
} else {
|
||||
$(element).trigger('enabled');
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
@@ -14,11 +14,19 @@
|
||||
"ctrl-e": "core:show-export-dialog",
|
||||
"ctrl-i": "core:show-import-dialog",
|
||||
"ctrl-space": "core:toggle-sidebar",
|
||||
"ctrl-p": "core:toggle-palette",
|
||||
"ctrl-,": "core:show-user-settings",
|
||||
"ctrl-alt-r": "core:show-remote-diff",
|
||||
"ctrl-alt-n": "core:new-project",
|
||||
"ctrl-alt-o": "core:open-project",
|
||||
"ctrl-g v": "core:show-version-control-tab"
|
||||
"ctrl-g v": "core:show-version-control-tab",
|
||||
"ctrl-shift-l": "core:show-event-log"
|
||||
},
|
||||
"sidebar-node-config": {
|
||||
"backspace": "core:delete-config-selection",
|
||||
"delete": "core:delete-config-selection",
|
||||
"ctrl-a": "core:select-all-config-nodes",
|
||||
"ctrl-z": "core:undo"
|
||||
},
|
||||
"workspace": {
|
||||
"backspace": "core:delete-selection",
|
||||
|
@@ -174,6 +174,7 @@ RED.nodes = (function() {
|
||||
},
|
||||
setIconSets: function(sets) {
|
||||
iconSets = sets;
|
||||
iconSets["font-awesome"] = RED.nodes.fontAwesome.getIconList();
|
||||
},
|
||||
getIconSets: function() {
|
||||
return iconSets;
|
||||
@@ -297,10 +298,14 @@ RED.nodes = (function() {
|
||||
}
|
||||
}
|
||||
|
||||
function addWorkspace(ws) {
|
||||
function addWorkspace(ws,targetIndex) {
|
||||
workspaces[ws.id] = ws;
|
||||
ws._def = RED.nodes.getType('tab');
|
||||
workspacesOrder.push(ws.id);
|
||||
if (targetIndex === undefined) {
|
||||
workspacesOrder.push(ws.id);
|
||||
} else {
|
||||
workspacesOrder.splice(targetIndex,0,ws.id);
|
||||
}
|
||||
}
|
||||
function getWorkspace(id) {
|
||||
return workspaces[id];
|
||||
@@ -508,6 +513,12 @@ RED.nodes = (function() {
|
||||
node.icon = n.icon;
|
||||
}
|
||||
}
|
||||
if ((!n._def.defaults || !n._def.defaults.hasOwnProperty("l")) && n.hasOwnProperty('l')) {
|
||||
var isLink = /^link (in|out)$/.test(node.type);
|
||||
if (isLink == n.l) {
|
||||
node.l = n.l;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (n.info) {
|
||||
node.info = n.info;
|
||||
@@ -642,42 +653,39 @@ RED.nodes = (function() {
|
||||
}
|
||||
|
||||
function checkForMatchingSubflow(subflow,subflowNodes) {
|
||||
subflowNodes = subflowNodes || [];
|
||||
var i;
|
||||
var match = null;
|
||||
try {
|
||||
RED.nodes.eachSubflow(function(sf) {
|
||||
if (sf.name != subflow.name ||
|
||||
sf.info != subflow.info ||
|
||||
sf.in.length != subflow.in.length ||
|
||||
sf.out.length != subflow.out.length) {
|
||||
return;
|
||||
}
|
||||
var sfNodes = RED.nodes.filterNodes({z:sf.id});
|
||||
if (sfNodes.length != subflowNodes.length) {
|
||||
RED.nodes.eachSubflow(function(sf) {
|
||||
if (sf.name != subflow.name ||
|
||||
sf.info != subflow.info ||
|
||||
sf.in.length != subflow.in.length ||
|
||||
sf.out.length != subflow.out.length) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
var sfNodes = RED.nodes.filterNodes({z:sf.id});
|
||||
if (sfNodes.length != subflowNodes.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
var subflowNodeSet = [subflow].concat(subflowNodes);
|
||||
var sfNodeSet = [sf].concat(sfNodes);
|
||||
var subflowNodeSet = [subflow].concat(subflowNodes);
|
||||
var sfNodeSet = [sf].concat(sfNodes);
|
||||
|
||||
var exportableSubflowNodes = JSON.stringify(subflowNodeSet);
|
||||
var exportableSFNodes = JSON.stringify(createExportableNodeSet(sfNodeSet));
|
||||
var nodeMap = {};
|
||||
for (i=0;i<sfNodes.length;i++) {
|
||||
exportableSubflowNodes = exportableSubflowNodes.replace(new RegExp("\""+subflowNodes[i].id+"\"","g"),'"'+sfNodes[i].id+'"');
|
||||
}
|
||||
exportableSubflowNodes = exportableSubflowNodes.replace(new RegExp("\""+subflow.id+"\"","g"),'"'+sf.id+'"');
|
||||
var exportableSubflowNodes = JSON.stringify(subflowNodeSet);
|
||||
var exportableSFNodes = JSON.stringify(createExportableNodeSet(sfNodeSet));
|
||||
var nodeMap = {};
|
||||
for (i=0;i<sfNodes.length;i++) {
|
||||
exportableSubflowNodes = exportableSubflowNodes.replace(new RegExp("\""+subflowNodes[i].id+"\"","g"),'"'+sfNodes[i].id+'"');
|
||||
}
|
||||
exportableSubflowNodes = exportableSubflowNodes.replace(new RegExp("\""+subflow.id+"\"","g"),'"'+sf.id+'"');
|
||||
|
||||
if (exportableSubflowNodes !== exportableSFNodes) {
|
||||
return;
|
||||
}
|
||||
if (exportableSubflowNodes !== exportableSFNodes) {
|
||||
return;
|
||||
}
|
||||
|
||||
match = sf;
|
||||
throw new Error();
|
||||
});
|
||||
} catch(err) {
|
||||
console.log(err.stack);
|
||||
}
|
||||
match = sf;
|
||||
return false;
|
||||
});
|
||||
return match;
|
||||
}
|
||||
function compareNodes(nodeA,nodeB,idMustMatch) {
|
||||
@@ -757,7 +765,6 @@ RED.nodes = (function() {
|
||||
}
|
||||
if (!isInitialLoad && unknownTypes.length > 0) {
|
||||
var typeList = "<ul><li>"+unknownTypes.join("</li><li>")+"</li></ul>";
|
||||
var type = "type"+(unknownTypes.length > 1?"s":"");
|
||||
RED.notify("<p>"+RED._("clipboard.importUnrecognised",{count:unknownTypes.length})+"</p>"+typeList,"error",false,10000);
|
||||
}
|
||||
|
||||
@@ -948,11 +955,11 @@ RED.nodes = (function() {
|
||||
def = registry.getNodeType(n.type);
|
||||
if (!def || def.category != "config") {
|
||||
var node = {
|
||||
x:n.x,
|
||||
y:n.y,
|
||||
x:parseFloat(n.x || 0),
|
||||
y:parseFloat(n.y || 0),
|
||||
z:n.z,
|
||||
type:0,
|
||||
wires:n.wires,
|
||||
wires:n.wires||[],
|
||||
inputLabels: n.inputLabels,
|
||||
outputLabels: n.outputLabels,
|
||||
icon: n.icon,
|
||||
@@ -960,6 +967,9 @@ RED.nodes = (function() {
|
||||
changed:false,
|
||||
_config:{}
|
||||
};
|
||||
if (n.hasOwnProperty('l')) {
|
||||
node.l = n.l;
|
||||
}
|
||||
if (createNewIds) {
|
||||
if (subflow_blacklist[n.z]) {
|
||||
continue;
|
||||
@@ -1296,21 +1306,23 @@ RED.nodes = (function() {
|
||||
RED.events.on("registry:node-type-added",function(type) {
|
||||
var def = registry.getNodeType(type);
|
||||
var replaced = false;
|
||||
var replaceNodes = [];
|
||||
var replaceNodes = {};
|
||||
RED.nodes.eachNode(function(n) {
|
||||
if (n.type === "unknown" && n.name === type) {
|
||||
replaceNodes.push(n);
|
||||
replaceNodes[n.id] = n;
|
||||
}
|
||||
});
|
||||
RED.nodes.eachConfig(function(n) {
|
||||
if (n.type === "unknown" && n.name === type) {
|
||||
replaceNodes.push(n);
|
||||
replaceNodes[n.id] = n;
|
||||
}
|
||||
});
|
||||
|
||||
if (replaceNodes.length > 0) {
|
||||
var replaceNodeIds = Object.keys(replaceNodes);
|
||||
if (replaceNodeIds.length > 0) {
|
||||
var reimportList = [];
|
||||
replaceNodes.forEach(function(n) {
|
||||
replaceNodeIds.forEach(function(id) {
|
||||
var n = replaceNodes[id];
|
||||
if (configNodes.hasOwnProperty(n.id)) {
|
||||
delete configNodes[n.id];
|
||||
} else {
|
||||
@@ -1318,6 +1330,18 @@ RED.nodes = (function() {
|
||||
}
|
||||
reimportList.push(convertNode(n));
|
||||
});
|
||||
|
||||
// Remove any links between nodes that are going to be reimported.
|
||||
// This prevents a duplicate link from being added.
|
||||
var removeLinks = [];
|
||||
RED.nodes.eachLink(function(l) {
|
||||
if (replaceNodes.hasOwnProperty(l.source.id) && replaceNodes.hasOwnProperty(l.target.id)) {
|
||||
removeLinks.push(l);
|
||||
}
|
||||
});
|
||||
removeLinks.forEach(removeLink);
|
||||
|
||||
|
||||
RED.view.redraw(true);
|
||||
var result = importNodes(reimportList,false);
|
||||
var newNodeMap = {};
|
||||
@@ -1372,31 +1396,41 @@ RED.nodes = (function() {
|
||||
|
||||
eachNode: function(cb) {
|
||||
for (var n=0;n<nodes.length;n++) {
|
||||
cb(nodes[n]);
|
||||
if (cb(nodes[n]) === false) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
eachLink: function(cb) {
|
||||
for (var l=0;l<links.length;l++) {
|
||||
cb(links[l]);
|
||||
if (cb(links[l]) === false) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
eachConfig: function(cb) {
|
||||
for (var id in configNodes) {
|
||||
if (configNodes.hasOwnProperty(id)) {
|
||||
cb(configNodes[id]);
|
||||
if (cb(configNodes[id]) === false) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
eachSubflow: function(cb) {
|
||||
for (var id in subflows) {
|
||||
if (subflows.hasOwnProperty(id)) {
|
||||
cb(subflows[id]);
|
||||
if (cb(subflows[id]) === false) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
eachWorkspace: function(cb) {
|
||||
for (var i=0;i<workspacesOrder.length;i++) {
|
||||
cb(workspaces[workspacesOrder[i]]);
|
||||
if (cb(workspaces[workspacesOrder[i]]) === false) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
|
@@ -391,13 +391,17 @@ var RED = (function() {
|
||||
typeList = "<ul><li>"+msg.types.join("</li><li>")+"</li></ul>";
|
||||
RED.notify(RED._("palette.event.nodeDisabled", {count:msg.types.length})+typeList,"success");
|
||||
}
|
||||
} else if (topic == "node/upgraded") {
|
||||
} else if (topic == "notification/node/upgraded") {
|
||||
RED.notify(RED._("palette.event.nodeUpgraded", {module:msg.module,version:msg.version}),"success");
|
||||
RED.nodes.registry.setModulePendingUpdated(msg.module,msg.version);
|
||||
}
|
||||
// Refresh flow library to ensure any examples are updated
|
||||
RED.library.loadFlowLibrary();
|
||||
});
|
||||
RED.comms.subscribe("event-log/#", function(topic,payload) {
|
||||
var id = topic.substring(9);
|
||||
RED.eventLog.log(id,payload);
|
||||
});
|
||||
}
|
||||
|
||||
function showAbout() {
|
||||
@@ -414,10 +418,10 @@ var RED = (function() {
|
||||
function loadEditor() {
|
||||
var menuOptions = [];
|
||||
if (RED.settings.theme("projects.enabled",false)) {
|
||||
menuOptions.push({id:"menu-item-projects-menu",label:"Projects",options:[
|
||||
{id:"menu-item-projects-new",label:"New",disabled:false,onselect:"core:new-project"},
|
||||
{id:"menu-item-projects-open",label:"Open",disabled:false,onselect:"core:open-project"},
|
||||
{id:"menu-item-projects-settings",label:"Project Settings",disabled:false,onselect:"core:show-project-settings"}
|
||||
menuOptions.push({id:"menu-item-projects-menu",label:RED._("menu.label.projects"),options:[
|
||||
{id:"menu-item-projects-new",label:RED._("menu.label.projects-new"),disabled:false,onselect:"core:new-project"},
|
||||
{id:"menu-item-projects-open",label:RED._("menu.label.projects-open"),disabled:false,onselect:"core:open-project"},
|
||||
{id:"menu-item-projects-settings",label:RED._("menu.label.projects-settings"),disabled:false,onselect:"core:show-project-settings"}
|
||||
]});
|
||||
}
|
||||
|
||||
@@ -434,7 +438,9 @@ var RED = (function() {
|
||||
// {id:"menu-item-bidi-auto",toggle:"text-direction",label:RED._("menu.label.view.auto"), onselect:function(s) { if(s){RED.text.bidi.setTextDirection("auto")}}}
|
||||
// ]},
|
||||
// null,
|
||||
{id:"menu-item-palette",label:RED._("menu.label.palette.show"),toggle:true,onselect:"core:toggle-palette", selected: true},
|
||||
{id:"menu-item-sidebar",label:RED._("menu.label.sidebar.show"),toggle:true,onselect:"core:toggle-sidebar", selected: true},
|
||||
{id:"menu-item-event-log",label:RED._("eventLog.title"),onselect:"core:show-event-log"},
|
||||
null
|
||||
]});
|
||||
menuOptions.push(null);
|
||||
@@ -482,6 +488,7 @@ var RED = (function() {
|
||||
RED.library.init();
|
||||
RED.keyboard.init();
|
||||
RED.palette.init();
|
||||
RED.eventLog.init();
|
||||
if (RED.settings.theme('palette.editable') !== false) {
|
||||
RED.palette.editor.init();
|
||||
} else {
|
||||
|
@@ -1242,7 +1242,7 @@ RED.text.format = (function() {
|
||||
element.dispatchEvent(event);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
var range = selection.getRangeAt(0);
|
||||
var tempRange = range.cloneRange(), startNode, startOffset;
|
||||
startNode = range.startContainer;
|
||||
@@ -1304,7 +1304,7 @@ RED.text.format = (function() {
|
||||
}
|
||||
|
||||
return {
|
||||
/**
|
||||
/*!
|
||||
* Returns the HTML representation of a given structured text
|
||||
* @param text - the structured text
|
||||
* @param type - could be one of filepath, url, email
|
||||
@@ -1315,7 +1315,7 @@ RED.text.format = (function() {
|
||||
getHtml: function (text, type, args, isRtl, locale) {
|
||||
return getHandler(type).format(text, args, isRtl, true, locale);
|
||||
},
|
||||
/**
|
||||
/*!
|
||||
* Handle Structured text correct display for a given HTML element.
|
||||
* @param element - the element : should be of type div contenteditable=true
|
||||
* @param type - could be one of filepath, url, email
|
||||
|
@@ -12,9 +12,9 @@ RED.actions = (function() {
|
||||
function getAction(name) {
|
||||
return actions[name];
|
||||
}
|
||||
function invokeAction(name) {
|
||||
function invokeAction(name,args) {
|
||||
if (actions.hasOwnProperty(name)) {
|
||||
actions[name]();
|
||||
actions[name](args);
|
||||
}
|
||||
}
|
||||
function listActions() {
|
||||
|
@@ -22,6 +22,8 @@ RED.clipboard = (function() {
|
||||
var exportNodesDialog;
|
||||
var importNodesDialog;
|
||||
var disabled = false;
|
||||
var popover;
|
||||
var currentPopoverError;
|
||||
|
||||
function setupDialogs() {
|
||||
dialog = $('<div id="clipboard-dialog" class="hide node-red-dialog"><form class="dialog-form form-horizontal"></form></div>')
|
||||
@@ -47,6 +49,21 @@ RED.clipboard = (function() {
|
||||
$( this ).dialog( "close" );
|
||||
}
|
||||
},
|
||||
{
|
||||
id: "clipboard-dialog-download",
|
||||
class: "primary",
|
||||
text: RED._("clipboard.download"),
|
||||
click: function() {
|
||||
var element = document.createElement('a');
|
||||
element.setAttribute('href', 'data:text/plain;charset=utf-8,' + encodeURIComponent($("#clipboard-export").val()));
|
||||
element.setAttribute('download', "flows.json");
|
||||
element.style.display = 'none';
|
||||
document.body.appendChild(element);
|
||||
element.click();
|
||||
document.body.removeChild(element);
|
||||
$( this ).dialog( "close" );
|
||||
}
|
||||
},
|
||||
{
|
||||
id: "clipboard-dialog-copy",
|
||||
class: "primary",
|
||||
@@ -55,7 +72,7 @@ RED.clipboard = (function() {
|
||||
$("#clipboard-export").select();
|
||||
document.execCommand("copy");
|
||||
document.getSelection().removeAllRanges();
|
||||
RED.notify(RED._("clipboard.nodesExported"));
|
||||
RED.notify(RED._("clipboard.nodesExported"),{id:"clipboard"});
|
||||
$( this ).dialog( "close" );
|
||||
}
|
||||
},
|
||||
@@ -73,6 +90,10 @@ RED.clipboard = (function() {
|
||||
$(this).parent().find(".ui-dialog-titlebar-close").hide();
|
||||
},
|
||||
close: function(e) {
|
||||
if (popover) {
|
||||
popover.close(true);
|
||||
currentPopoverError = null;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
@@ -86,7 +107,7 @@ RED.clipboard = (function() {
|
||||
'<a id="export-range-flow" class="editor-button toggle" href="#" data-i18n="clipboard.export.current"></a>'+
|
||||
'<a id="export-range-full" class="editor-button toggle" href="#" data-i18n="clipboard.export.all"></a>'+
|
||||
'</span>'+
|
||||
'</div>'+
|
||||
'</div>'+
|
||||
'<div class="form-row">'+
|
||||
'<textarea readonly style="resize: none; width: 100%; border-radius: 4px;font-family: monospace; font-size: 12px; background:#f3f3f3; padding-left: 0.5em; box-sizing:border-box;" id="clipboard-export" rows="5"></textarea>'+
|
||||
'</div>'+
|
||||
@@ -97,10 +118,13 @@ RED.clipboard = (function() {
|
||||
'</span>'+
|
||||
'</div>';
|
||||
|
||||
importNodesDialog = '<div class="form-row">'+
|
||||
'<textarea style="resize: none; width: 100%; border-radius: 0px;font-family: monospace; font-size: 12px; background:#eee; padding-left: 0.5em; box-sizing:border-box;" id="clipboard-import" rows="5" placeholder="'+
|
||||
RED._("clipboard.pasteNodes")+
|
||||
'"></textarea>'+
|
||||
importNodesDialog =
|
||||
'<div class="form-row"><span data-i18n="clipboard.pasteNodes"></span>'+
|
||||
' <a class="editor-button" id="import-file-upload-btn"><i class="fa fa-upload"></i> <span data-i18n="clipboard.selectFile"></span></a>'+
|
||||
'<input type="file" id="import-file-upload" accept=".json" style="display:none">'+
|
||||
'</div>'+
|
||||
'<div class="form-row">'+
|
||||
'<textarea style="resize: none; width: 100%; border-radius: 0px;font-family: monospace; font-size: 12px; background:#eee; padding-left: 0.5em; box-sizing:border-box;" id="clipboard-import" rows="5"></textarea>'+
|
||||
'</div>'+
|
||||
'<div class="form-row">'+
|
||||
'<label style="width:auto;margin-right: 10px;" data-i18n="clipboard.import.import"></label>'+
|
||||
@@ -111,21 +135,98 @@ RED.clipboard = (function() {
|
||||
'</div>';
|
||||
}
|
||||
|
||||
var validateImportTimeout;
|
||||
|
||||
function validateImport() {
|
||||
var importInput = $("#clipboard-import");
|
||||
var v = importInput.val();
|
||||
v = v.substring(v.indexOf('['),v.lastIndexOf(']')+1);
|
||||
try {
|
||||
JSON.parse(v);
|
||||
importInput.removeClass("input-error");
|
||||
importInput.val(v);
|
||||
$("#clipboard-dialog-ok").button("enable");
|
||||
} catch(err) {
|
||||
if (v !== "") {
|
||||
importInput.addClass("input-error");
|
||||
}
|
||||
$("#clipboard-dialog-ok").button("disable");
|
||||
if (validateImportTimeout) {
|
||||
clearTimeout(validateImportTimeout);
|
||||
}
|
||||
validateImportTimeout = setTimeout(function() {
|
||||
var importInput = $("#clipboard-import");
|
||||
var v = importInput.val().trim();
|
||||
if (v === "") {
|
||||
popover.close(true);
|
||||
currentPopoverError = null;
|
||||
importInput.removeClass("input-error");
|
||||
$("#clipboard-dialog-ok").button("disable");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
if (!/^\[[\s\S]*\]$/m.test(v)) {
|
||||
throw new Error(RED._("clipboard.import.errors.notArray"));
|
||||
}
|
||||
var res = JSON.parse(v);
|
||||
for (var i=0;i<res.length;i++) {
|
||||
if (typeof res[i] !== "object") {
|
||||
throw new Error(RED._("clipboard.import.errors.itemNotObject",{index:i}));
|
||||
}
|
||||
if (!res[i].hasOwnProperty('id')) {
|
||||
throw new Error(RED._("clipboard.import.errors.missingId",{index:i}));
|
||||
}
|
||||
if (!res[i].hasOwnProperty('type')) {
|
||||
throw new Error(RED._("clipboard.import.errors.missingType",{index:i}));
|
||||
}
|
||||
}
|
||||
currentPopoverError = null;
|
||||
popover.close(true);
|
||||
importInput.removeClass("input-error");
|
||||
importInput.val(v);
|
||||
$("#clipboard-dialog-ok").button("enable");
|
||||
} catch(err) {
|
||||
if (v !== "") {
|
||||
importInput.addClass("input-error");
|
||||
var errString = err.toString();
|
||||
if (errString !== currentPopoverError) {
|
||||
// Display the error as-is.
|
||||
// Error messages are only in English. Each browser has its
|
||||
// own set of messages with very little consistency.
|
||||
// To provide translated messages this code will either need to:
|
||||
// - reduce everything down to 'unexpected token at position x'
|
||||
// which is the least useful, but most consistent message
|
||||
// - use a custom/library parser that gives consistent messages
|
||||
// which can be translated.
|
||||
var message = $('<div class="clipboard-import-error"></div>').text(errString);
|
||||
var errorPos;
|
||||
// Chrome error messages
|
||||
var m = /at position (\d+)/i.exec(errString);
|
||||
if (m) {
|
||||
errorPos = parseInt(m[1]);
|
||||
} else {
|
||||
// Firefox error messages
|
||||
m = /at line (\d+) column (\d+)/i.exec(errString);
|
||||
if (m) {
|
||||
var line = parseInt(m[1])-1;
|
||||
var col = parseInt(m[2])-1;
|
||||
var lines = v.split("\n");
|
||||
errorPos = 0;
|
||||
for (var i=0;i<line;i++) {
|
||||
errorPos += lines[i].length+1;
|
||||
}
|
||||
errorPos += col;
|
||||
} else {
|
||||
// Safari doesn't provide any position information
|
||||
// IE: tbd
|
||||
}
|
||||
}
|
||||
|
||||
if (errorPos !== undefined) {
|
||||
v = v.replace(/\n/g,"↵");
|
||||
var index = parseInt(m[1]);
|
||||
var parseError = $('<div>').appendTo(message);
|
||||
var code = $('<pre>').appendTo(parseError);
|
||||
$('<span>').text(v.substring(errorPos-12,errorPos)).appendTo(code)
|
||||
$('<span class="error">').text(v.charAt(errorPos)).appendTo(code);
|
||||
$('<span>').text(v.substring(errorPos+1,errorPos+12)).appendTo(code);
|
||||
}
|
||||
popover.close(true).setContent(message).open();
|
||||
currentPopoverError = errString;
|
||||
}
|
||||
} else {
|
||||
currentPopoverError = null;
|
||||
}
|
||||
$("#clipboard-dialog-ok").button("disable");
|
||||
}
|
||||
},100);
|
||||
}
|
||||
|
||||
function importNodes() {
|
||||
@@ -140,6 +241,7 @@ RED.clipboard = (function() {
|
||||
$("#clipboard-dialog-cancel").show();
|
||||
$("#clipboard-dialog-close").hide();
|
||||
$("#clipboard-dialog-copy").hide();
|
||||
$("#clipboard-dialog-download").hide();
|
||||
$("#clipboard-dialog-ok").button("disable");
|
||||
$("#clipboard-import").keyup(validateImport);
|
||||
$("#clipboard-import").on('paste',function() { setTimeout(validateImport,10)});
|
||||
@@ -153,7 +255,26 @@ RED.clipboard = (function() {
|
||||
$(this).addClass('selected');
|
||||
});
|
||||
|
||||
$("#import-file-upload").change(function() {
|
||||
var fileReader = new FileReader();
|
||||
fileReader.onload = function () {
|
||||
$("#clipboard-import").val(fileReader.result);
|
||||
validateImport();
|
||||
};
|
||||
fileReader.readAsText($(this).prop('files')[0]);
|
||||
})
|
||||
$("#import-file-upload-btn").click(function(evt) {
|
||||
evt.preventDefault();
|
||||
$("#import-file-upload").click();
|
||||
})
|
||||
|
||||
dialog.dialog("option","title",RED._("clipboard.importNodes")).dialog("open");
|
||||
popover = RED.popover.create({
|
||||
target: $("#clipboard-import"),
|
||||
trigger: "manual",
|
||||
direction: "bottom",
|
||||
content: ""
|
||||
});
|
||||
}
|
||||
|
||||
function exportNodes() {
|
||||
@@ -202,9 +323,18 @@ RED.clipboard = (function() {
|
||||
var flow = "";
|
||||
var nodes = null;
|
||||
if (type === 'export-range-selected') {
|
||||
var selection = RED.view.selection();
|
||||
var selection = RED.workspaces.selection();
|
||||
if (selection.length > 0) {
|
||||
nodes = [];
|
||||
selection.forEach(function(n) {
|
||||
nodes.push(n);
|
||||
nodes = nodes.concat(RED.nodes.filterNodes({z:n.id}));
|
||||
});
|
||||
} else {
|
||||
nodes = RED.view.selection().nodes||[];
|
||||
}
|
||||
// Don't include the subflow meta-port nodes in the exported selection
|
||||
nodes = RED.nodes.createExportableNodeSet(selection.nodes.filter(function(n) { return n.type !== 'subflow'}));
|
||||
nodes = RED.nodes.createExportableNodeSet(nodes.filter(function(n) { return n.type !== 'subflow'}));
|
||||
} else if (type === 'export-range-flow') {
|
||||
var activeWorkspace = RED.workspaces.active();
|
||||
nodes = RED.nodes.filterNodes({z:activeWorkspace});
|
||||
@@ -234,12 +364,17 @@ RED.clipboard = (function() {
|
||||
$("#clipboard-dialog-cancel").hide();
|
||||
$("#clipboard-dialog-copy").hide();
|
||||
$("#clipboard-dialog-close").hide();
|
||||
var selection = RED.view.selection();
|
||||
if (selection.nodes) {
|
||||
var selection = RED.workspaces.selection();
|
||||
if (selection.length > 0) {
|
||||
$("#export-range-selected").click();
|
||||
} else {
|
||||
$("#export-range-selected").addClass('disabled').removeClass('selected');
|
||||
$("#export-range-flow").click();
|
||||
selection = RED.view.selection();
|
||||
if (selection.nodes) {
|
||||
$("#export-range-selected").click();
|
||||
} else {
|
||||
$("#export-range-selected").addClass('disabled').removeClass('selected');
|
||||
$("#export-range-flow").click();
|
||||
}
|
||||
}
|
||||
if (format === "export-format-full") {
|
||||
$("#export-format-full").click();
|
||||
@@ -265,6 +400,8 @@ RED.clipboard = (function() {
|
||||
$("#clipboard-dialog-cancel").show();
|
||||
$("#clipboard-dialog-copy").show();
|
||||
}
|
||||
$("#clipboard-dialog-download").show();
|
||||
|
||||
}
|
||||
|
||||
function hideDropTarget() {
|
||||
|
@@ -150,13 +150,14 @@ RED.menu = (function() {
|
||||
|
||||
}
|
||||
function createMenu(options) {
|
||||
var topMenu = $("<ul/>",{class:"dropdown-menu pull-right"});
|
||||
|
||||
var menuParent = $("#"+options.id);
|
||||
|
||||
var topMenu = $("<ul/>",{id:options.id+"-submenu", class:"dropdown-menu pull-right"});
|
||||
|
||||
if (menuParent.length === 1) {
|
||||
topMenu.insertAfter(menuParent);
|
||||
if (options.id) {
|
||||
topMenu.attr({id:options.id+"-submenu"});
|
||||
var menuParent = $("#"+options.id);
|
||||
if (menuParent.length === 1) {
|
||||
topMenu.insertAfter(menuParent);
|
||||
}
|
||||
}
|
||||
|
||||
var lastAddedSeparator = false;
|
||||
|
@@ -32,8 +32,7 @@ RED.panels = (function() {
|
||||
var startPosition;
|
||||
var panelSizes = [];
|
||||
var modifiedSizes = false;
|
||||
var panelRatio;
|
||||
|
||||
var panelRatio = 0.5;
|
||||
separator.draggable({
|
||||
axis: vertical?"y":"x",
|
||||
containment: container,
|
||||
@@ -62,31 +61,47 @@ RED.panels = (function() {
|
||||
if (options.resize) {
|
||||
options.resize(newSizes[0],newSizes[1]);
|
||||
}
|
||||
panelRatio = newSizes[0]/size;
|
||||
panelRatio = newSizes[0]/(size-8);
|
||||
},
|
||||
stop:function(event,ui) {
|
||||
modifiedSizes = true;
|
||||
}
|
||||
});
|
||||
|
||||
return {
|
||||
resize: function(size) {
|
||||
var panelSizes = [$(children[0]).height(),$(children[1]).height()];
|
||||
var panel = {
|
||||
ratio: function(ratio) {
|
||||
panelRatio = ratio;
|
||||
modifiedSizes = true;
|
||||
if (ratio === 0 || ratio === 1) {
|
||||
separator.hide();
|
||||
} else {
|
||||
separator.show();
|
||||
}
|
||||
if (vertical) {
|
||||
panel.resize(container.height());
|
||||
} else {
|
||||
panel.resize(container.width());
|
||||
}
|
||||
},
|
||||
resize: function(size) {
|
||||
var panelSizes;
|
||||
if (vertical) {
|
||||
panelSizes = [$(children[0]).height(),$(children[1]).height()];
|
||||
container.height(size);
|
||||
} else {
|
||||
panelSizes = [$(children[0]).width(),$(children[1]).width()];
|
||||
container.width(size);
|
||||
}
|
||||
if (modifiedSizes) {
|
||||
var topPanelSize = panelRatio*size;
|
||||
var bottomPanelSize = size - topPanelSize - 48;
|
||||
var topPanelSize = panelRatio*(size-8);
|
||||
var bottomPanelSize = size - topPanelSize - 8;
|
||||
panelSizes = [topPanelSize,bottomPanelSize];
|
||||
if (vertical) {
|
||||
$(children[0]).height(panelSizes[0]);
|
||||
$(children[1]).height(panelSizes[1]);
|
||||
$(children[0]).outerHeight(panelSizes[0]);
|
||||
$(children[1]).outerHeight(panelSizes[1]);
|
||||
} else {
|
||||
$(children[0]).width(panelSizes[0]);
|
||||
$(children[1]).width(panelSizes[1]);
|
||||
$(children[0]).outerWidth(panelSizes[0]);
|
||||
$(children[1]).outerWidth(panelSizes[1]);
|
||||
}
|
||||
}
|
||||
if (options.resize) {
|
||||
@@ -94,6 +109,7 @@ RED.panels = (function() {
|
||||
}
|
||||
}
|
||||
}
|
||||
return panel;
|
||||
}
|
||||
|
||||
return {
|
||||
|
@@ -18,15 +18,19 @@ RED.popover = (function() {
|
||||
var deltaSizes = {
|
||||
"default": {
|
||||
top: 10,
|
||||
topTop: 30,
|
||||
leftRight: 17,
|
||||
leftLeft: 25,
|
||||
leftBottom: 8,
|
||||
leftTop: 11
|
||||
},
|
||||
"small": {
|
||||
top: 5,
|
||||
leftRight: 17,
|
||||
leftLeft: 16,
|
||||
leftBottom: 3,
|
||||
top: 6,
|
||||
topTop: 20,
|
||||
leftRight: 8,
|
||||
leftLeft: 26,
|
||||
leftBottom: 8,
|
||||
leftTop: 9
|
||||
}
|
||||
}
|
||||
function createPopover(options) {
|
||||
@@ -34,7 +38,7 @@ RED.popover = (function() {
|
||||
var direction = options.direction || "right";
|
||||
var trigger = options.trigger;
|
||||
var content = options.content;
|
||||
var delay = options.delay;
|
||||
var delay = options.delay || { show: 750, hide: 50 };
|
||||
var autoClose = options.autoClose;
|
||||
var width = options.width||"auto";
|
||||
var size = options.size||"default";
|
||||
@@ -48,7 +52,7 @@ RED.popover = (function() {
|
||||
|
||||
var openPopup = function(instant) {
|
||||
if (active) {
|
||||
div = $('<div class="red-ui-popover red-ui-popover-'+direction+'"></div>');
|
||||
div = $('<div class="red-ui-popover"></div>');
|
||||
if (size !== "default") {
|
||||
div.addClass("red-ui-popover-size-"+size);
|
||||
}
|
||||
@@ -75,13 +79,50 @@ RED.popover = (function() {
|
||||
var targetHeight = target.outerHeight();
|
||||
var divHeight = div.height();
|
||||
var divWidth = div.width();
|
||||
if (direction === 'right') {
|
||||
div.css({top: targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top,left:targetPos.left+targetWidth+deltaSizes[size].leftRight});
|
||||
} else if (direction === 'left') {
|
||||
div.css({top: targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top,left:targetPos.left-deltaSizes[size].leftLeft-divWidth});
|
||||
} else if (direction === 'bottom') {
|
||||
div.css({top: targetPos.top+targetHeight+deltaSizes[size].top,left:targetPos.left+targetWidth/2-divWidth/2 - deltaSizes[size].leftBottom});
|
||||
|
||||
var viewportTop = $(window).scrollTop();
|
||||
var viewportLeft = $(window).scrollLeft();
|
||||
var viewportBottom = viewportTop + $(window).height();
|
||||
var viewportRight = viewportLeft + $(window).width();
|
||||
var top = 0;
|
||||
var left = 0;
|
||||
var d = direction;
|
||||
if (d === 'right') {
|
||||
top = targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top;
|
||||
left = targetPos.left+targetWidth+deltaSizes[size].leftRight;
|
||||
} else if (d === 'left') {
|
||||
top = targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top;
|
||||
left = targetPos.left-deltaSizes[size].leftLeft-divWidth;
|
||||
} else if (d === 'bottom') {
|
||||
top = targetPos.top+targetHeight+deltaSizes[size].top;
|
||||
left = targetPos.left+targetWidth/2-divWidth/2 - deltaSizes[size].leftBottom;
|
||||
if (left < 0) {
|
||||
d = "right";
|
||||
top = targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top;
|
||||
left = targetPos.left+targetWidth+deltaSizes[size].leftRight;
|
||||
} else if (left+divWidth > viewportRight) {
|
||||
d = "left";
|
||||
top = targetPos.top+targetHeight/2-divHeight/2-deltaSizes[size].top;
|
||||
left = targetPos.left-deltaSizes[size].leftLeft-divWidth;
|
||||
if (top+divHeight+targetHeight/2 + 5 > viewportBottom) {
|
||||
top -= (top+divHeight+targetHeight/2 - viewportBottom + 5)
|
||||
}
|
||||
} else if (top+divHeight > viewportBottom) {
|
||||
d = 'top';
|
||||
top = targetPos.top-deltaSizes[size].topTop-divHeight;
|
||||
left = targetPos.left+targetWidth/2-divWidth/2 - deltaSizes[size].leftTop;
|
||||
}
|
||||
} else if (d === 'top') {
|
||||
top = targetPos.top-deltaSizes[size].topTop-divHeight;
|
||||
left = targetPos.left+targetWidth/2-divWidth/2 - deltaSizes[size].leftTop;
|
||||
if (top < 0) {
|
||||
d = 'bottom';
|
||||
top = targetPos.top+targetHeight+deltaSizes[size].top;
|
||||
left = targetPos.left+targetWidth/2-divWidth/2 - deltaSizes[size].leftBottom;
|
||||
}
|
||||
}
|
||||
div.addClass('red-ui-popover-'+d).css({top: top, left: left});
|
||||
|
||||
if (instant) {
|
||||
div.show();
|
||||
} else {
|
||||
@@ -90,10 +131,11 @@ RED.popover = (function() {
|
||||
}
|
||||
}
|
||||
var closePopup = function(instant) {
|
||||
$(document).off('mousedown.modal-popover-close');
|
||||
if (!active) {
|
||||
if (div) {
|
||||
if (instant) {
|
||||
$(this).remove();
|
||||
div.remove();
|
||||
} else {
|
||||
div.fadeOut("fast",function() {
|
||||
$(this).remove();
|
||||
@@ -110,12 +152,14 @@ RED.popover = (function() {
|
||||
active = true;
|
||||
timer = setTimeout(openPopup,delay.show);
|
||||
});
|
||||
target.on('mouseleave', function(e) {
|
||||
target.on('mouseleave disabled', function(e) {
|
||||
if (timer) {
|
||||
clearTimeout(timer);
|
||||
}
|
||||
active = false;
|
||||
setTimeout(closePopup,delay.hide);
|
||||
if (active) {
|
||||
active = false;
|
||||
setTimeout(closePopup,delay.hide);
|
||||
}
|
||||
});
|
||||
} else if (trigger === 'click') {
|
||||
target.click(function(e) {
|
||||
@@ -128,6 +172,29 @@ RED.popover = (function() {
|
||||
openPopup();
|
||||
}
|
||||
});
|
||||
if (autoClose) {
|
||||
target.on('mouseleave disabled', function(e) {
|
||||
if (timer) {
|
||||
clearTimeout(timer);
|
||||
}
|
||||
if (active) {
|
||||
active = false;
|
||||
setTimeout(closePopup,autoClose);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
} else if (trigger === 'modal') {
|
||||
$(document).on('mousedown.modal-popover-close', function (event) {
|
||||
var target = event.target;
|
||||
while (target.nodeName !== 'BODY' && target !== div[0]) {
|
||||
target = target.parentElement;
|
||||
}
|
||||
if (target.nodeName === 'BODY') {
|
||||
active = false;
|
||||
closePopup();
|
||||
}
|
||||
});
|
||||
} else if (autoClose) {
|
||||
setTimeout(function() {
|
||||
active = false;
|
||||
@@ -156,14 +223,25 @@ RED.popover = (function() {
|
||||
|
||||
return {
|
||||
create: createPopover,
|
||||
tooltip: function(target,content) {
|
||||
RED.popover.create({
|
||||
tooltip: function(target,content, action) {
|
||||
var label = content;
|
||||
if (action) {
|
||||
label = function() {
|
||||
var label = content;
|
||||
var shortcut = RED.keyboard.getShortcut(action);
|
||||
if (shortcut && shortcut.key) {
|
||||
label = $('<span>'+content+' <span class="red-ui-popover-key">'+RED.keyboard.formatKey(shortcut.key, true)+'</span></span>');
|
||||
}
|
||||
return label;
|
||||
}
|
||||
}
|
||||
return RED.popover.create({
|
||||
target:target,
|
||||
trigger: "hover",
|
||||
size: "small",
|
||||
direction: "bottom",
|
||||
content: content,
|
||||
delay: { show: 550, hide: 10 }
|
||||
content: label,
|
||||
delay: { show: 750, hide: 50 }
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@@ -66,6 +66,14 @@ RED.stack = (function() {
|
||||
}
|
||||
}
|
||||
entry.expand();
|
||||
} else if (entries.length === 2) {
|
||||
if (entries[0] === entry) {
|
||||
entries[0].collapse();
|
||||
entries[1].expand();
|
||||
} else {
|
||||
entries[1].collapse();
|
||||
entries[0].expand();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
entry.toggle();
|
||||
|
@@ -34,13 +34,42 @@ RED.tabs = (function() {
|
||||
if (options.vertical) {
|
||||
wrapper.addClass("red-ui-tabs-vertical");
|
||||
}
|
||||
if (options.addButton && typeof options.addButton === 'function') {
|
||||
if (options.addButton) {
|
||||
wrapper.addClass("red-ui-tabs-add");
|
||||
var addButton = $('<div class="red-ui-tab-button"><a href="#"><i class="fa fa-plus"></i></a></div>').appendTo(wrapper);
|
||||
addButton.find('a').click(function(evt) {
|
||||
evt.preventDefault();
|
||||
options.addButton();
|
||||
if (typeof options.addButton === 'function') {
|
||||
options.addButton();
|
||||
} else if (typeof options.addButton === 'string') {
|
||||
RED.actions.invoke(options.addButton);
|
||||
}
|
||||
})
|
||||
if (typeof options.addButton === 'string') {
|
||||
var l = options.addButton;
|
||||
if (options.addButtonCaption) {
|
||||
l = options.addButtonCaption
|
||||
}
|
||||
RED.popover.tooltip(addButton,l,options.addButton);
|
||||
}
|
||||
ul.on("dblclick", function(evt) {
|
||||
var existingTabs = ul.children();
|
||||
var clickX = evt.clientX;
|
||||
var targetIndex = 0;
|
||||
existingTabs.each(function(index) {
|
||||
var pos = $(this).offset();
|
||||
if (pos.left > clickX) {
|
||||
return false;
|
||||
}
|
||||
targetIndex = index+1;
|
||||
})
|
||||
if (typeof options.addButton === 'function') {
|
||||
options.addButton({index:targetIndex});
|
||||
} else if (typeof options.addButton === 'string') {
|
||||
RED.actions.invoke(options.addButton,{index:targetIndex});
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
}
|
||||
var scrollLeft;
|
||||
@@ -63,45 +92,54 @@ RED.tabs = (function() {
|
||||
|
||||
var collapsedButtonsRow = $('<div class="red-ui-tab-link-buttons"></div>').appendTo(wrapper);
|
||||
|
||||
var selectButton = $('<a href="#"><i class="fa fa-caret-down"></i></a>').appendTo(collapsedButtonsRow);
|
||||
selectButton.addClass("red-ui-tab-link-button-menu")
|
||||
selectButton.click(function(evt) {
|
||||
evt.preventDefault();
|
||||
if (!collapsibleMenu) {
|
||||
var pinnedOptions = [];
|
||||
var options = [];
|
||||
ul.children().each(function(i,el) {
|
||||
var id = $(el).data('tabId');
|
||||
var opt = {
|
||||
id:"red-ui-tabs-menu-option-"+id,
|
||||
icon: tabs[id].iconClass || defaultTabIcon,
|
||||
label: tabs[id].name,
|
||||
onselect: function() {
|
||||
activateTab(id);
|
||||
if (options.menu !== false) {
|
||||
var selectButton = $('<a href="#"><i class="fa fa-caret-down"></i></a>').appendTo(collapsedButtonsRow);
|
||||
selectButton.addClass("red-ui-tab-link-button-menu")
|
||||
selectButton.click(function(evt) {
|
||||
evt.stopPropagation();
|
||||
evt.preventDefault();
|
||||
if (!collapsibleMenu) {
|
||||
var pinnedOptions = [];
|
||||
var options = [];
|
||||
ul.children().each(function(i,el) {
|
||||
var id = $(el).data('tabId');
|
||||
var opt = {
|
||||
id:"red-ui-tabs-menu-option-"+id,
|
||||
icon: tabs[id].iconClass || defaultTabIcon,
|
||||
label: tabs[id].name,
|
||||
onselect: function() {
|
||||
activateTab(id);
|
||||
}
|
||||
};
|
||||
if (tabs[id].pinned) {
|
||||
pinnedOptions.push(opt);
|
||||
} else {
|
||||
options.push(opt);
|
||||
}
|
||||
};
|
||||
if (tabs[id].pinned) {
|
||||
pinnedOptions.push(opt);
|
||||
} else {
|
||||
options.push(opt);
|
||||
}
|
||||
});
|
||||
options = pinnedOptions.concat(options);
|
||||
collapsibleMenu = RED.menu.init({id:"debug-message-option-menu",options: options});
|
||||
});
|
||||
options = pinnedOptions.concat(options);
|
||||
collapsibleMenu = RED.menu.init({id:"debug-message-option-menu",options: options});
|
||||
collapsibleMenu.css({
|
||||
position: "absolute"
|
||||
})
|
||||
collapsibleMenu.appendTo("body");
|
||||
}
|
||||
var elementPos = selectButton.offset();
|
||||
collapsibleMenu.css({
|
||||
position: "absolute"
|
||||
top: (elementPos.top+selectButton.height()-2)+"px",
|
||||
left: (elementPos.left - collapsibleMenu.width() + selectButton.width())+"px"
|
||||
})
|
||||
collapsibleMenu.on('mouseleave', function(){ $(this).hide() });
|
||||
collapsibleMenu.on('mouseup', function() { $(this).hide() });
|
||||
collapsibleMenu.appendTo("body");
|
||||
}
|
||||
var elementPos = selectButton.offset();
|
||||
collapsibleMenu.css({
|
||||
top: (elementPos.top+selectButton.height()-20)+"px",
|
||||
left: (elementPos.left - collapsibleMenu.width() + selectButton.width())+"px"
|
||||
if (collapsibleMenu.is(":visible")) {
|
||||
$(document).off("click.tabmenu");
|
||||
} else {
|
||||
$(document).on("click.tabmenu", function(evt) {
|
||||
$(document).off("click.tabmenu");
|
||||
collapsibleMenu.hide();
|
||||
});
|
||||
}
|
||||
collapsibleMenu.toggle();
|
||||
})
|
||||
collapsibleMenu.toggle();
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -130,11 +168,86 @@ RED.tabs = (function() {
|
||||
ul.children().first().addClass("active");
|
||||
ul.children().addClass("red-ui-tab");
|
||||
|
||||
function onTabClick() {
|
||||
if (options.onclick) {
|
||||
options.onclick(tabs[$(this).attr('href').slice(1)]);
|
||||
function getSelection() {
|
||||
var selection = ul.find("li.red-ui-tab.selected");
|
||||
var selectedTabs = [];
|
||||
selection.each(function() {
|
||||
selectedTabs.push(tabs[$(this).find('a').attr('href').slice(1)])
|
||||
})
|
||||
return selectedTabs;
|
||||
}
|
||||
|
||||
function selectionChanged() {
|
||||
options.onselect(getSelection());
|
||||
}
|
||||
|
||||
function onTabClick(evt) {
|
||||
evt.preventDefault();
|
||||
var currentTab = ul.find("li.red-ui-tab.active");
|
||||
var thisTab = $(this).parent();
|
||||
var fireSelectionChanged = false;
|
||||
if (options.onselect) {
|
||||
if (evt.metaKey) {
|
||||
if (thisTab.hasClass("selected")) {
|
||||
thisTab.removeClass("selected");
|
||||
if (thisTab[0] !== currentTab[0]) {
|
||||
// Deselect background tab
|
||||
// - don't switch to it
|
||||
selectionChanged();
|
||||
return;
|
||||
} else {
|
||||
// Deselect current tab
|
||||
// - if nothing remains selected, do nothing
|
||||
// - otherwise switch to first selected tab
|
||||
var selection = ul.find("li.red-ui-tab.selected");
|
||||
if (selection.length === 0) {
|
||||
selectionChanged();
|
||||
return;
|
||||
}
|
||||
thisTab = selection.first();
|
||||
}
|
||||
} else {
|
||||
if (!currentTab.hasClass("selected")) {
|
||||
var currentTabObj = tabs[currentTab.find('a').attr('href').slice(1)];
|
||||
// Auto select current tab
|
||||
currentTab.addClass("selected");
|
||||
}
|
||||
thisTab.addClass("selected");
|
||||
}
|
||||
fireSelectionChanged = true;
|
||||
} else if (evt.shiftKey) {
|
||||
if (currentTab[0] !== thisTab[0]) {
|
||||
var firstTab,lastTab;
|
||||
if (currentTab.index() < thisTab.index()) {
|
||||
firstTab = currentTab;
|
||||
lastTab = thisTab;
|
||||
} else {
|
||||
firstTab = thisTab;
|
||||
lastTab = currentTab;
|
||||
}
|
||||
ul.find("li.red-ui-tab").removeClass("selected");
|
||||
firstTab.addClass("selected");
|
||||
lastTab.addClass("selected");
|
||||
firstTab.nextUntil(lastTab).addClass("selected");
|
||||
}
|
||||
fireSelectionChanged = true;
|
||||
} else {
|
||||
var selection = ul.find("li.red-ui-tab.selected");
|
||||
if (selection.length > 0) {
|
||||
selection.removeClass("selected");
|
||||
fireSelectionChanged = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var thisTabA = thisTab.find("a");
|
||||
if (options.onclick) {
|
||||
options.onclick(tabs[thisTabA.attr('href').slice(1)]);
|
||||
}
|
||||
activateTab(thisTabA);
|
||||
if (fireSelectionChanged) {
|
||||
selectionChanged();
|
||||
}
|
||||
activateTab($(this));
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -155,7 +268,12 @@ RED.tabs = (function() {
|
||||
}
|
||||
}
|
||||
}
|
||||
function onTabDblClick() {
|
||||
function onTabDblClick(evt) {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
if (evt.metaKey || evt.shiftKey) {
|
||||
return;
|
||||
}
|
||||
if (options.ondblclick) {
|
||||
options.ondblclick(tabs[$(this).attr('href').slice(1)]);
|
||||
}
|
||||
@@ -257,23 +375,23 @@ RED.tabs = (function() {
|
||||
currentActiveTabWidth = 0;
|
||||
}
|
||||
}
|
||||
if (options.collapsible) {
|
||||
console.log(currentTabWidth);
|
||||
}
|
||||
// if (options.collapsible) {
|
||||
// console.log(currentTabWidth);
|
||||
// }
|
||||
|
||||
tabs.css({width:currentTabWidth});
|
||||
if (tabWidth < 50) {
|
||||
ul.find(".red-ui-tab-close").hide();
|
||||
// ul.find(".red-ui-tab-close").hide();
|
||||
ul.find(".red-ui-tab-icon").hide();
|
||||
ul.find(".red-ui-tab-label").css({paddingLeft:Math.min(12,Math.max(0,tabWidth-38))+"px"})
|
||||
} else {
|
||||
ul.find(".red-ui-tab-close").show();
|
||||
// ul.find(".red-ui-tab-close").show();
|
||||
ul.find(".red-ui-tab-icon").show();
|
||||
ul.find(".red-ui-tab-label").css({paddingLeft:""})
|
||||
}
|
||||
if (currentActiveTabWidth !== 0) {
|
||||
ul.find("li.red-ui-tab.active").css({"width":options.minimumActiveTabWidth});
|
||||
ul.find("li.red-ui-tab.active .red-ui-tab-close").show();
|
||||
// ul.find("li.red-ui-tab.active .red-ui-tab-close").show();
|
||||
ul.find("li.red-ui-tab.active .red-ui-tab-icon").show();
|
||||
ul.find("li.red-ui-tab.active .red-ui-tab-label").css({paddingLeft:""})
|
||||
}
|
||||
@@ -288,6 +406,13 @@ RED.tabs = (function() {
|
||||
|
||||
|
||||
function removeTab(id) {
|
||||
if (options.onselect) {
|
||||
var selection = ul.find("li.red-ui-tab.selected");
|
||||
if (selection.length > 0) {
|
||||
selection.removeClass("selected");
|
||||
selectionChanged();
|
||||
}
|
||||
}
|
||||
var li = ul.find("a[href='#"+id+"']").parent();
|
||||
if (li.hasClass("active")) {
|
||||
var tab = li.prev();
|
||||
@@ -309,9 +434,26 @@ RED.tabs = (function() {
|
||||
}
|
||||
|
||||
return {
|
||||
addTab: function(tab) {
|
||||
addTab: function(tab,targetIndex) {
|
||||
if (options.onselect) {
|
||||
var selection = ul.find("li.red-ui-tab.selected");
|
||||
if (selection.length > 0) {
|
||||
selection.removeClass("selected");
|
||||
selectionChanged();
|
||||
}
|
||||
}
|
||||
tabs[tab.id] = tab;
|
||||
var li = $("<li/>",{class:"red-ui-tab"}).appendTo(ul);
|
||||
var li = $("<li/>",{class:"red-ui-tab"});
|
||||
if (ul.children().length === 0) {
|
||||
targetIndex = undefined;
|
||||
}
|
||||
if (targetIndex === 0) {
|
||||
li.prependTo(ul);
|
||||
} else if (targetIndex > 0) {
|
||||
li.insertAfter(ul.find("li:nth-child("+(targetIndex)+")"));
|
||||
} else {
|
||||
li.appendTo(ul);
|
||||
}
|
||||
li.attr('id',"red-ui-tab-"+(tab.id.replace(".","-")));
|
||||
li.data("tabId",tab.id);
|
||||
|
||||
@@ -336,7 +478,11 @@ RED.tabs = (function() {
|
||||
pinnedLink.insertAfter(collapsedButtonsRow.find("a.red-ui-tab-link-button-pinned:last"));
|
||||
}
|
||||
} else {
|
||||
pinnedLink.insertBefore(collapsedButtonsRow.find("a:last"));
|
||||
if (options.menu !== false) {
|
||||
pinnedLink.insertBefore(collapsedButtonsRow.find("a:last"));
|
||||
} else {
|
||||
pinnedLink.appendTo(collapsedButtonsRow);
|
||||
}
|
||||
}
|
||||
|
||||
pinnedLink.attr('id',li.attr('id')+"-link-button");
|
||||
@@ -353,20 +499,28 @@ RED.tabs = (function() {
|
||||
pinnedLink.addClass("red-ui-tab-link-button-pinned");
|
||||
pinnedTabsCount++;
|
||||
}
|
||||
RED.popover.tooltip($(pinnedLink), tab.name);
|
||||
RED.popover.tooltip($(pinnedLink), tab.name, tab.action);
|
||||
|
||||
}
|
||||
link.on("click",onTabClick);
|
||||
link.on("dblclick",onTabDblClick);
|
||||
|
||||
|
||||
if (tab.closeable) {
|
||||
li.addClass("red-ui-tabs-closeable")
|
||||
var closeLink = $("<a/>",{href:"#",class:"red-ui-tab-close"}).appendTo(li);
|
||||
closeLink.append('<i class="fa fa-times" />');
|
||||
|
||||
closeLink.on("click",function(event) {
|
||||
event.preventDefault();
|
||||
removeTab(tab.id);
|
||||
});
|
||||
}
|
||||
|
||||
var badges = $('<span class="red-ui-tabs-badges"></span>').appendTo(li);
|
||||
if (options.onselect) {
|
||||
$('<i class="red-ui-tabs-badge-changed fa fa-circle"></i>').appendTo(badges);
|
||||
$('<i class="red-ui-tabs-badge-selected fa fa-check-circle"></i>').appendTo(badges);
|
||||
}
|
||||
if (options.onadd) {
|
||||
options.onadd(tab);
|
||||
}
|
||||
@@ -474,6 +628,7 @@ RED.tabs = (function() {
|
||||
tab.find("span.bidiAware").text(label).attr('dir', RED.text.bidi.resolveBaseTextDir(label));
|
||||
updateTabWidths();
|
||||
},
|
||||
selection: getSelection,
|
||||
order: function(order) {
|
||||
var existingTabOrder = $.makeArray(ul.children().map(function() { return $(this).data('tabId');}));
|
||||
if (existingTabOrder.length !== order.length) {
|
||||
|
177
packages/node_modules/@node-red/editor-client/src/js/ui/common/treeList.js
vendored
Normal file
177
packages/node_modules/@node-red/editor-client/src/js/ui/common/treeList.js
vendored
Normal file
@@ -0,0 +1,177 @@
|
||||
/**
|
||||
* 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.
|
||||
**/
|
||||
(function($) {
|
||||
|
||||
/**
|
||||
* options:
|
||||
* - data : array - initial items to display in tree
|
||||
*
|
||||
* methods:
|
||||
* - data(items) - clears existing items and replaces with new data
|
||||
*
|
||||
* events:
|
||||
* - treelistselect : function(event, item) {}
|
||||
*
|
||||
*
|
||||
* data:
|
||||
* [
|
||||
* {
|
||||
* label: 'Local', // label for the item
|
||||
* icon: 'fa fa-rocket', // (optional) icon for the item
|
||||
* selected: true/false, // (optional) if present, display checkbox accordingly
|
||||
* children: [] | function(done) // (optional) an array of child items, or a function
|
||||
* // that will call the `done` callback with an array
|
||||
* // of child items
|
||||
* }
|
||||
* ]
|
||||
*
|
||||
*
|
||||
*
|
||||
* var treeList = $("<div>").css({width: "100%", height: "100%"}).treeList({data:[...]})
|
||||
* treeList.on('treelistselect', function(e,item) { console.log(item)})
|
||||
* treeList.treeList('data',[ ... ] )
|
||||
*
|
||||
*/
|
||||
|
||||
$.widget( "nodered.treeList", {
|
||||
_create: function() {
|
||||
var that = this;
|
||||
|
||||
this.element.addClass('red-ui-treeList');
|
||||
var wrapper = $('<div>',{class:'red-ui-treeList-container'}).appendTo(this.element);
|
||||
|
||||
this._data = [];
|
||||
|
||||
this._topList = $('<ol>').css({
|
||||
position:'absolute',
|
||||
top: 0,
|
||||
left:0,
|
||||
right:0,
|
||||
bottom:0
|
||||
}).appendTo(wrapper).editableList({
|
||||
addButton: false,
|
||||
scrollOnAdd: false,
|
||||
height: '100%',
|
||||
addItem: function(container,i,item) {
|
||||
that._addSubtree(container,item,0);
|
||||
}
|
||||
});
|
||||
if (this.options.data) {
|
||||
this.data(this.options.data);
|
||||
}
|
||||
},
|
||||
_addChildren: function(container,children,depth) {
|
||||
var that = this;
|
||||
var subtree = $('<ol>').appendTo(container).editableList({
|
||||
addButton: false,
|
||||
scrollOnAdd: false,
|
||||
height: 'auto',
|
||||
addItem: function(container,i,item) {
|
||||
that._addSubtree(container,item,depth+1);
|
||||
}
|
||||
});
|
||||
for (var i=0;i<children.length;i++) {
|
||||
subtree.editableList('addItem',children[i])
|
||||
}
|
||||
},
|
||||
_addSubtree: function(container, item, depth) {
|
||||
var that = this;
|
||||
var labelNodeType = "<label>";
|
||||
if (item.children && item.hasOwnProperty('selected')) {
|
||||
labelNodeType = "<div>";
|
||||
}
|
||||
var label = $(labelNodeType,{tabindex:"0",class:"red-ui-treeList-label"}).appendTo(container);
|
||||
if (item.class) {
|
||||
label.addClass(item.class);
|
||||
}
|
||||
label.css({
|
||||
paddingLeft: (depth*15)+'px'
|
||||
})
|
||||
label.on('mouseover',function(e) { that._trigger('itemmouseover',e,item); })
|
||||
label.on('mouseout',function(e) { that._trigger('itemmouseout',e,item); })
|
||||
|
||||
if (item.children) {
|
||||
$('<span class="red-ui-treeList-icon"><i class="fa fa-angle-right" /></span>').appendTo(label);
|
||||
// $('<span class="red-ui-treeList-icon"><i class="fa fa-folder-o" /></span>').appendTo(label);
|
||||
label.click(function(e) {
|
||||
if (!container.hasClass("built") && typeof item.children === 'function') {
|
||||
container.addClass('built');
|
||||
var childrenAdded = false;
|
||||
var spinner;
|
||||
item.children(function(children) {
|
||||
childrenAdded = true;
|
||||
that._addChildren(container,children,depth);
|
||||
if (spinner) {
|
||||
spinner.remove();
|
||||
}
|
||||
});
|
||||
if (!childrenAdded) {
|
||||
spinner = $('<div class="red-ui-treeList-spinner">').css({
|
||||
"background-position": (35+depth*15)+'px 50%'
|
||||
}).appendTo(container);
|
||||
}
|
||||
|
||||
}
|
||||
container.toggleClass("expanded");
|
||||
})
|
||||
} else {
|
||||
$('<span class="red-ui-treeList-icon"></span>').appendTo(label);
|
||||
}
|
||||
if (item.hasOwnProperty('selected')) {
|
||||
var selectWrapper = $('<span class="red-ui-treeList-icon"></span>').appendTo(label);
|
||||
var cb = $('<input type="checkbox">').prop('checked',item.selected).appendTo(selectWrapper);
|
||||
cb.on('click', function(e) {
|
||||
e.stopPropagation();
|
||||
});
|
||||
cb.on('change', function(e) {
|
||||
item.selected = this.checked;
|
||||
that._trigger("select",e,item);
|
||||
})
|
||||
} else if (!item.children) {
|
||||
label.click(function(e) {
|
||||
that._trigger("select",e,item)
|
||||
})
|
||||
}
|
||||
if (item.icon) {
|
||||
$('<span class="red-ui-treeList-icon"><i class="'+item.icon+'" /></span>').appendTo(label);
|
||||
}
|
||||
$('<span class="red-ui-treeList-label-text"></span>').html(item.label).appendTo(label);
|
||||
if (item.children) {
|
||||
if (Array.isArray(item.children)) {
|
||||
that._addChildren(container,item.children,depth);
|
||||
}
|
||||
if (item.expanded) {
|
||||
label.click();
|
||||
}
|
||||
}
|
||||
},
|
||||
empty: function() {
|
||||
this._topList.editableList('empty');
|
||||
},
|
||||
data: function(items) {
|
||||
if (items !== undefined) {
|
||||
this._data = items;
|
||||
this._topList.editableList('empty');
|
||||
for (var i=0; i<items.length;i++) {
|
||||
this._topList.editableList('addItem',items[i]);
|
||||
}
|
||||
} else {
|
||||
return this._data;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
})(jQuery);
|
@@ -537,6 +537,10 @@
|
||||
} else {
|
||||
this.selectLabel.text(opt.label);
|
||||
}
|
||||
if (this.optionMenu) {
|
||||
this.optionMenu.remove();
|
||||
this.optionMenu = null;
|
||||
}
|
||||
if (opt.options) {
|
||||
if (this.optionExpandButton) {
|
||||
this.optionExpandButton.hide();
|
||||
@@ -627,10 +631,6 @@
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (this.optionMenu) {
|
||||
this.optionMenu.remove();
|
||||
this.optionMenu = null;
|
||||
}
|
||||
if (this.optionSelectTrigger) {
|
||||
this.optionSelectTrigger.hide();
|
||||
}
|
||||
|
@@ -340,7 +340,7 @@ RED.deploy = (function() {
|
||||
|
||||
var unusedConfigNodes = [];
|
||||
RED.nodes.eachConfig(function(node) {
|
||||
if (node.users.length === 0 && (node._def.hasUsers !== false)) {
|
||||
if ((node._def.hasUsers !== false) && (node.users.length === 0)) {
|
||||
unusedConfigNodes.push(getNodeInfo(node));
|
||||
hasUnusedConfig = true;
|
||||
}
|
||||
|
@@ -498,7 +498,7 @@ RED.diff = (function() {
|
||||
nodeDiv.css('backgroundColor',colour);
|
||||
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"}).appendTo(nodeDiv);
|
||||
$('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, false);
|
||||
|
||||
return nodeDiv;
|
||||
}
|
||||
@@ -687,8 +687,7 @@ RED.diff = (function() {
|
||||
diff: remoteDiff
|
||||
}
|
||||
}
|
||||
createNodePropertiesTable(def,node,localNode,remoteNode).appendTo(div);
|
||||
|
||||
|
||||
var selectState = "";
|
||||
|
||||
if (conflicted) {
|
||||
@@ -707,6 +706,10 @@ RED.diff = (function() {
|
||||
createNodeConflictRadioBoxes(node,div,localNodeDiv,remoteNodeDiv,false,!conflicted,selectState,CurrentDiff);
|
||||
row.click(function(evt) {
|
||||
$(this).parent().toggleClass('collapsed');
|
||||
|
||||
if($(this).siblings('.node-diff-node-entry-properties').length === 0) {
|
||||
createNodePropertiesTable(def,node,localNode,remoteNode).appendTo(div);
|
||||
}
|
||||
});
|
||||
|
||||
return div;
|
||||
|
@@ -13,6 +13,10 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
|
||||
/**
|
||||
* @namespace RED.editor
|
||||
*/
|
||||
RED.editor = (function() {
|
||||
|
||||
|
||||
@@ -21,6 +25,8 @@ RED.editor = (function() {
|
||||
var editing_config_node = null;
|
||||
var subflowEditor;
|
||||
|
||||
var customEditTypes = {};
|
||||
|
||||
var editTrayWidthCache = {};
|
||||
|
||||
function getCredentialsURL(nodeType, nodeID) {
|
||||
@@ -124,6 +130,9 @@ RED.editor = (function() {
|
||||
if (/^\$\([a-zA-Z_][a-zA-Z0-9_]*\)$/.test(value)) {
|
||||
return true;
|
||||
}
|
||||
if (/^\$\{[a-zA-Z_][a-zA-Z0-9_]*\}$/.test(value)) {
|
||||
return true;
|
||||
}
|
||||
if ("required" in definition[property] && definition[property].required) {
|
||||
valid = value !== "";
|
||||
}
|
||||
@@ -569,7 +578,13 @@ RED.editor = (function() {
|
||||
var inputsDiv = $("#node-label-form-inputs");
|
||||
var outputsDiv = $("#node-label-form-outputs");
|
||||
|
||||
var inputCount = node.inputs || node._def.inputs || 0;
|
||||
var inputCount;
|
||||
if (node.type === 'subflow') {
|
||||
inputCount = node.in.length;
|
||||
} else {
|
||||
inputCount = node.inputs || node._def.inputs || 0;
|
||||
}
|
||||
|
||||
var children = inputsDiv.children();
|
||||
var childCount = children.length;
|
||||
if (childCount === 1 && $(children[0]).hasClass('node-label-form-none')) {
|
||||
@@ -588,7 +603,7 @@ RED.editor = (function() {
|
||||
for (i=inputCount;i<childCount;i++) {
|
||||
$(children[i]).remove();
|
||||
}
|
||||
if (outputCount === 0) {
|
||||
if (inputCount === 0) {
|
||||
buildLabelRow().appendTo(inputsDiv);
|
||||
}
|
||||
}
|
||||
@@ -598,7 +613,11 @@ RED.editor = (function() {
|
||||
var formOutputs = $("#node-input-outputs").val();
|
||||
|
||||
if (formOutputs === undefined) {
|
||||
outputCount = node.outputs || node._def.outputs || 0;
|
||||
if (node.type === 'subflow') {
|
||||
outputCount = node.out.length;
|
||||
} else {
|
||||
inputCount = node.outputs || node._def.outputs || 0;
|
||||
}
|
||||
} else if (isNaN(formOutputs)) {
|
||||
var outputMap = JSON.parse(formOutputs);
|
||||
var keys = Object.keys(outputMap);
|
||||
@@ -746,11 +765,11 @@ RED.editor = (function() {
|
||||
var iconDiv = $('<div>',{class:"red-ui-icon-list-icon"}).appendTo(iconList);
|
||||
var nodeDiv = $('<div>',{class:"red-ui-search-result-node"}).appendTo(iconDiv);
|
||||
var colour = RED.utils.getNodeColor(node.type, node._def);
|
||||
var icon_url = "icons/"+moduleName+"/"+icon;
|
||||
iconDiv.data('icon',icon_url)
|
||||
var icon_url = RED.settings.apiRootUrl+"icons/"+moduleName+"/"+icon;
|
||||
iconDiv.data('icon',icon_url);
|
||||
nodeDiv.css('backgroundColor',colour);
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"}).appendTo(nodeDiv);
|
||||
$('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
|
||||
if (iconPath.module === moduleName && iconPath.file === icon) {
|
||||
iconDiv.addClass("selected");
|
||||
@@ -775,52 +794,52 @@ RED.editor = (function() {
|
||||
function buildAppearanceForm(container,node) {
|
||||
var dialogForm = $('<form class="dialog-form form-horizontal" autocomplete="off"></form>').appendTo(container);
|
||||
|
||||
var inputCount = node.inputs || node._def.inputs || 0;
|
||||
var outputCount = node.outputs || node._def.outputs || 0;
|
||||
if (node.type === 'subflow') {
|
||||
inputCount = node.in.length;
|
||||
outputCount = node.out.length;
|
||||
}
|
||||
|
||||
var inputLabels = node.inputLabels || [];
|
||||
var outputLabels = node.outputLabels || [];
|
||||
|
||||
var inputPlaceholder = node._def.inputLabels?RED._("editor.defaultLabel"):RED._("editor.noDefaultLabel");
|
||||
var outputPlaceholder = node._def.outputLabels?RED._("editor.defaultLabel"):RED._("editor.noDefaultLabel");
|
||||
|
||||
var i,row;
|
||||
$('<div class="form-row"><span data-i18n="editor.labelInputs"></span><div id="node-label-form-inputs"></div></div>').appendTo(dialogForm);
|
||||
var inputsDiv = $("#node-label-form-inputs");
|
||||
if (inputCount > 0) {
|
||||
for (i=0;i<inputCount;i++) {
|
||||
buildLabelRow("input",i,inputLabels[i],inputPlaceholder).appendTo(inputsDiv);
|
||||
}
|
||||
} else {
|
||||
buildLabelRow().appendTo(inputsDiv);
|
||||
}
|
||||
$('<div class="form-row"><span data-i18n="editor.labelOutputs"></span><div id="node-label-form-outputs"></div></div>').appendTo(dialogForm);
|
||||
var outputsDiv = $("#node-label-form-outputs");
|
||||
if (outputCount > 0) {
|
||||
for (i=0;i<outputCount;i++) {
|
||||
buildLabelRow("output",i,outputLabels[i],outputPlaceholder).appendTo(outputsDiv);
|
||||
}
|
||||
} else {
|
||||
buildLabelRow().appendTo(outputsDiv);
|
||||
}
|
||||
|
||||
$('<div class="form-row">'+
|
||||
'<label for="node-input-show-label-btn" data-i18n="editor.label"></label>'+
|
||||
'<button id="node-input-show-label-btn" class="editor-button" style="min-width: 80px; text-align: left;" type="button"><i id="node-input-show-label-btn-i" class="fa fa-toggle-on"></i> <span id="node-input-show-label-label"></span></button> '+
|
||||
'<input type="checkbox" id="node-input-show-label" style="display: none;"/>'+
|
||||
'</div>').appendTo(dialogForm);
|
||||
|
||||
var setToggleState = function(state) {
|
||||
var i = $("#node-input-show-label-btn-i");
|
||||
if (!state) {
|
||||
i.addClass('fa-toggle-off');
|
||||
i.removeClass('fa-toggle-on');
|
||||
$("#node-input-show-label").prop("checked",false);
|
||||
$("#node-input-show-label-label").text(RED._("editor.hide"));
|
||||
} else {
|
||||
i.addClass('fa-toggle-on');
|
||||
i.removeClass('fa-toggle-off');
|
||||
$("#node-input-show-label").prop("checked",true);
|
||||
$("#node-input-show-label-label").text(RED._("editor.show"));
|
||||
}
|
||||
}
|
||||
dialogForm.find('#node-input-show-label-btn').on("click",function(e) {
|
||||
e.preventDefault();
|
||||
var i = $("#node-input-show-label-btn-i");
|
||||
setToggleState(i.hasClass('fa-toggle-off'));
|
||||
})
|
||||
if (!node.hasOwnProperty("l")) {
|
||||
// Show label if type not link
|
||||
node.l = !/^link (in|out)$/.test(node._def.type);
|
||||
}
|
||||
setToggleState(node.l);
|
||||
|
||||
// If a node has icon property in defaults, the icon of the node cannot be modified. (e.g, ui_button node in dashboard)
|
||||
if ((!node._def.defaults || !node._def.defaults.hasOwnProperty("icon"))) {
|
||||
$('<hr>').appendTo(dialogForm);
|
||||
var iconRow = $('<div class="form-row"></div>').appendTo(dialogForm);
|
||||
$('<label style="width: 50px" data-i18n="editor.settingIcon">').appendTo(iconRow);
|
||||
$('<label data-i18n="editor.settingIcon">').appendTo(iconRow);
|
||||
|
||||
var iconButton = $('<button class="editor-button">').appendTo(iconRow);
|
||||
var iconButton = $('<button class="editor-button" id="node-settings-icon-button">').appendTo(iconRow);
|
||||
|
||||
var nodeDiv = $('<div>',{class:"red-ui-search-result-node"}).appendTo(iconButton);
|
||||
var colour = RED.utils.getNodeColor(node.type, node._def);
|
||||
var icon_url = RED.utils.getNodeIcon(node._def,node);
|
||||
nodeDiv.css('backgroundColor',colour);
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"}).appendTo(nodeDiv);
|
||||
var iconDiv = $('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
|
||||
iconButton.click(function(e) {
|
||||
e.preventDefault();
|
||||
@@ -834,10 +853,44 @@ RED.editor = (function() {
|
||||
showIconPicker(iconRow,node,iconPath,function(newIcon) {
|
||||
$("#node-settings-icon").text(newIcon||"");
|
||||
var icon_url = RED.utils.getNodeIcon(node._def,{type:node.type,icon:newIcon});
|
||||
iconDiv.css("backgroundImage","url("+icon_url+")");
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
});
|
||||
})
|
||||
$('<div class="uneditable-input" id="node-settings-icon">').text(node.icon).appendTo(iconRow);
|
||||
});
|
||||
$('<div id="node-settings-icon">').text(node.icon).appendTo(iconButton);
|
||||
}
|
||||
|
||||
$('<div class="form-row"><span data-i18n="editor.portLabels"></span></div>').appendTo(dialogForm);
|
||||
|
||||
var inputCount = node.inputs || node._def.inputs || 0;
|
||||
var outputCount = node.outputs || node._def.outputs || 0;
|
||||
if (node.type === 'subflow') {
|
||||
inputCount = node.in.length;
|
||||
outputCount = node.out.length;
|
||||
}
|
||||
|
||||
var inputLabels = node.inputLabels || [];
|
||||
var outputLabels = node.outputLabels || [];
|
||||
|
||||
var inputPlaceholder = node._def.inputLabels?RED._("editor.defaultLabel"):RED._("editor.noDefaultLabel");
|
||||
var outputPlaceholder = node._def.outputLabels?RED._("editor.defaultLabel"):RED._("editor.noDefaultLabel");
|
||||
|
||||
$('<div class="form-row"><span style="margin-left: 50px;" data-i18n="editor.labelInputs"></span><div id="node-label-form-inputs"></div></div>').appendTo(dialogForm);
|
||||
var inputsDiv = $("#node-label-form-inputs");
|
||||
if (inputCount > 0) {
|
||||
for (i=0;i<inputCount;i++) {
|
||||
buildLabelRow("input",i,inputLabels[i],inputPlaceholder).appendTo(inputsDiv);
|
||||
}
|
||||
} else {
|
||||
buildLabelRow().appendTo(inputsDiv);
|
||||
}
|
||||
$('<div class="form-row"><span style="margin-left: 50px;" data-i18n="editor.labelOutputs"></span><div id="node-label-form-outputs"></div></div>').appendTo(dialogForm);
|
||||
var outputsDiv = $("#node-label-form-outputs");
|
||||
if (outputCount > 0) {
|
||||
for (i=0;i<outputCount;i++) {
|
||||
buildLabelRow("output",i,outputLabels[i],outputPlaceholder).appendTo(outputsDiv);
|
||||
}
|
||||
} else {
|
||||
buildLabelRow().appendTo(outputsDiv);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -884,9 +937,9 @@ RED.editor = (function() {
|
||||
|
||||
function buildDescriptionForm(container,node) {
|
||||
var dialogForm = $('<form class="dialog-form form-horizontal" autocomplete="off"></form>').appendTo(container);
|
||||
var toolbarRow = $('<div></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="position: absolute; right:0; bottom:100%;"><button id="node-info-input-info-expand" class="editor-button editor-button-small"><i class="fa fa-expand"></i></button></div>').appendTo(row);
|
||||
$('<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({
|
||||
id: "node-info-input-info-editor",
|
||||
mode: 'ace/mode/markdown',
|
||||
@@ -895,23 +948,6 @@ RED.editor = (function() {
|
||||
if (node.info) {
|
||||
nodeInfoEditor.getSession().setValue(node.info, -1);
|
||||
}
|
||||
|
||||
$('#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;
|
||||
}
|
||||
|
||||
@@ -1049,6 +1085,13 @@ RED.editor = (function() {
|
||||
var input = $("#node-input-"+d);
|
||||
if (input.attr('type') === "checkbox") {
|
||||
newValue = input.prop('checked');
|
||||
} else if (input.prop("nodeName") === "select" && input.attr("multiple") === "multiple") {
|
||||
// An empty select-multiple box returns null.
|
||||
// Need to treat that as an empty array.
|
||||
newValue = input.val();
|
||||
if (newValue == null) {
|
||||
newValue = [];
|
||||
}
|
||||
} else if ("format" in editing_node._def.defaults[d] && editing_node._def.defaults[d].format !== "" && input[0].nodeName === "DIV") {
|
||||
newValue = input.text();
|
||||
} else {
|
||||
@@ -1162,6 +1205,42 @@ RED.editor = (function() {
|
||||
}
|
||||
}
|
||||
|
||||
if (!$("#node-input-show-label").prop('checked')) {
|
||||
// Not checked - hide label
|
||||
if (!/^link (in|out)$/.test(node.type)) {
|
||||
// Not a link node - default state is true
|
||||
if (node.l !== false) {
|
||||
changes.l = node.l
|
||||
changed = true;
|
||||
}
|
||||
node.l = false;
|
||||
} else {
|
||||
// A link node - default state is false
|
||||
if (node.hasOwnProperty('l') && node.l) {
|
||||
changes.l = node.l
|
||||
changed = true;
|
||||
}
|
||||
delete node.l;
|
||||
}
|
||||
} else {
|
||||
// Checked - show label
|
||||
if (!/^link (in|out)$/.test(node.type)) {
|
||||
// Not a link node - default state is true
|
||||
if (node.hasOwnProperty('l') && !node.l) {
|
||||
changes.l = node.l
|
||||
changed = true;
|
||||
}
|
||||
delete node.l;
|
||||
} else {
|
||||
if (!node.l) {
|
||||
changes.l = node.l
|
||||
changed = true;
|
||||
}
|
||||
node.l = true;
|
||||
}
|
||||
}
|
||||
node.resize = true;
|
||||
|
||||
var oldInfo = node.info;
|
||||
if (nodeInfoEditor) {
|
||||
var newInfo = nodeInfoEditor.getValue();
|
||||
@@ -1267,7 +1346,8 @@ RED.editor = (function() {
|
||||
RED.tray.resize();
|
||||
}
|
||||
},
|
||||
collapsible: true
|
||||
collapsible: true,
|
||||
menu: false
|
||||
});
|
||||
if (editing_node) {
|
||||
RED.sidebar.info.refresh(editing_node);
|
||||
@@ -1288,8 +1368,8 @@ RED.editor = (function() {
|
||||
|
||||
var nodePropertiesTab = {
|
||||
id: "editor-tab-properties",
|
||||
label: "Properties",
|
||||
name: "Properties",
|
||||
label: RED._("editor-tab.properties"),
|
||||
name: RED._("editor-tab.properties"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-cog"
|
||||
};
|
||||
@@ -1299,8 +1379,8 @@ RED.editor = (function() {
|
||||
if (!node._def.defaults || !node._def.defaults.hasOwnProperty('info')) {
|
||||
var descriptionTab = {
|
||||
id: "editor-tab-description",
|
||||
label: "Description",
|
||||
name: "Description",
|
||||
label: RED._("editor-tab.description"),
|
||||
name: RED._("editor-tab.description"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-file-text-o",
|
||||
onchange: function() {
|
||||
@@ -1313,8 +1393,8 @@ RED.editor = (function() {
|
||||
|
||||
var appearanceTab = {
|
||||
id: "editor-tab-appearance",
|
||||
label: "Appearance",
|
||||
name: "Appearance",
|
||||
label: RED._("editor-tab.appearance"),
|
||||
name: RED._("editor-tab.appearance"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-object-group",
|
||||
onchange: function() {
|
||||
@@ -1454,8 +1534,8 @@ RED.editor = (function() {
|
||||
|
||||
var nodePropertiesTab = {
|
||||
id: "editor-tab-cproperties",
|
||||
label: "Properties",
|
||||
name: "Properties",
|
||||
label: RED._("editor-tab.properties"),
|
||||
name: RED._("editor-tab.properties"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-cog"
|
||||
};
|
||||
@@ -1465,8 +1545,8 @@ RED.editor = (function() {
|
||||
if (!node_def.defaults || !node_def.defaults.hasOwnProperty('info')) {
|
||||
var descriptionTab = {
|
||||
id: "editor-tab-description",
|
||||
label: "Description",
|
||||
name: "Description",
|
||||
label: RED._("editor-tab.description"),
|
||||
name: RED._("editor-tab.description"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-file-text-o",
|
||||
onchange: function() {
|
||||
@@ -1528,6 +1608,7 @@ RED.editor = (function() {
|
||||
$("#node-config-dialog-user-count").find("span").text(RED._("editor.nodesUse", {count:editing_config_node.users.length})).parent().show();
|
||||
}
|
||||
trayBody.i18n();
|
||||
trayFooter.i18n();
|
||||
finishedBuilding = true;
|
||||
done();
|
||||
});
|
||||
@@ -1977,8 +2058,8 @@ RED.editor = (function() {
|
||||
|
||||
var nodePropertiesTab = {
|
||||
id: "editor-tab-properties",
|
||||
label: "Properties",
|
||||
name: "Properties",
|
||||
label: RED._("editor-tab.properties"),
|
||||
name: RED._("editor-tab.properties"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-cog"
|
||||
};
|
||||
@@ -1987,8 +2068,8 @@ RED.editor = (function() {
|
||||
|
||||
var descriptionTab = {
|
||||
id: "editor-tab-description",
|
||||
label: "Description",
|
||||
name: "Description",
|
||||
label: RED._("editor-tab.description"),
|
||||
name: RED._("editor-tab.description"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-file-text-o",
|
||||
onchange: function() {
|
||||
@@ -2000,8 +2081,8 @@ RED.editor = (function() {
|
||||
|
||||
var appearanceTab = {
|
||||
id: "editor-tab-appearance",
|
||||
label: "Appearance",
|
||||
name: "Appearance",
|
||||
label: RED._("editor-tab.appearance"),
|
||||
name: RED._("editor-tab.appearance"),
|
||||
content: $('<div>', {class:"editor-tray-content"}).appendTo(editorContent).hide(),
|
||||
iconClass: "fa fa-object-group",
|
||||
onchange: function() {
|
||||
@@ -2072,7 +2153,7 @@ RED.editor = (function() {
|
||||
}
|
||||
|
||||
function showTypeEditor(type, options) {
|
||||
if (RED.editor.types.hasOwnProperty(type)) {
|
||||
if (customEditTypes.hasOwnProperty(type)) {
|
||||
if (editStack.length > 0) {
|
||||
options.parent = editStack[editStack.length-1].id;
|
||||
}
|
||||
@@ -2081,12 +2162,99 @@ RED.editor = (function() {
|
||||
options.onclose = function() {
|
||||
editStack.pop();
|
||||
}
|
||||
RED.editor.types[type].show(options);
|
||||
customEditTypes[type].show(options);
|
||||
} else {
|
||||
console.log("Unknown type editor:",type);
|
||||
}
|
||||
}
|
||||
|
||||
function createEditor(options) {
|
||||
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");
|
||||
var session = editor.getSession();
|
||||
session.on("changeAnnotation", function () {
|
||||
var annotations = session.getAnnotations() || [];
|
||||
var i = annotations.length;
|
||||
var len = annotations.length;
|
||||
while (i--) {
|
||||
if (/doctype first\. Expected/.test(annotations[i].text)) { annotations.splice(i, 1); }
|
||||
else if (/Unexpected End of file\. Expected/.test(annotations[i].text)) { annotations.splice(i, 1); }
|
||||
}
|
||||
if (len > annotations.length) { session.setAnnotations(annotations); }
|
||||
});
|
||||
if (options.mode) {
|
||||
session.setMode(options.mode);
|
||||
}
|
||||
if (options.foldStyle) {
|
||||
session.setFoldStyle(options.foldStyle);
|
||||
} else {
|
||||
session.setFoldStyle('markbeginend');
|
||||
}
|
||||
if (options.options) {
|
||||
editor.setOptions(options.options);
|
||||
} else {
|
||||
editor.setOptions({
|
||||
enableBasicAutocompletion:true,
|
||||
enableSnippets:true,
|
||||
tooltipFollowsMouse: false
|
||||
});
|
||||
}
|
||||
if (options.readOnly) {
|
||||
editor.setOption('readOnly',options.readOnly);
|
||||
editor.container.classList.add("ace_read-only");
|
||||
}
|
||||
if (options.hasOwnProperty('lineNumbers')) {
|
||||
editor.renderer.setOption('showGutter',options.lineNumbers);
|
||||
}
|
||||
editor.$blockScrolling = Infinity;
|
||||
if (options.value) {
|
||||
session.setValue(options.value,-1);
|
||||
}
|
||||
if (options.globals) {
|
||||
setTimeout(function() {
|
||||
if (!!session.$worker) {
|
||||
session.$worker.send("setOptions", [{globals: options.globals, esversion:6, sub:true, asi:true, maxerr:1000}]);
|
||||
}
|
||||
},100);
|
||||
}
|
||||
if (options.mode === 'ace/mode/markdown') {
|
||||
$(el).addClass("node-text-editor-container-toolbar");
|
||||
editor.toolbar = customEditTypes['_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 {
|
||||
init: function() {
|
||||
@@ -2099,14 +2267,7 @@ RED.editor = (function() {
|
||||
$("#node-dialog-cancel").click();
|
||||
$("#node-config-dialog-cancel").click();
|
||||
});
|
||||
|
||||
for (var type in RED.editor.types) {
|
||||
if (RED.editor.types.hasOwnProperty(type)) {
|
||||
RED.editor.types[type].init();
|
||||
}
|
||||
}
|
||||
},
|
||||
types: {},
|
||||
edit: showEditDialog,
|
||||
editConfig: showEditConfigNodeDialog,
|
||||
editSubflow: showEditSubflowDialog,
|
||||
@@ -2119,56 +2280,32 @@ RED.editor = (function() {
|
||||
validateNode: validateNode,
|
||||
updateNodeProperties: updateNodeProperties, // TODO: only exposed for edit-undo
|
||||
|
||||
/**
|
||||
* Show a type editor.
|
||||
* @param {string} type - the type to display
|
||||
* @param {object} options - options for the editor
|
||||
* @function
|
||||
* @memberof RED.editor
|
||||
*/
|
||||
showTypeEditor: showTypeEditor,
|
||||
|
||||
createEditor: function(options) {
|
||||
var editor = ace.edit(options.id||options.element);
|
||||
editor.setTheme("ace/theme/tomorrow");
|
||||
var session = editor.getSession();
|
||||
session.on("changeAnnotation", function () {
|
||||
var annotations = session.getAnnotations() || [];
|
||||
var i = annotations.length;
|
||||
var len = annotations.length;
|
||||
while (i--) {
|
||||
if (/doctype first\. Expected/.test(annotations[i].text)) { annotations.splice(i, 1); }
|
||||
else if (/Unexpected End of file\. Expected/.test(annotations[i].text)) { annotations.splice(i, 1); }
|
||||
}
|
||||
if (len > annotations.length) { session.setAnnotations(annotations); }
|
||||
});
|
||||
if (options.mode) {
|
||||
session.setMode(options.mode);
|
||||
}
|
||||
if (options.foldStyle) {
|
||||
session.setFoldStyle(options.foldStyle);
|
||||
} else {
|
||||
session.setFoldStyle('markbeginend');
|
||||
}
|
||||
if (options.options) {
|
||||
editor.setOptions(options.options);
|
||||
} else {
|
||||
editor.setOptions({
|
||||
enableBasicAutocompletion:true,
|
||||
enableSnippets:true
|
||||
});
|
||||
}
|
||||
if (options.readOnly) {
|
||||
editor.setOption('readOnly',options.readOnly);
|
||||
editor.container.classList.add("ace_read-only");
|
||||
}
|
||||
if (options.hasOwnProperty('lineNumbers')) {
|
||||
editor.renderer.setOption('showGutter',options.lineNumbers);
|
||||
}
|
||||
editor.$blockScrolling = Infinity;
|
||||
if (options.value) {
|
||||
session.setValue(options.value,-1);
|
||||
}
|
||||
if (options.globals) {
|
||||
setTimeout(function() {
|
||||
if (!!session.$worker) {
|
||||
session.$worker.send("setOptions", [{globals: options.globals, esversion:6, sub:true, asi:true, maxerr:1000}]);
|
||||
}
|
||||
},100);
|
||||
}
|
||||
return editor;
|
||||
}
|
||||
/**
|
||||
* Register a type editor.
|
||||
* @param {string} type - the type name
|
||||
* @param {object} options - the editor definition
|
||||
* @function
|
||||
* @memberof RED.editor
|
||||
*/
|
||||
registerTypeEditor: function(type, definition) {
|
||||
customEditTypes[type] = definition;
|
||||
},
|
||||
|
||||
/**
|
||||
* Create a editor ui component
|
||||
* @param {object} options - the editor options
|
||||
* @function
|
||||
* @memberof RED.editor
|
||||
*/
|
||||
createEditor: createEditor
|
||||
}
|
||||
})();
|
||||
|
@@ -13,8 +13,7 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
RED.editor.types._buffer = (function() {
|
||||
|
||||
(function() {
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_buffer"><div id="node-input-buffer-panels"><div id="node-input-buffer-panel-str" class="red-ui-panel"><div class="form-row" style="margin-bottom: 3px; text-align: right;"><span class="node-input-buffer-type"><i class="fa fa-exclamation-circle"></i> <span id="node-input-buffer-type-string" data-i18n="bufferEditor.modeString"></span><span id="node-input-buffer-type-array" data-i18n="bufferEditor.modeArray"></span></span></div><div class="form-row node-text-editor-row"><div class="node-text-editor" id="node-input-buffer-str"></div></div></div><div id="node-input-buffer-panel-bin" class="red-ui-panel"><div class="form-row node-text-editor-row" style="margin-top: 10px"><div class="node-text-editor" id="node-input-buffer-bin"></div></div></div></div></script>';
|
||||
|
||||
@@ -45,10 +44,7 @@ RED.editor.types._buffer = (function() {
|
||||
}
|
||||
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
},
|
||||
var definition = {
|
||||
show: function(options) {
|
||||
var value = options.value;
|
||||
var onComplete = options.complete;
|
||||
@@ -206,4 +202,7 @@ RED.editor.types._buffer = (function() {
|
||||
RED.tray.show(trayOptions);
|
||||
}
|
||||
}
|
||||
$(template).appendTo(document.body);
|
||||
RED.editor.registerTypeEditor("_buffer", definition);
|
||||
|
||||
})();
|
||||
|
@@ -13,7 +13,7 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
RED.editor.types._expression = (function() {
|
||||
(function() {
|
||||
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_expression">'+
|
||||
@@ -46,10 +46,7 @@ RED.editor.types._expression = (function() {
|
||||
'</script>';
|
||||
var expressionTestCache = {};
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
},
|
||||
var definition = {
|
||||
show: function(options) {
|
||||
var expressionTestCacheId = options.parent||"_";
|
||||
var value = options.value;
|
||||
@@ -349,4 +346,6 @@ RED.editor.types._expression = (function() {
|
||||
RED.tray.show(trayOptions);
|
||||
}
|
||||
}
|
||||
$(template).appendTo(document.body);
|
||||
RED.editor.registerTypeEditor("_expression", definition);
|
||||
})();
|
||||
|
@@ -13,15 +13,12 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
RED.editor.types._js = (function() {
|
||||
(function() {
|
||||
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_js"><div class="form-row node-text-editor-row"><div style="height: 200px;min-height: 150px;" class="node-text-editor" id="node-input-js"></div></div></script>';
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
},
|
||||
var definition = {
|
||||
show: function(options) {
|
||||
var value = options.value;
|
||||
var onComplete = options.complete;
|
||||
@@ -66,7 +63,7 @@ RED.editor.types._js = (function() {
|
||||
var dialogForm = RED.editor.buildEditForm(tray.find('.editor-tray-body'),'dialog-form',type,'editor');
|
||||
expressionEditor = RED.editor.createEditor({
|
||||
id: 'node-input-js',
|
||||
mode: 'ace/mode/javascript',
|
||||
mode: options.mode || 'ace/mode/javascript',
|
||||
value: value,
|
||||
globals: {
|
||||
msg:true,
|
||||
@@ -99,4 +96,7 @@ RED.editor.types._js = (function() {
|
||||
RED.tray.show(trayOptions);
|
||||
}
|
||||
}
|
||||
$(template).appendTo(document.body);
|
||||
RED.editor.registerTypeEditor("_js", definition);
|
||||
|
||||
})();
|
||||
|
@@ -13,15 +13,12 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
RED.editor.types._json = (function() {
|
||||
(function() {
|
||||
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_json"><div class="form-row" style="margin-bottom: 3px; text-align: right;"><button id="node-input-json-reformat" class="editor-button editor-button-small"><span data-i18n="jsonEditor.format"></span></button></div><div class="form-row node-text-editor-row"><div style="height: 200px;min-height: 150px;" class="node-text-editor" id="node-input-json"></div></div></script>';
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
},
|
||||
var definition = {
|
||||
show: function(options) {
|
||||
var value = options.value;
|
||||
var onComplete = options.complete;
|
||||
@@ -115,4 +112,6 @@ RED.editor.types._json = (function() {
|
||||
RED.tray.show(trayOptions);
|
||||
}
|
||||
}
|
||||
$(template).appendTo(document.body);
|
||||
RED.editor.registerTypeEditor("_json", definition);
|
||||
})();
|
||||
|
@@ -13,26 +13,45 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
**/
|
||||
RED.editor.types._markdown = (function() {
|
||||
(function() {
|
||||
|
||||
var toolbarTemplate = '<div style="margin-bottom: 5px">'+
|
||||
'<span class="button-group">'+
|
||||
'<button class="editor-button" data-style="h1" style="font-size:1.1em; font-weight: bold">h1</button>'+
|
||||
'<button class="editor-button" data-style="h2" style="font-size:1.0em; font-weight: bold">h2</button>'+
|
||||
'<button class="editor-button" data-style="h3" style="font-size:0.9em; font-weight: bold">h3</button>'+
|
||||
'</span>'+
|
||||
'<span class="button-group">'+
|
||||
'<button class="editor-button" data-style="b"><i class="fa fa-bold"></i></button>'+
|
||||
'<button class="editor-button" data-style="i"><i class="fa fa-italic"></i></button>'+
|
||||
'<button class="editor-button" data-style="code"><i class="fa fa-code"></i></button>'+
|
||||
'</span>'+
|
||||
'<span class="button-group">'+
|
||||
'<button class="editor-button" data-style="ol"><i class="fa fa-list-ol"></i></button>'+
|
||||
'<button class="editor-button" data-style="ul"><i class="fa fa-list-ul"></i></button>'+
|
||||
'<button class="editor-button" data-style="bq"><i class="fa fa-quote-left"></i></button>'+
|
||||
'<button class="editor-button" data-style="hr"><i class="fa fa-minus"></i></button>'+
|
||||
'<button class="editor-button" data-style="link"><i class="fa fa-link"></i></button>'+
|
||||
'</span>'
|
||||
'</div>';
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_markdown">'+
|
||||
'<div id="node-input-markdown-panels">'+
|
||||
'<div id="node-input-markdown-panel-editor" class="red-ui-panel">'+
|
||||
'<div class="node-text-editor" style="height: calc(100% - 20px)" id="node-input-markdown"></div>'+
|
||||
'</div>'+
|
||||
'<div class="red-ui-panel">'+
|
||||
'<div id="node-input-markdown-panel-preview" style="padding: 20px;" class="node-help"></div>'+
|
||||
'</div>'+
|
||||
'</script>';
|
||||
'<div id="node-input-markdown-panels">'+
|
||||
'<div id="node-input-markdown-panel-editor" class="red-ui-panel">'+
|
||||
'<div style="height: 100%; margin: auto; max-width: 1000px;">'+
|
||||
'<div id="node-input-markdown-toolbar"></div>'+
|
||||
'<div class="node-text-editor" style="height: 100%" id="node-input-markdown"></div>'+
|
||||
'</div>'+
|
||||
'</div>'+
|
||||
'<div class="red-ui-panel">'+
|
||||
'<div class="node-input-markdown-panel-preview node-help"></div>'+
|
||||
'</div>'+
|
||||
'</script>';
|
||||
|
||||
|
||||
var panels;
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
},
|
||||
var definition = {
|
||||
show: function(options) {
|
||||
var value = options.value;
|
||||
var onComplete = options.complete;
|
||||
@@ -75,15 +94,16 @@ RED.editor.types._markdown = (function() {
|
||||
expressionEditor = RED.editor.createEditor({
|
||||
id: 'node-input-markdown',
|
||||
value: value,
|
||||
mode:"ace/mode/markdown"
|
||||
mode:"ace/mode/markdown",
|
||||
expandable: false
|
||||
});
|
||||
var changeTimer;
|
||||
expressionEditor.getSession().on("change", function() {
|
||||
clearTimeout(changeTimer);
|
||||
changeTimer = setTimeout(function() {
|
||||
var currentScrollTop = $("#node-input-markdown-panel-preview").scrollTop();
|
||||
$("#node-input-markdown-panel-preview").html(marked(expressionEditor.getValue()));
|
||||
$("#node-input-markdown-panel-preview").scrollTop(currentScrollTop);
|
||||
var currentScrollTop = $(".node-input-markdown-panel-preview").scrollTop();
|
||||
$(".node-input-markdown-panel-preview").html(marked(expressionEditor.getValue()));
|
||||
$(".node-input-markdown-panel-preview").scrollTop(currentScrollTop);
|
||||
},200);
|
||||
})
|
||||
if (options.header) {
|
||||
@@ -91,7 +111,7 @@ RED.editor.types._markdown = (function() {
|
||||
}
|
||||
|
||||
if (value) {
|
||||
$("#node-input-markdown-panel-preview").html(marked(expressionEditor.getValue()));
|
||||
$(".node-input-markdown-panel-preview").html(marked(expressionEditor.getValue()));
|
||||
}
|
||||
panels = RED.panels.create({
|
||||
id:"node-input-markdown-panels",
|
||||
@@ -100,6 +120,23 @@ RED.editor.types._markdown = (function() {
|
||||
expressionEditor.resize();
|
||||
}
|
||||
});
|
||||
panels.ratio(1);
|
||||
|
||||
$('<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>'+
|
||||
'</span>').appendTo(expressionEditor.toolbar);
|
||||
|
||||
$("#node-btn-markdown-preview").click(function(e) {
|
||||
e.preventDefault();
|
||||
if ($(this).hasClass("selected")) {
|
||||
$(this).removeClass("selected");
|
||||
panels.ratio(1);
|
||||
} else {
|
||||
$(this).addClass("selected");
|
||||
panels.ratio(0.5);
|
||||
}
|
||||
});
|
||||
RED.popover.tooltip($("#node-btn-markdown-preview"), RED._("markdownEditor.toggle-preview"));
|
||||
|
||||
if (options.cursor) {
|
||||
expressionEditor.gotoLine(options.cursor.row+1,options.cursor.column,false);
|
||||
@@ -116,7 +153,60 @@ RED.editor.types._markdown = (function() {
|
||||
show: function() {}
|
||||
}
|
||||
RED.tray.show(trayOptions);
|
||||
},
|
||||
|
||||
buildToolbar: function(container, editor) {
|
||||
var styleActions = {
|
||||
'h1': { newline: true, before:"# ", tooltip:RED._("markdownEditor.heading1")},
|
||||
'h2': { newline: true, before:"## ", tooltip:RED._("markdownEditor.heading2")},
|
||||
'h3': { newline: true, before:"### ", tooltip:RED._("markdownEditor.heading3")},
|
||||
'b': { before:"**", after: "**", tooltip: RED._("markdownEditor.bold")},
|
||||
'i': { before:"_", after: "_", tooltip: RED._("markdownEditor.italic")},
|
||||
'code': { before:"`", after: "`", tooltip: RED._("markdownEditor.code")},
|
||||
'ol': { before:" * ", newline: true, tooltip: RED._("markdownEditor.ordered-list")},
|
||||
'ul': { before:" - ", newline: true, tooltip: RED._("markdownEditor.unordered-list")},
|
||||
'bq': { before:"> ", newline: true, tooltip: RED._("markdownEditor.quote")},
|
||||
'link': { before:"[", after: "]()", tooltip: RED._("markdownEditor.link")},
|
||||
'hr': { before:"\n---\n\n", tooltip: RED._("markdownEditor.horizontal-rule")}
|
||||
}
|
||||
var toolbar = $(toolbarTemplate).appendTo(container);
|
||||
toolbar.find('button[data-style]').each(function(el) {
|
||||
var style = styleActions[$(this).data('style')];
|
||||
$(this).click(function(e) {
|
||||
e.preventDefault();
|
||||
var current = editor.getSelectedText();
|
||||
var range = editor.selection.getRange();
|
||||
if (style.newline) {
|
||||
var offset = 0;
|
||||
var beforeOffset = ((style.before||"").match(/\n/g)||[]).length;
|
||||
var afterOffset = ((style.after||"").match(/\n/g)||[]).length;
|
||||
for (var i = range.start.row; i<= range.end.row+offset; i++) {
|
||||
if (style.before) {
|
||||
editor.session.insert({row:i, column:0},style.before);
|
||||
offset += beforeOffset;
|
||||
i += beforeOffset;
|
||||
}
|
||||
if (style.after) {
|
||||
editor.session.insert({row:i, column:Infinity},style.after);
|
||||
offset += afterOffset;
|
||||
i += afterOffset;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
editor.session.replace(editor.selection.getRange(), (style.before||"")+current+(style.after||""));
|
||||
if (current === "") {
|
||||
editor.gotoLine(range.start.row+1,range.start.column+(style.before||"").length,false);
|
||||
}
|
||||
}
|
||||
editor.focus();
|
||||
});
|
||||
if (style.tooltip) {
|
||||
RED.popover.tooltip($(this),style.tooltip);
|
||||
}
|
||||
})
|
||||
return toolbar;
|
||||
}
|
||||
}
|
||||
$(template).appendTo(document.body);
|
||||
RED.editor.registerTypeEditor("_markdown", definition);
|
||||
})();
|
||||
|
121
packages/node_modules/@node-red/editor-client/src/js/ui/event-log.js
vendored
Normal file
121
packages/node_modules/@node-red/editor-client/src/js/ui/event-log.js
vendored
Normal file
@@ -0,0 +1,121 @@
|
||||
/**
|
||||
* 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.eventLog = (function() {
|
||||
|
||||
var template = '<script type="text/x-red" data-template-name="_eventLog"><div class="form-row node-text-editor-row"><div style="height: 100%;min-height: 150px;" class="node-text-editor" id="event-log-editor"></div></div></script>';
|
||||
|
||||
var eventLogEditor;
|
||||
var backlog = [];
|
||||
var shown = false;
|
||||
|
||||
function appendLogLine(line) {
|
||||
backlog.push(line);
|
||||
if (backlog.length > 500) {
|
||||
backlog = backlog.slice(-500);
|
||||
}
|
||||
if (eventLogEditor) {
|
||||
eventLogEditor.getSession().insert({
|
||||
row: eventLogEditor.getSession().getLength(),
|
||||
column: 0
|
||||
}, "\n" + line);
|
||||
eventLogEditor.scrollToLine(eventLogEditor.getSession().getLength());
|
||||
}
|
||||
}
|
||||
return {
|
||||
init: function() {
|
||||
$(template).appendTo(document.body);
|
||||
RED.actions.add("core:show-event-log",RED.eventLog.show);
|
||||
},
|
||||
show: function() {
|
||||
if (shown) {
|
||||
return;
|
||||
}
|
||||
shown = true;
|
||||
var type = "_eventLog"
|
||||
|
||||
var trayOptions = {
|
||||
title: RED._("eventLog.title"),
|
||||
width: Infinity,
|
||||
buttons: [
|
||||
{
|
||||
id: "node-dialog-close",
|
||||
text: RED._("common.label.close"),
|
||||
click: function() {
|
||||
RED.tray.close();
|
||||
}
|
||||
}
|
||||
],
|
||||
resize: function(dimensions) {
|
||||
var rows = $("#dialog-form>div:not(.node-text-editor-row)");
|
||||
var editorRow = $("#dialog-form>div.node-text-editor-row");
|
||||
var height = $("#dialog-form").height();
|
||||
for (var i=0;i<rows.size();i++) {
|
||||
height -= $(rows[i]).outerHeight(true);
|
||||
}
|
||||
height -= (parseInt($("#dialog-form").css("marginTop"))+parseInt($("#dialog-form").css("marginBottom")));
|
||||
$(".node-text-editor").css("height",height+"px");
|
||||
eventLogEditor.resize();
|
||||
},
|
||||
open: function(tray) {
|
||||
var trayBody = tray.find('.editor-tray-body');
|
||||
var dialogForm = RED.editor.buildEditForm(tray.find('.editor-tray-body'),'dialog-form',type,'editor');
|
||||
eventLogEditor = RED.editor.createEditor({
|
||||
id: 'event-log-editor',
|
||||
value: backlog.join("\n"),
|
||||
lineNumbers: false,
|
||||
readOnly: true,
|
||||
options: {
|
||||
showPrintMargin: false
|
||||
}
|
||||
});
|
||||
setTimeout(function() {
|
||||
eventLogEditor.scrollToLine(eventLogEditor.getSession().getLength());
|
||||
},200);
|
||||
dialogForm.i18n();
|
||||
},
|
||||
close: function() {
|
||||
eventLogEditor.destroy();
|
||||
eventLogEditor = null;
|
||||
shown = false;
|
||||
},
|
||||
show: function() {}
|
||||
}
|
||||
RED.tray.show(trayOptions);
|
||||
},
|
||||
log: function(id,payload) {
|
||||
var ts = (new Date(payload.ts)).toISOString()+" ";
|
||||
if (payload.type) {
|
||||
ts += "["+payload.type+"] "
|
||||
}
|
||||
if (payload.data) {
|
||||
var data = payload.data;
|
||||
if (data.endsWith('\n')) {
|
||||
data = data.substring(0,data.length-1);
|
||||
}
|
||||
var lines = data.split(/\n/);
|
||||
lines.forEach(function(line) {
|
||||
appendLogLine(ts+line);
|
||||
})
|
||||
}
|
||||
},
|
||||
startEvent: function(name) {
|
||||
backlog.push("");
|
||||
backlog.push("-----------------------------------------------------------");
|
||||
backlog.push((new Date()).toISOString()+" "+name);
|
||||
backlog.push("");
|
||||
}
|
||||
}
|
||||
})();
|
@@ -19,7 +19,7 @@ RED.keyboard = (function() {
|
||||
|
||||
var handlers = {};
|
||||
var partialState;
|
||||
|
||||
RED.h = handlers;
|
||||
var keyMap = {
|
||||
"left":37,
|
||||
"up":38,
|
||||
@@ -161,6 +161,19 @@ RED.keyboard = (function() {
|
||||
return [keycode,modifiers];
|
||||
}
|
||||
|
||||
function matchHandlerToEvent(evt,handler) {
|
||||
var target = evt.target;
|
||||
var depth = 0;
|
||||
while (target.nodeName !== 'BODY' && target.id !== handler.scope) {
|
||||
target = target.parentElement;
|
||||
depth++;
|
||||
}
|
||||
if (target.nodeName === 'BODY' && handler.scope !== "*") {
|
||||
depth = -1;
|
||||
}
|
||||
return depth;
|
||||
}
|
||||
|
||||
function resolveKeyEvent(evt) {
|
||||
var slot = partialState||handlers;
|
||||
if (evt.ctrlKey || evt.metaKey) {
|
||||
@@ -175,7 +188,7 @@ RED.keyboard = (function() {
|
||||
var keyCode = firefoxKeyCodeMap[evt.keyCode] || evt.keyCode;
|
||||
if (slot && slot[keyCode]) {
|
||||
var handler = slot[keyCode];
|
||||
if (!handler.scope) {
|
||||
if (!handler.handlers) {
|
||||
if (partialState) {
|
||||
partialState = null;
|
||||
return resolveKeyEvent(evt);
|
||||
@@ -186,14 +199,19 @@ RED.keyboard = (function() {
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
} else if (handler.scope && handler.scope !== "*") {
|
||||
var target = evt.target;
|
||||
while (target.nodeName !== 'BODY' && target.id !== handler.scope) {
|
||||
target = target.parentElement;
|
||||
}
|
||||
if (target.nodeName === 'BODY') {
|
||||
handler = null;
|
||||
} else {
|
||||
var depth = Infinity;
|
||||
var matchedHandler;
|
||||
var i = 0;
|
||||
var l = handler.handlers.length;
|
||||
for (i=0;i<l;i++) {
|
||||
var d = matchHandlerToEvent(evt,handler.handlers[i]);
|
||||
if (d > -1 && d < depth) {
|
||||
depth = d;
|
||||
matchedHandler = handler.handlers[i];
|
||||
}
|
||||
}
|
||||
handler = matchedHandler;
|
||||
}
|
||||
partialState = null;
|
||||
return handler;
|
||||
@@ -265,6 +283,8 @@ RED.keyboard = (function() {
|
||||
slot = slot[key];
|
||||
//slot[key] = {scope: scope, ondown:cbdown};
|
||||
}
|
||||
slot.handlers = slot.handlers || [];
|
||||
slot.handlers.push({scope:scope,ondown:cbdown})
|
||||
slot.scope = scope;
|
||||
slot.ondown = cbdown;
|
||||
}
|
||||
@@ -315,11 +335,13 @@ RED.keyboard = (function() {
|
||||
}
|
||||
delete slot.scope;
|
||||
delete slot.ondown;
|
||||
// TODO: this wipes everything! Need to have something to identify handler
|
||||
delete slot.handlers;
|
||||
}
|
||||
|
||||
var cmdCtrlKey = '<span class="help-key">'+(isMac?'⌘':'Ctrl')+'</span>';
|
||||
|
||||
function formatKey(key) {
|
||||
function formatKey(key,plain) {
|
||||
var formattedKey = isMac?key.replace(/ctrl-?/,"⌘"):key;
|
||||
formattedKey = isMac?formattedKey.replace(/alt-?/,"⌥"):key;
|
||||
formattedKey = formattedKey.replace(/shift-?/,"⇧")
|
||||
@@ -327,6 +349,9 @@ RED.keyboard = (function() {
|
||||
formattedKey = formattedKey.replace(/up/,"↑")
|
||||
formattedKey = formattedKey.replace(/right/,"→")
|
||||
formattedKey = formattedKey.replace(/down/,"↓")
|
||||
if (plain) {
|
||||
return formattedKey;
|
||||
}
|
||||
return '<span class="help-key-block"><span class="help-key">'+formattedKey.split(" ").join('</span> <span class="help-key">')+'</span></span>';
|
||||
}
|
||||
|
||||
|
@@ -458,7 +458,10 @@ RED.library = (function() {
|
||||
click: function() {
|
||||
//TODO: move this to RED.library
|
||||
var flowName = $("#node-input-library-filename").val();
|
||||
if (!/^\s*$/.test(flowName)) {
|
||||
flowName = flowName.trim();
|
||||
if(flowName === "" || flowName.endsWith("/")) {
|
||||
RED.notify(RED._("library.invalidFilename"),"warning");
|
||||
} else {
|
||||
$.ajax({
|
||||
url:'library/flows/'+flowName,
|
||||
type: "POST",
|
||||
|
@@ -16,6 +16,10 @@
|
||||
RED.notifications = (function() {
|
||||
|
||||
/*
|
||||
If RED.notifications.hide is set to true, all notifications will be hidden.
|
||||
This is to help with UI testing in certain cases and not intended for the
|
||||
end-user.
|
||||
|
||||
// Example usage for a modal dialog with buttons
|
||||
var myNotification = RED.notify("This is the message to display",{
|
||||
modal: true,
|
||||
@@ -52,6 +56,11 @@ RED.notifications = (function() {
|
||||
type = options.type;
|
||||
}
|
||||
|
||||
if (options.id && persistentNotifications.hasOwnProperty(options.id)) {
|
||||
persistentNotifications[options.id].update(msg,options);
|
||||
return persistentNotifications[options.id];
|
||||
}
|
||||
|
||||
if (options.modal) {
|
||||
$("#full-shade").show();
|
||||
}
|
||||
@@ -108,7 +117,9 @@ RED.notifications = (function() {
|
||||
|
||||
|
||||
$("#notifications").append(n);
|
||||
$(n).slideDown(300);
|
||||
if (!RED.notifications.hide) {
|
||||
$(n).slideDown(300);
|
||||
}
|
||||
n.close = (function() {
|
||||
var nn = n;
|
||||
return function() {
|
||||
@@ -123,9 +134,13 @@ RED.notifications = (function() {
|
||||
notificationButtonWrapper.hide();
|
||||
}
|
||||
}
|
||||
$(nn).slideUp(300, function() {
|
||||
if (!RED.notifications.hide) {
|
||||
$(nn).slideUp(300, function() {
|
||||
nn.parentNode.removeChild(nn);
|
||||
});
|
||||
} else {
|
||||
nn.parentNode.removeChild(nn);
|
||||
});
|
||||
}
|
||||
if (options.modal) {
|
||||
$("#full-shade").hide();
|
||||
}
|
||||
@@ -138,7 +153,9 @@ RED.notifications = (function() {
|
||||
return
|
||||
}
|
||||
nn.hidden = true;
|
||||
$(nn).slideUp(300);
|
||||
if (!RED.notifications.hide) {
|
||||
$(nn).slideUp(300);
|
||||
}
|
||||
}
|
||||
})();
|
||||
n.showNotification = (function() {
|
||||
@@ -148,7 +165,9 @@ RED.notifications = (function() {
|
||||
return
|
||||
}
|
||||
nn.hidden = false;
|
||||
$(nn).slideDown(300);
|
||||
if (!RED.notifications.hide) {
|
||||
$(nn).slideDown(300);
|
||||
}
|
||||
}
|
||||
})();
|
||||
|
||||
@@ -167,7 +186,9 @@ RED.notifications = (function() {
|
||||
if (typeof options === 'number') {
|
||||
timeout = options;
|
||||
} else if (options !== undefined) {
|
||||
timeout = options.timeout;
|
||||
if (!options.fixed) {
|
||||
timeout = options.timeout || 5000;
|
||||
}
|
||||
if (options.buttons) {
|
||||
var buttonSet = $('<div style="margin-top: 20px;" class="ui-dialog-buttonset"></div>').appendTo(nn)
|
||||
options.buttons.forEach(function(buttonDef) {
|
||||
@@ -189,6 +210,11 @@ RED.notifications = (function() {
|
||||
}
|
||||
if (nn.hidden) {
|
||||
nn.showNotification();
|
||||
} else if (!options || !options.silent){
|
||||
$(nn).addClass("notification-shake-horizontal");
|
||||
setTimeout(function() {
|
||||
$(nn).removeClass("notification-shake-horizontal");
|
||||
},300);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -207,7 +233,9 @@ RED.notifications = (function() {
|
||||
currentNotifications.push(n);
|
||||
if (options.id) {
|
||||
persistentNotifications[options.id] = n;
|
||||
notificationButtonWrapper.show();
|
||||
if (options.fixed) {
|
||||
notificationButtonWrapper.show();
|
||||
}
|
||||
}
|
||||
c+=1;
|
||||
return n;
|
||||
|
@@ -289,7 +289,7 @@ RED.palette.editor = (function() {
|
||||
}
|
||||
if (moduleInfo.pending_version) {
|
||||
nodeEntry.versionSpan.html(moduleInfo.version+' <i class="fa fa-long-arrow-right"></i> '+moduleInfo.pending_version).appendTo(nodeEntry.metaRow)
|
||||
nodeEntry.updateButton.text(RED._('palette.editor.updated')).addClass('disabled').show();
|
||||
nodeEntry.updateButton.text(RED._('palette.editor.updated')).addClass('disabled').css('display', 'inline-block');
|
||||
} else if (loadedIndex.hasOwnProperty(module)) {
|
||||
if (semVerCompare(loadedIndex[module].version,moduleInfo.version) === 1) {
|
||||
nodeEntry.updateButton.show();
|
||||
@@ -321,7 +321,7 @@ RED.palette.editor = (function() {
|
||||
var catalogueLoadStart;
|
||||
var catalogueLoadErrors = false;
|
||||
|
||||
var activeSort = sortModulesAZ;
|
||||
var activeSort = sortModulesRelevance;
|
||||
|
||||
function handleCatalogResponse(err,catalog,index,v) {
|
||||
catalogueLoadStatus.push(err||v);
|
||||
@@ -333,6 +333,9 @@ RED.palette.editor = (function() {
|
||||
if (m.keywords) {
|
||||
m.index = m.index.concat(m.keywords);
|
||||
}
|
||||
if (m.types) {
|
||||
m.index = m.index.concat(m.types);
|
||||
}
|
||||
if (m.updated_at) {
|
||||
m.timestamp = new Date(m.updated_at).getTime();
|
||||
} else {
|
||||
@@ -413,6 +416,17 @@ RED.palette.editor = (function() {
|
||||
packageList.editableList('addItem',{start:10,more:filteredList.length-10})
|
||||
}
|
||||
}
|
||||
function sortModulesRelevance(A,B) {
|
||||
var currentFilter = searchInput.searchBox('value').trim();
|
||||
if (currentFilter === "") {
|
||||
return sortModulesAZ(A,B);
|
||||
}
|
||||
var i = A.info.index.indexOf(currentFilter) - B.info.index.indexOf(currentFilter);
|
||||
if (i === 0) {
|
||||
return sortModulesAZ(A,B);
|
||||
}
|
||||
return i;
|
||||
}
|
||||
function sortModulesAZ(A,B) {
|
||||
return A.info.id.localeCompare(B.info.id);
|
||||
}
|
||||
@@ -747,32 +761,29 @@ RED.palette.editor = (function() {
|
||||
|
||||
$('<span>').text(RED._("palette.editor.sort")+' ').appendTo(toolBar);
|
||||
var sortGroup = $('<span class="button-group"></span>').appendTo(toolBar);
|
||||
var sortAZ = $('<a href="#" class="sidebar-header-button-toggle selected" data-i18n="palette.editor.sortAZ"></a>').appendTo(sortGroup);
|
||||
var sortRecent = $('<a href="#" class="sidebar-header-button-toggle" data-i18n="palette.editor.sortRecent"></a>').appendTo(sortGroup);
|
||||
var sortRelevance = $('<a href="#" class="palette-editor-install-sort-option sidebar-header-button-toggle selected"><i class="fa fa-sort-amount-desc"></i></a>').appendTo(sortGroup);
|
||||
var sortAZ = $('<a href="#" class="palette-editor-install-sort-option sidebar-header-button-toggle" data-i18n="palette.editor.sortAZ"></a>').appendTo(sortGroup);
|
||||
var sortRecent = $('<a href="#" class="palette-editor-install-sort-option sidebar-header-button-toggle" data-i18n="palette.editor.sortRecent"></a>').appendTo(sortGroup);
|
||||
|
||||
sortAZ.click(function(e) {
|
||||
e.preventDefault();
|
||||
if ($(this).hasClass("selected")) {
|
||||
return;
|
||||
}
|
||||
$(this).addClass("selected");
|
||||
sortRecent.removeClass("selected");
|
||||
activeSort = sortModulesAZ;
|
||||
refreshFilteredItems();
|
||||
|
||||
var sortOpts = [
|
||||
{button: sortRelevance, func: sortModulesRelevance},
|
||||
{button: sortAZ, func: sortModulesAZ},
|
||||
{button: sortRecent, func: sortModulesRecent}
|
||||
]
|
||||
sortOpts.forEach(function(opt) {
|
||||
opt.button.click(function(e) {
|
||||
e.preventDefault();
|
||||
if ($(this).hasClass("selected")) {
|
||||
return;
|
||||
}
|
||||
$(".palette-editor-install-sort-option").removeClass("selected");
|
||||
$(this).addClass("selected");
|
||||
activeSort = opt.func;
|
||||
refreshFilteredItems();
|
||||
});
|
||||
});
|
||||
|
||||
sortRecent.click(function(e) {
|
||||
e.preventDefault();
|
||||
if ($(this).hasClass("selected")) {
|
||||
return;
|
||||
}
|
||||
$(this).addClass("selected");
|
||||
sortAZ.removeClass("selected");
|
||||
activeSort = sortModulesRecent;
|
||||
refreshFilteredItems();
|
||||
});
|
||||
|
||||
|
||||
var refreshSpan = $('<span>').appendTo(toolBar);
|
||||
var refreshButton = $('<a href="#" class="sidebar-header-button"><i class="fa fa-refresh"></i></a>').appendTo(refreshSpan);
|
||||
refreshButton.click(function(e) {
|
||||
@@ -814,10 +825,23 @@ RED.palette.editor = (function() {
|
||||
$('<a target="_blank" class="palette-module-link"><i class="fa fa-external-link"></i></a>').attr('href',entry.url).appendTo(titleRow);
|
||||
var descRow = $('<div class="palette-module-meta"></div>').appendTo(headerRow);
|
||||
$('<div>',{class:"palette-module-description"}).text(entry.description).appendTo(descRow);
|
||||
|
||||
var metaRow = $('<div class="palette-module-meta"></div>').appendTo(headerRow);
|
||||
$('<span class="palette-module-version"><i class="fa fa-tag"></i> '+entry.version+'</span>').appendTo(metaRow);
|
||||
$('<span class="palette-module-updated"><i class="fa fa-calendar"></i> '+formatUpdatedAt(entry.updated_at)+'</span>').appendTo(metaRow);
|
||||
|
||||
var duplicateType = false;
|
||||
if (entry.types && entry.types.length > 0) {
|
||||
|
||||
for (var i=0;i<entry.types.length;i++) {
|
||||
var nodeset = RED.nodes.registry.getNodeSetForType(entry.types[i]);
|
||||
if (nodeset) {
|
||||
duplicateType = nodeset.module;
|
||||
break;
|
||||
}
|
||||
}
|
||||
// $('<div>',{class:"palette-module-meta"}).text(entry.types.join(",")).appendTo(headerRow);
|
||||
}
|
||||
|
||||
var buttonRow = $('<div>',{class:"palette-module-meta"}).appendTo(headerRow);
|
||||
var buttonGroup = $('<div>',{class:"palette-module-button-group"}).appendTo(buttonRow);
|
||||
var installButton = $('<a href="#" class="editor-button editor-button-small"></a>').text(RED._('palette.editor.install')).appendTo(buttonGroup);
|
||||
@@ -830,6 +854,16 @@ RED.palette.editor = (function() {
|
||||
if (nodeEntries.hasOwnProperty(entry.id)) {
|
||||
installButton.addClass('disabled');
|
||||
installButton.text(RED._('palette.editor.installed'));
|
||||
} else if (duplicateType) {
|
||||
installButton.addClass('disabled');
|
||||
installButton.text(RED._('palette.editor.conflict'));
|
||||
RED.popover.create({
|
||||
target:installButton,
|
||||
content: RED._('palette.editor.conflictTip',{module:duplicateType}),
|
||||
trigger:"hover",
|
||||
direction:"bottom",
|
||||
delay:{show:750,hide:50}
|
||||
})
|
||||
}
|
||||
|
||||
object.elements = {
|
||||
@@ -863,11 +897,35 @@ RED.palette.editor = (function() {
|
||||
class: "primary palette-module-install-confirm-button-update",
|
||||
click: function() {
|
||||
var spinner = RED.utils.addSpinnerOverlay(container, true);
|
||||
var buttonRow = $('<div style="position: relative;bottom: calc(50% + 17px); padding-right: 10px;text-align: right;"></div>').appendTo(spinner);
|
||||
$('<button class="editor-button"></button>').text(RED._("eventLog.view")).appendTo(buttonRow).click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
});
|
||||
RED.eventLog.startEvent(RED._("palette.editor.confirm.button.install")+" : "+entry.name+" "+version);
|
||||
installNodeModule(entry.name,version,function(xhr) {
|
||||
spinner.remove();
|
||||
if (xhr) {
|
||||
if (xhr.responseJSON) {
|
||||
RED.notify(RED._('palette.editor.errors.updateFailed',{module: entry.name,message:xhr.responseJSON.message}));
|
||||
var notification = RED.notify(RED._('palette.editor.errors.updateFailed',{module: entry.name,message:xhr.responseJSON.message}),{
|
||||
type: 'error',
|
||||
modal: true,
|
||||
fixed: true,
|
||||
buttons: [
|
||||
{
|
||||
text: RED._("common.label.close"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
}
|
||||
},{
|
||||
text: RED._("eventLog.view"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
}
|
||||
}
|
||||
]
|
||||
});
|
||||
}
|
||||
}
|
||||
done(xhr);
|
||||
@@ -898,12 +956,35 @@ RED.palette.editor = (function() {
|
||||
class: "primary palette-module-install-confirm-button-remove",
|
||||
click: function() {
|
||||
var spinner = RED.utils.addSpinnerOverlay(container, true);
|
||||
var buttonRow = $('<div style="position: relative;bottom: calc(50% + 17px); padding-right: 10px;text-align: right;"></div>').appendTo(spinner);
|
||||
$('<button class="editor-button"></button>').text(RED._("eventLog.view")).appendTo(buttonRow).click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
});
|
||||
RED.eventLog.startEvent(RED._("palette.editor.confirm.button.remove")+" : "+entry.name);
|
||||
removeNodeModule(entry.name, function(xhr) {
|
||||
spinner.remove();
|
||||
if (xhr) {
|
||||
if (xhr.responseJSON) {
|
||||
RED.notify(RED._('palette.editor.errors.removeFailed',{module: entry.name,message:xhr.responseJSON.message}));
|
||||
}
|
||||
var notification = RED.notify(RED._('palette.editor.errors.removeFailed',{module: entry.name,message:xhr.responseJSON.message}),{
|
||||
type: 'error',
|
||||
modal: true,
|
||||
fixed: true,
|
||||
buttons: [
|
||||
{
|
||||
text: RED._("common.label.close"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
}
|
||||
},{
|
||||
text: RED._("eventLog.view"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
}
|
||||
}
|
||||
]
|
||||
}); }
|
||||
}
|
||||
})
|
||||
notification.close();
|
||||
@@ -940,11 +1021,36 @@ RED.palette.editor = (function() {
|
||||
class: "primary palette-module-install-confirm-button-install",
|
||||
click: function() {
|
||||
var spinner = RED.utils.addSpinnerOverlay(container, true);
|
||||
|
||||
var buttonRow = $('<div style="position: relative;bottom: calc(50% + 17px); padding-right: 10px;text-align: right;"></div>').appendTo(spinner);
|
||||
$('<button class="editor-button"></button>').text(RED._("eventLog.view")).appendTo(buttonRow).click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
});
|
||||
RED.eventLog.startEvent(RED._("palette.editor.confirm.button.install")+" : "+entry.id+" "+entry.version);
|
||||
installNodeModule(entry.id,entry.version,function(xhr) {
|
||||
spinner.remove();
|
||||
if (xhr) {
|
||||
if (xhr.responseJSON) {
|
||||
RED.notify(RED._('palette.editor.errors.installFailed',{module: entry.id,message:xhr.responseJSON.message}));
|
||||
var notification = RED.notify(RED._('palette.editor.errors.installFailed',{module: entry.id,message:xhr.responseJSON.message}),{
|
||||
type: 'error',
|
||||
modal: true,
|
||||
fixed: true,
|
||||
buttons: [
|
||||
{
|
||||
text: RED._("common.label.close"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
}
|
||||
},{
|
||||
text: RED._("eventLog.view"),
|
||||
click: function() {
|
||||
notification.close();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
}
|
||||
}
|
||||
]
|
||||
});
|
||||
}
|
||||
}
|
||||
done(xhr);
|
||||
|
@@ -20,7 +20,7 @@ RED.palette = (function() {
|
||||
var coreCategories = ['subflows', 'input', 'output', 'function', 'social', 'mobile', 'storage', 'analysis', 'advanced'];
|
||||
|
||||
var categoryContainers = {};
|
||||
|
||||
var sidebarControls;
|
||||
|
||||
function createCategory(originalCategory,rootCategory,category,ns) {
|
||||
if ($("#palette-base-category-"+rootCategory).length === 0) {
|
||||
@@ -110,13 +110,26 @@ RED.palette = (function() {
|
||||
var popOverContent;
|
||||
try {
|
||||
var l = "<p><b>"+RED.text.bidi.enforceTextDirectionWithUCC(label)+"</b></p>";
|
||||
if (label != type) {
|
||||
l = "<p><b>"+RED.text.bidi.enforceTextDirectionWithUCC(label)+"</b><br/><i>"+type+"</i></p>";
|
||||
}
|
||||
popOverContent = $(l+(info?info:$("script[data-help-name='"+type+"']").html()||"<p>"+RED._("palette.noInfo")+"</p>").trim())
|
||||
popOverContent = $('<div></div>').append($(l+(info?info:$("script[data-help-name='"+type+"']").html()||"<p>"+RED._("palette.noInfo")+"</p>").trim())
|
||||
.filter(function(n) {
|
||||
return (this.nodeType == 1 && this.nodeName == "P") || (this.nodeType == 3 && this.textContent.trim().length > 0)
|
||||
}).slice(0,2);
|
||||
}).slice(0,2));
|
||||
popOverContent.find("a").each(function(){
|
||||
var linkText = $(this).text();
|
||||
$(this).before(linkText);
|
||||
$(this).remove();
|
||||
});
|
||||
|
||||
var typeInfo = RED.nodes.getType(type);
|
||||
|
||||
if (typeInfo) {
|
||||
var metaData = "";
|
||||
if (typeInfo && !/^subflow:/.test(type)) {
|
||||
metaData = typeInfo.set.module+" : ";
|
||||
}
|
||||
metaData += type;
|
||||
$('<p>',{style:"font-size: 0.8em"}).text(metaData).appendTo(popOverContent);
|
||||
}
|
||||
} catch(err) {
|
||||
// Malformed HTML may cause errors. TODO: need to understand what can break
|
||||
// NON-NLS: internal debug
|
||||
@@ -129,9 +142,9 @@ RED.palette = (function() {
|
||||
}
|
||||
|
||||
function setIcon(element,sf) {
|
||||
var iconElement = element.find(".palette_icon");
|
||||
var icon_url = RED.utils.getNodeIcon(sf._def,sf);
|
||||
iconElement.attr("style", "background-image: url("+icon_url+")");
|
||||
var icon_url = RED.utils.getNodeIcon(sf._def);
|
||||
var iconContainer = element.find(".palette_icon_container");
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
}
|
||||
|
||||
function escapeNodeType(nt) {
|
||||
@@ -169,7 +182,7 @@ RED.palette = (function() {
|
||||
if (def.icon) {
|
||||
var icon_url = RED.utils.getNodeIcon(def);
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"+(def.align=="right"?" palette_icon_container_right":"")}).appendTo(d);
|
||||
$('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
}
|
||||
|
||||
d.style.backgroundColor = RED.utils.getNodeColor(nt,def);
|
||||
@@ -275,7 +288,8 @@ RED.palette = (function() {
|
||||
}
|
||||
|
||||
for (var i=0;i<nodes.length;i++) {
|
||||
if (d3.select(nodes[i]).classed('link_background')) {
|
||||
var node = d3.select(nodes[i]);
|
||||
if (node.classed('link_background') && !node.classed('link_link')) {
|
||||
var length = nodes[i].getTotalLength();
|
||||
for (var j=0;j<length;j+=10) {
|
||||
var p = nodes[i].getPointAtLength(j);
|
||||
@@ -320,9 +334,9 @@ RED.palette = (function() {
|
||||
}
|
||||
setLabel(nt,$(d),label,nodeInfo);
|
||||
|
||||
var categoryNode = $("#palette-container-"+category);
|
||||
var categoryNode = $("#palette-container-"+rootCategory);
|
||||
if (categoryNode.find(".palette_node").length === 1) {
|
||||
categoryContainers[category].open();
|
||||
categoryContainers[rootCategory].open();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -488,6 +502,22 @@ RED.palette = (function() {
|
||||
}
|
||||
})
|
||||
|
||||
sidebarControls = $('<div class="sidebar-control-left"><i class="fa fa-chevron-left"</div>').appendTo($("#palette"));
|
||||
RED.popover.tooltip(sidebarControls,RED._("keyboard.togglePalette"),"core:toggle-palette");
|
||||
|
||||
sidebarControls.click(function() {
|
||||
RED.menu.toggleSelected("menu-item-palette");
|
||||
})
|
||||
$("#palette").on("mouseenter", function() {
|
||||
sidebarControls.toggle("slide", { direction: "left" }, 200);
|
||||
})
|
||||
$("#palette").on("mouseleave", function() {
|
||||
sidebarControls.hide();
|
||||
})
|
||||
|
||||
|
||||
|
||||
|
||||
var categoryList = coreCategories;
|
||||
if (RED.settings.paletteCategories) {
|
||||
categoryList = RED.settings.paletteCategories;
|
||||
@@ -509,6 +539,8 @@ RED.palette = (function() {
|
||||
}
|
||||
}
|
||||
});
|
||||
RED.popover.tooltip($("#palette-collapse-all"),RED._('palette.actions.collapse-all'));
|
||||
|
||||
$("#palette-expand-all").on("click", function(e) {
|
||||
e.preventDefault();
|
||||
for (var cat in categoryContainers) {
|
||||
@@ -517,7 +549,29 @@ RED.palette = (function() {
|
||||
}
|
||||
}
|
||||
});
|
||||
RED.popover.tooltip($("#palette-expand-all"),RED._('palette.actions.expand-all'));
|
||||
|
||||
RED.actions.add("core:toggle-palette", function(state) {
|
||||
if (state === undefined) {
|
||||
RED.menu.toggleSelected("menu-item-palette");
|
||||
} else {
|
||||
togglePalette(state);
|
||||
}
|
||||
});
|
||||
}
|
||||
function togglePalette(state) {
|
||||
if (!state) {
|
||||
$("#main-container").addClass("palette-closed");
|
||||
sidebarControls.hide();
|
||||
sidebarControls.find("i").addClass("fa-chevron-right").removeClass("fa-chevron-left");
|
||||
} else {
|
||||
$("#main-container").removeClass("palette-closed");
|
||||
sidebarControls.find("i").removeClass("fa-chevron-right").addClass("fa-chevron-left");
|
||||
}
|
||||
setTimeout(function() { $(window).resize(); } ,200);
|
||||
}
|
||||
|
||||
|
||||
function getCategories() {
|
||||
var categories = [];
|
||||
$("#palette-container .palette-category").each(function(i,d) {
|
||||
|
@@ -49,7 +49,7 @@ RED.projects.settings = (function() {
|
||||
var tabContainer;
|
||||
|
||||
var trayOptions = {
|
||||
title: RED._("menu.label.userSettings"),
|
||||
title: RED._("sidebar.project.projectSettings.title"),
|
||||
buttons: [
|
||||
{
|
||||
id: "node-dialog-ok",
|
||||
@@ -461,7 +461,11 @@ RED.projects.settings = (function() {
|
||||
setTimeout(function() {
|
||||
depsList.editableList('removeItem',entry);
|
||||
refreshModuleInUseCounts();
|
||||
entry.count = modulesInUse[entry.id].count;
|
||||
if (modulesInUse.hasOwnProperty(entry.id)) {
|
||||
entry.count = modulesInUse[entry.id].count;
|
||||
} else {
|
||||
entry.count = 0;
|
||||
}
|
||||
depsList.editableList('addItem',entry);
|
||||
},500);
|
||||
}
|
||||
|
@@ -21,7 +21,7 @@ RED.projects = (function() {
|
||||
var activeProject;
|
||||
function reportUnexpectedError(error) {
|
||||
var notification;
|
||||
if (error.error === 'git_missing_user') {
|
||||
if (error.code === 'git_missing_user') {
|
||||
notification = RED.notify("<p>"+RED._("projects.errors.no-username-email")+"</p>",{
|
||||
fixed: true,
|
||||
type:'error',
|
||||
@@ -43,7 +43,7 @@ RED.projects = (function() {
|
||||
})
|
||||
} else {
|
||||
console.log(error);
|
||||
notification = RED.notify("<p>"+RED._("projects.errors.unexpected")+":</p><p>"+error.message+"</p><small>"+RED._("projects.errors.code")+": "+error.error+"</small>",{
|
||||
notification = RED.notify("<p>"+RED._("projects.errors.unexpected")+":</p><p>"+error.message+"</p><small>"+RED._("projects.errors.code")+": "+error.code+"</small>",{
|
||||
fixed: true,
|
||||
modal: true,
|
||||
type: 'error',
|
||||
@@ -103,6 +103,18 @@ RED.projects = (function() {
|
||||
return container;
|
||||
},
|
||||
buttons: [
|
||||
{
|
||||
// id: "clipboard-dialog-cancel",
|
||||
text: "Open existing project", //RED._("projects.welcome.not-right-now"),
|
||||
class: "secondary",
|
||||
click: function() {
|
||||
createProjectOptions = {
|
||||
action: "open"
|
||||
}
|
||||
show('git-config');
|
||||
}
|
||||
},
|
||||
|
||||
{
|
||||
// id: "clipboard-dialog-cancel",
|
||||
text: RED._("projects.welcome.not-right-now"),
|
||||
@@ -187,6 +199,8 @@ RED.projects = (function() {
|
||||
show('project-details');
|
||||
} else if (createProjectOptions.action === "clone") {
|
||||
show('clone-project');
|
||||
} else if (createProjectOptions.action === "open") {
|
||||
show('create',{screen:'open'})
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -532,7 +546,7 @@ RED.projects = (function() {
|
||||
subrow = $('<div style="text-align: center">').appendTo(sshwarningRow);
|
||||
$('<button class="editor-button">'+RED._("projects.clone-project.ssh-key-add")+'</button>').appendTo(subrow).click(function(e) {
|
||||
e.preventDefault();
|
||||
$('#projects-dialog-cancel').click();
|
||||
dialog.dialog( "close" );
|
||||
RED.userSettings.show('gitconfig');
|
||||
setTimeout(function() {
|
||||
$("#user-settings-gitconfig-add-key").click();
|
||||
@@ -1493,7 +1507,7 @@ RED.projects = (function() {
|
||||
return switchProject(selectedProject.name,function(err,data) {
|
||||
dialog.dialog( "close" );
|
||||
if (err) {
|
||||
if (err.error !== 'credentials_load_failed') {
|
||||
if (err.code !== 'credentials_load_failed') {
|
||||
console.log(RED._("projects.create.unexpected_error"),err)
|
||||
}
|
||||
}
|
||||
@@ -1587,7 +1601,6 @@ RED.projects = (function() {
|
||||
sendRequest({
|
||||
url: "projects/"+name,
|
||||
type: "PUT",
|
||||
requireCleanWorkspace: true,
|
||||
responses: {
|
||||
200: function(data) {
|
||||
done(null,data);
|
||||
@@ -1879,7 +1892,6 @@ RED.projects = (function() {
|
||||
function sendRequest(options,body) {
|
||||
// dialogBody.hide();
|
||||
// console.log(options.url,body);
|
||||
|
||||
if (options.requireCleanWorkspace && RED.nodes.dirty()) {
|
||||
var thenCallback;
|
||||
var alwaysCallback;
|
||||
@@ -1938,7 +1950,7 @@ RED.projects = (function() {
|
||||
resultCallback = responses;
|
||||
resultCallbackArgs = {error:responses.statusText};
|
||||
return;
|
||||
} else if (options.handleAuthFail !== false && xhr.responseJSON.error === 'git_auth_failed') {
|
||||
} else if (options.handleAuthFail !== false && xhr.responseJSON.code === 'git_auth_failed') {
|
||||
var url = activeProject.git.remotes[xhr.responseJSON.remote||options.remote||'origin'].fetch;
|
||||
|
||||
var message = $('<div>'+
|
||||
@@ -2026,8 +2038,8 @@ RED.projects = (function() {
|
||||
]
|
||||
});
|
||||
return;
|
||||
} else if (responses[xhr.responseJSON.error]) {
|
||||
resultCallback = responses[xhr.responseJSON.error];
|
||||
} else if (responses[xhr.responseJSON.code]) {
|
||||
resultCallback = responses[xhr.responseJSON.code];
|
||||
resultCallbackArgs = xhr.responseJSON;
|
||||
return;
|
||||
} else if (responses['*']) {
|
||||
@@ -2036,10 +2048,12 @@ RED.projects = (function() {
|
||||
return;
|
||||
}
|
||||
}
|
||||
console.log(responses)
|
||||
console.log(RED._("projects.send-req.unhandled")+":");
|
||||
console.log(xhr);
|
||||
console.log(textStatus);
|
||||
console.log(err);
|
||||
console.log(stack);
|
||||
}).always(function() {
|
||||
var delta = Date.now() - start;
|
||||
delta = Math.max(0,500-delta);
|
||||
@@ -2344,7 +2358,15 @@ RED.projects = (function() {
|
||||
RED.notify(RED._("user.errors.notAuthorized"),"error");
|
||||
return;
|
||||
}
|
||||
show('create',{screen:'open'})
|
||||
if (RED.nodes.dirty()) {
|
||||
return requireCleanWorkspace(function(cancelled) {
|
||||
if (!cancelled) {
|
||||
show('create',{screen:'open'})
|
||||
}
|
||||
})
|
||||
} else {
|
||||
show('create',{screen:'open'})
|
||||
}
|
||||
},
|
||||
showCredentialsPrompt: function() { //TODO: rename this function
|
||||
if (!RED.user.hasPermission("projects.write")) {
|
||||
|
@@ -200,12 +200,12 @@ RED.sidebar.versionControl = (function() {
|
||||
|
||||
]
|
||||
})
|
||||
|
||||
});
|
||||
RED.popover.tooltip(revertButton,RED._("sidebar.project.versionControl.revertChanges"));
|
||||
}
|
||||
bg = $('<span class="button-group"></span>').appendTo(entryTools);
|
||||
if (state !== 'unmerged') {
|
||||
$('<button class="editor-button editor-button-small"><i class="fa fa-'+((state==='unstaged')?"plus":"minus")+'"></i></button>')
|
||||
var stageButton = $('<button class="editor-button editor-button-small"><i class="fa fa-'+((state==='unstaged')?"plus":"minus")+'"></i></button>')
|
||||
.appendTo(bg)
|
||||
.click(function(evt) {
|
||||
evt.preventDefault();
|
||||
@@ -231,6 +231,7 @@ RED.sidebar.versionControl = (function() {
|
||||
}
|
||||
},{});
|
||||
});
|
||||
RED.popover.tooltip(stageButton,RED._("sidebar.project.versionControl."+((state==='unstaged')?"stage":"unstage")+"Change"));
|
||||
}
|
||||
entry["update"+((state==='unstaged')?"Unstaged":"Staged")] = function(entry,status) {
|
||||
container.removeClass();
|
||||
@@ -321,12 +322,14 @@ RED.sidebar.versionControl = (function() {
|
||||
localChanges.content.css({height:"100%"});
|
||||
|
||||
var bg = $('<div style="float: right"></div>').appendTo(localChanges.header);
|
||||
$('<button class="editor-button editor-button-small"><i class="fa fa-refresh"></i></button>')
|
||||
var refreshButton = $('<button class="editor-button editor-button-small"><i class="fa fa-refresh"></i></button>')
|
||||
.appendTo(bg)
|
||||
.click(function(evt) {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
refresh(true);
|
||||
})
|
||||
});
|
||||
RED.popover.tooltip(refreshButton,RED._("sidebar.project.versionControl.refreshChanges"));
|
||||
|
||||
emptyStagedItem = { label: RED._("sidebar.project.versionControl.none") };
|
||||
emptyMergedItem = { label: RED._("sidebar.project.versionControl.conflictResolve") };
|
||||
@@ -343,6 +346,7 @@ RED.sidebar.versionControl = (function() {
|
||||
});
|
||||
updateBulk(toStage,true);
|
||||
});
|
||||
RED.popover.tooltip(stageAllButton,RED._("sidebar.project.versionControl.stageAllChange"));
|
||||
unstagedChangesList = $("<ol>",{style:"position: absolute; top: 30px; bottom: 0; right:0; left:0;"}).appendTo(unstagedContent);
|
||||
unstagedChangesList.editableList({
|
||||
addButton: false,
|
||||
@@ -432,7 +436,7 @@ RED.sidebar.versionControl = (function() {
|
||||
bg = $('<div style="float: right"></div>').appendTo(header);
|
||||
var showCommitBox = function() {
|
||||
commitMessage.val("");
|
||||
submitCommitButton.attr("disabled",true);
|
||||
submitCommitButton.prop("disabled",true);
|
||||
unstagedContent.css("height","30px");
|
||||
if (unmergedContent.is(":visible")) {
|
||||
unmergedContent.css("height","30px");
|
||||
@@ -444,10 +448,10 @@ RED.sidebar.versionControl = (function() {
|
||||
setTimeout(function() {
|
||||
commitBox.css("height","175px");
|
||||
},10);
|
||||
stageAllButton.attr("disabled",true);
|
||||
unstageAllButton.attr("disabled",true);
|
||||
commitButton.attr("disabled",true);
|
||||
abortMergeButton.attr("disabled",true);
|
||||
stageAllButton.prop("disabled",true);
|
||||
unstageAllButton.prop("disabled",true);
|
||||
commitButton.prop("disabled",true);
|
||||
abortMergeButton.prop("disabled",true);
|
||||
commitMessage.focus();
|
||||
}
|
||||
commitButton = $('<button class="editor-button editor-button-small" style="margin-right: 5px;">'+RED._("sidebar.project.versionControl.commit")+'</button>')
|
||||
@@ -457,6 +461,7 @@ RED.sidebar.versionControl = (function() {
|
||||
evt.stopPropagation();
|
||||
showCommitBox();
|
||||
});
|
||||
RED.popover.tooltip(commitButton,RED._("sidebar.project.versionControl.commitChanges"));
|
||||
unstageAllButton = $('<button class="editor-button editor-button-small"><i class="fa fa-minus"></i> '+RED._("sidebar.project.versionControl.all")+'</button>')
|
||||
.appendTo(bg)
|
||||
.click(function(evt) {
|
||||
@@ -468,6 +473,7 @@ RED.sidebar.versionControl = (function() {
|
||||
updateBulk(toUnstage,false);
|
||||
|
||||
});
|
||||
RED.popover.tooltip(unstageAllButton,RED._("sidebar.project.versionControl.unstageAllChange"));
|
||||
|
||||
|
||||
stagedChangesList = $("<ol>",{style:"position: absolute; top: 30px; bottom: 0; right:0; left:0;"}).appendTo(stagedContent);
|
||||
@@ -487,7 +493,7 @@ RED.sidebar.versionControl = (function() {
|
||||
var commitMessage = $('<textarea placeholder='+RED._("sidebar.project.versionControl.commitPlaceholder")+'></textarea>')
|
||||
.appendTo(commitBox)
|
||||
.on("change keyup paste",function() {
|
||||
submitCommitButton.attr('disabled',$(this).val().trim()==="");
|
||||
submitCommitButton.prop('disabled',$(this).val().trim()==="");
|
||||
});
|
||||
var commitToolbar = $('<div class="sidebar-version-control-slide-box-toolbar button-group">').appendTo(commitBox);
|
||||
|
||||
@@ -503,10 +509,10 @@ RED.sidebar.versionControl = (function() {
|
||||
setTimeout(function() {
|
||||
commitBox.hide();
|
||||
},200);
|
||||
stageAllButton.attr("disabled",false);
|
||||
unstageAllButton.attr("disabled",false);
|
||||
commitButton.attr("disabled",false);
|
||||
abortMergeButton.attr("disabled",false);
|
||||
stageAllButton.prop("disabled",false);
|
||||
unstageAllButton.prop("disabled",false);
|
||||
commitButton.prop("disabled",false);
|
||||
abortMergeButton.prop("disabled",false);
|
||||
|
||||
})
|
||||
var submitCommitButton = $('<button class="editor-button">'+RED._("sidebar.project.versionControl.commitCapital")+'</button>')
|
||||
@@ -549,13 +555,15 @@ RED.sidebar.versionControl = (function() {
|
||||
collapsible: true
|
||||
});
|
||||
|
||||
var bg = $('<div style="float: right"></div>').appendTo(localHistory.header);
|
||||
$('<button class="editor-button editor-button-small"><i class="fa fa-refresh"></i></button>')
|
||||
bg = $('<div style="float: right"></div>').appendTo(localHistory.header);
|
||||
refreshButton = $('<button class="editor-button editor-button-small"><i class="fa fa-refresh"></i></button>')
|
||||
.appendTo(bg)
|
||||
.click(function(evt) {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
refresh(true,true);
|
||||
})
|
||||
RED.popover.tooltip(refreshButton,RED._("sidebar.project.versionControl.refreshCommitHistory"))
|
||||
|
||||
var localBranchToolbar = $('<div class="sidebar-version-control-change-header" style="text-align: right;"></div>').appendTo(localHistory.content);
|
||||
|
||||
@@ -578,6 +586,7 @@ RED.sidebar.versionControl = (function() {
|
||||
},100);
|
||||
}
|
||||
})
|
||||
RED.popover.tooltip(localBranchButton,RED._("sidebar.project.versionControl.changeLocalBranch"))
|
||||
var repoStatusButton = $('<button class="editor-button editor-button-small" style="margin-left: 10px;" id="sidebar-version-control-repo-status-button">'+
|
||||
'<span id="sidebar-version-control-repo-status-stats">'+
|
||||
'<i class="fa fa-long-arrow-up"></i> <span id="sidebar-version-control-commits-ahead"></span> '+
|
||||
@@ -606,6 +615,7 @@ RED.sidebar.versionControl = (function() {
|
||||
|
||||
}
|
||||
});
|
||||
RED.popover.tooltip(repoStatusButton,RED._("sidebar.project.versionControl.manageRemoteBranch"))
|
||||
|
||||
localCommitList = $("<ol>",{style:"position: absolute; top: 30px; bottom: 0px; right:0; left:0;"}).appendTo(localHistory.content);
|
||||
localCommitListShade = $('<div class="component-shade" style="z-Index: 3"></div>').css('top',"30px").hide().appendTo(localHistory.content);
|
||||
@@ -855,8 +865,8 @@ RED.sidebar.versionControl = (function() {
|
||||
} else {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.selectUpstreamBranch"));
|
||||
}
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',false);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',false);
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -870,7 +880,13 @@ RED.sidebar.versionControl = (function() {
|
||||
.click(function(e) {
|
||||
e.preventDefault();
|
||||
var spinner = utils.addSpinnerOverlay(remoteBox).addClass("projects-dialog-spinner-contain");
|
||||
var buttonRow = $('<div style="position: relative; bottom: 60px;"></div>').appendTo(spinner);
|
||||
$('<button class="editor-button"></button>').text(RED._("eventLog.view")).appendTo(buttonRow).click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
});
|
||||
var activeProject = RED.projects.getActiveProject();
|
||||
RED.eventLog.startEvent("Push changes"+(activeProject.git.branches.remoteAlt?(" : "+activeProject.git.branches.remoteAlt):""));
|
||||
var url = "projects/"+activeProject.name+"/push";
|
||||
if (activeProject.git.branches.remoteAlt) {
|
||||
url+="/"+activeProject.git.branches.remoteAlt;
|
||||
@@ -914,7 +930,13 @@ RED.sidebar.versionControl = (function() {
|
||||
var pullRemote = function(options) {
|
||||
options = options || {};
|
||||
var spinner = utils.addSpinnerOverlay(remoteBox).addClass("projects-dialog-spinner-contain");
|
||||
var buttonRow = $('<div style="position: relative; bottom: 60px;"></div>').appendTo(spinner);
|
||||
$('<button class="editor-button"></button>').text(RED._("eventLog.view")).appendTo(buttonRow).click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.actions.invoke("core:show-event-log");
|
||||
});
|
||||
var activeProject = RED.projects.getActiveProject();
|
||||
RED.eventLog.startEvent("Pull changes"+(activeProject.git.branches.remoteAlt?(" : "+activeProject.git.branches.remoteAlt):""));
|
||||
var url = "projects/"+activeProject.name+"/pull";
|
||||
if (activeProject.git.branches.remoteAlt) {
|
||||
url+="/"+activeProject.git.branches.remoteAlt;
|
||||
@@ -1009,6 +1031,7 @@ RED.sidebar.versionControl = (function() {
|
||||
enableOnEdit: false,
|
||||
pinned: true,
|
||||
iconClass: "fa fa-code-fork",
|
||||
action: "core:show-version-control-tab",
|
||||
onchange: function() {
|
||||
setTimeout(function() {
|
||||
sections.resize();
|
||||
@@ -1234,9 +1257,9 @@ RED.sidebar.versionControl = (function() {
|
||||
var unstagedCount = unstagedChangesList.editableList('length');
|
||||
var unmergedCount = unmergedChangesList.editableList('length');
|
||||
|
||||
commitButton.attr('disabled',(isMerging && unmergedCount > 0)||(!isMerging && stagedCount === 0));
|
||||
stageAllButton.attr('disabled',unstagedCount === 0);
|
||||
unstageAllButton.attr('disabled',stagedCount === 0);
|
||||
commitButton.prop('disabled',(isMerging && unmergedCount > 0)||(!isMerging && stagedCount === 0));
|
||||
stageAllButton.prop('disabled',unstagedCount === 0);
|
||||
unstageAllButton.prop('disabled',stagedCount === 0);
|
||||
|
||||
if (stagedCount === 0) {
|
||||
stagedChangesList.editableList('addItem',emptyStagedItem);
|
||||
@@ -1286,9 +1309,9 @@ RED.sidebar.versionControl = (function() {
|
||||
if (result.branches.hasOwnProperty("remoteError") && result.branches.remoteError.code !== 'git_remote_gone') {
|
||||
$("#sidebar-version-control-repo-status-auth-issue").show();
|
||||
$("#sidebar-version-control-repo-status-stats").hide();
|
||||
$('#sidebar-version-control-repo-branch').attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$('#sidebar-version-control-repo-branch').prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
$('#sidebar-version-control-repo-toolbar-message').hide();
|
||||
$('#sidebar-version-control-repo-toolbar-error-message').show();
|
||||
} else {
|
||||
@@ -1298,7 +1321,7 @@ RED.sidebar.versionControl = (function() {
|
||||
$("#sidebar-version-control-repo-status-auth-issue").hide();
|
||||
$("#sidebar-version-control-repo-status-stats").show();
|
||||
|
||||
$('#sidebar-version-control-repo-branch').attr('disabled',false);
|
||||
$('#sidebar-version-control-repo-branch').prop('disabled',false);
|
||||
|
||||
$("#sidebar-version-control-repo-status-button").show();
|
||||
if (result.branches.hasOwnProperty('remote')) {
|
||||
@@ -1308,8 +1331,8 @@ RED.sidebar.versionControl = (function() {
|
||||
$('#sidebar-version-control-commits-behind').text("");
|
||||
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.notTracking"));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@@ -1334,27 +1357,27 @@ RED.sidebar.versionControl = (function() {
|
||||
$('#sidebar-version-control-commits-behind').text(commitsBehind);
|
||||
if (isMerging) {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.statusUnmergedChanged"));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
} else if (commitsAhead > 0 && commitsBehind === 0) {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.commitsAhead", {count:commitsAhead}));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',false);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',false);
|
||||
} else if (commitsAhead === 0 && commitsBehind > 0) {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.commitsBehind",{ count: commitsBehind }));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',false);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',false);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
} else if (commitsAhead > 0 && commitsBehind > 0) {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(
|
||||
RED._("sidebar.project.versionControl.commitsAheadAndBehind1",{ count:commitsBehind })+
|
||||
RED._("sidebar.project.versionControl.commitsAheadAndBehind2",{ count:commitsAhead })+
|
||||
RED._("sidebar.project.versionControl.commitsAheadAndBehind3",{ count:commitsBehind }));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',false);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',false);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
} else if (commitsAhead === 0 && commitsBehind === 0) {
|
||||
$('#sidebar-version-control-repo-toolbar-message').text(RED._("sidebar.project.versionControl.repositoryUpToDate"));
|
||||
$("#sidebar-version-control-repo-pull").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").attr('disabled',true);
|
||||
$("#sidebar-version-control-repo-pull").prop('disabled',true);
|
||||
$("#sidebar-version-control-repo-push").prop('disabled',true);
|
||||
}
|
||||
}
|
||||
function show() {
|
||||
|
@@ -203,7 +203,7 @@ RED.search = (function() {
|
||||
nodeDiv.css('backgroundColor',colour);
|
||||
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"}).appendTo(nodeDiv);
|
||||
$('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, true);
|
||||
|
||||
var contentDiv = $('<div>',{class:"red-ui-search-result-description"}).appendTo(div);
|
||||
if (node.z) {
|
||||
|
@@ -105,6 +105,8 @@ RED.sidebar = (function() {
|
||||
}
|
||||
|
||||
var sidebarSeparator = {};
|
||||
sidebarSeparator.dragging = false;
|
||||
|
||||
$("#sidebar-separator").draggable({
|
||||
axis: "x",
|
||||
start:function(event,ui) {
|
||||
@@ -114,6 +116,7 @@ RED.sidebar = (function() {
|
||||
sidebarSeparator.start = ui.position.left;
|
||||
sidebarSeparator.chartWidth = $("#workspace").width();
|
||||
sidebarSeparator.chartRight = winWidth-$("#workspace").width()-$("#workspace").offset().left-2;
|
||||
sidebarSeparator.dragging = true;
|
||||
|
||||
if (!RED.menu.isSelected("menu-item-sidebar")) {
|
||||
sidebarSeparator.opening = true;
|
||||
@@ -166,6 +169,7 @@ RED.sidebar = (function() {
|
||||
RED.events.emit("sidebar:resize");
|
||||
},
|
||||
stop:function(event,ui) {
|
||||
sidebarSeparator.dragging = false;
|
||||
if (sidebarSeparator.closing) {
|
||||
$("#sidebar").removeClass("closing");
|
||||
RED.menu.setSelected("menu-item-sidebar",false);
|
||||
@@ -181,6 +185,27 @@ RED.sidebar = (function() {
|
||||
}
|
||||
});
|
||||
|
||||
var sidebarControls = $('<div class="sidebar-control-right"><i class="fa fa-chevron-right"</div>').appendTo($("#sidebar-separator"));
|
||||
sidebarControls.click(function() {
|
||||
sidebarControls.hide();
|
||||
RED.menu.toggleSelected("menu-item-sidebar");
|
||||
})
|
||||
$("#sidebar-separator").on("mouseenter", function() {
|
||||
if (!sidebarSeparator.dragging) {
|
||||
if (RED.menu.isSelected("menu-item-sidebar")) {
|
||||
sidebarControls.find("i").addClass("fa-chevron-right").removeClass("fa-chevron-left");
|
||||
} else {
|
||||
sidebarControls.find("i").removeClass("fa-chevron-right").addClass("fa-chevron-left");
|
||||
}
|
||||
sidebarControls.toggle("slide", { direction: "right" }, 200);
|
||||
}
|
||||
})
|
||||
$("#sidebar-separator").on("mouseleave", function() {
|
||||
if (!sidebarSeparator.dragging) {
|
||||
sidebarControls.hide();
|
||||
}
|
||||
});
|
||||
|
||||
function toggleSidebar(state) {
|
||||
if (!state) {
|
||||
$("#main-container").addClass("sidebar-closed");
|
||||
@@ -215,6 +240,7 @@ RED.sidebar = (function() {
|
||||
toggleSidebar(state);
|
||||
}
|
||||
});
|
||||
RED.popover.tooltip($("#sidebar-separator").find(".sidebar-control-right"),RED._("keyboard.toggleSidebar"),"core:toggle-sidebar");
|
||||
showSidebar();
|
||||
RED.sidebar.info.init();
|
||||
RED.sidebar.config.init();
|
||||
|
@@ -370,9 +370,7 @@ RED.subflow = (function() {
|
||||
return {
|
||||
nodes:removedNodes,
|
||||
links:removedLinks,
|
||||
subflow: {
|
||||
subflow: activeSubflow
|
||||
}
|
||||
subflows: [activeSubflow]
|
||||
}
|
||||
}
|
||||
function init() {
|
||||
@@ -432,6 +430,12 @@ RED.subflow = (function() {
|
||||
RED.nodes.dirty(true);
|
||||
}
|
||||
|
||||
function snapToGrid(x) {
|
||||
if (RED.settings.get("editor").view['view-snap-grid']) {
|
||||
x = Math.round(x / RED.view.gridSize()) * RED.view.gridSize();
|
||||
}
|
||||
return x;
|
||||
}
|
||||
function convertToSubflow() {
|
||||
var selection = RED.view.selection();
|
||||
if (!selection.nodes) {
|
||||
@@ -463,8 +467,14 @@ RED.subflow = (function() {
|
||||
Math.max(boundingBox[3],n.y)
|
||||
]
|
||||
}
|
||||
var offsetX = snapToGrid(boundingBox[0] - 180);
|
||||
var offsetY = snapToGrid(boundingBox[1] - 60);
|
||||
|
||||
var center = [(boundingBox[2]+boundingBox[0]) / 2,(boundingBox[3]+boundingBox[1]) / 2];
|
||||
|
||||
var center = [
|
||||
snapToGrid((boundingBox[2]+boundingBox[0]) / 2),
|
||||
snapToGrid((boundingBox[3]+boundingBox[1]) / 2)
|
||||
];
|
||||
|
||||
RED.nodes.eachLink(function(link) {
|
||||
if (nodes[link.source.id] && nodes[link.target.id]) {
|
||||
@@ -521,8 +531,8 @@ RED.subflow = (function() {
|
||||
in: Object.keys(candidateInputNodes).map(function(v,i) { var index = i; return {
|
||||
type:"subflow",
|
||||
direction:"in",
|
||||
x:candidateInputNodes[v].x-(candidateInputNodes[v].w/2)-80,
|
||||
y:candidateInputNodes[v].y,
|
||||
x:snapToGrid(candidateInputNodes[v].x-(candidateInputNodes[v].w/2)-80 - offsetX),
|
||||
y:snapToGrid(candidateInputNodes[v].y - offsetY),
|
||||
z:subflowId,
|
||||
i:index,
|
||||
id:RED.nodes.id(),
|
||||
@@ -531,8 +541,8 @@ RED.subflow = (function() {
|
||||
out: candidateOutputs.map(function(v,i) { var index = i; return {
|
||||
type:"subflow",
|
||||
direction:"in",
|
||||
x:v.source.x+(v.source.w/2)+80,
|
||||
y:v.source.y,
|
||||
x:snapToGrid(v.source.x+(v.source.w/2)+80 - offsetX),
|
||||
y:snapToGrid(v.source.y - offsetY),
|
||||
z:subflowId,
|
||||
i:index,
|
||||
id:RED.nodes.id(),
|
||||
@@ -607,6 +617,8 @@ RED.subflow = (function() {
|
||||
return isLocalLink;
|
||||
});
|
||||
}
|
||||
n.x -= offsetX;
|
||||
n.y -= offsetY;
|
||||
n.z = subflow.id;
|
||||
}
|
||||
|
||||
@@ -615,7 +627,9 @@ RED.subflow = (function() {
|
||||
nodes:[subflowInstance.id],
|
||||
links:new_links,
|
||||
subflow: {
|
||||
subflow: subflow
|
||||
subflow: subflow,
|
||||
offsetX: offsetX,
|
||||
offsetY: offsetY
|
||||
},
|
||||
|
||||
activeWorkspace: RED.workspaces.active(),
|
||||
|
@@ -15,16 +15,19 @@
|
||||
**/
|
||||
RED.sidebar.config = (function() {
|
||||
|
||||
|
||||
var content = document.createElement("div");
|
||||
content.className = "sidebar-node-config";
|
||||
content.id = "sidebar-node-config";
|
||||
content.tabIndex = 0;
|
||||
|
||||
$('<div class="button-group sidebar-header">'+
|
||||
'<a style="float:left;" class="sidebar-header-button selected" id="workspace-config-node-delete-all" href="#"><span data-i18n="sidebar.config.deleteUnused"></a>'+
|
||||
'<a class="sidebar-header-button-toggle" id="workspace-config-node-filter-all" href="#"><span data-i18n="sidebar.config.filterAll"></span></a>'+
|
||||
'<a class="sidebar-header-button-toggle selected" id="workspace-config-node-filter-unused" href="#"><span data-i18n="sidebar.config.filterUnused"></span></a> '+
|
||||
'</div>'
|
||||
$('<div class="sidebar-header"><span class="button-group">'+
|
||||
'<a class="sidebar-header-button-toggle selected" id="workspace-config-node-filter-all" href="#"><span data-i18n="sidebar.config.filterAll"></span></a>'+
|
||||
'<a class="sidebar-header-button-toggle" id="workspace-config-node-filter-unused" href="#"><span data-i18n="sidebar.config.filterUnused"></span></a> '+
|
||||
'</span></div>'
|
||||
).appendTo(content);
|
||||
|
||||
|
||||
var toolbar = $('<div>'+
|
||||
'<a class="sidebar-footer-button" id="workspace-config-node-collapse-all" href="#"><i class="fa fa-angle-double-up"></i></a> '+
|
||||
'<a class="sidebar-footer-button" id="workspace-config-node-expand-all" href="#"><i class="fa fa-angle-double-down"></i></a>'+
|
||||
@@ -35,7 +38,7 @@ RED.sidebar.config = (function() {
|
||||
var subflowCategories = $("<div>").appendTo(content);
|
||||
|
||||
var showUnusedOnly = false;
|
||||
var unused = [];
|
||||
|
||||
var categories = {};
|
||||
|
||||
function getOrCreateCategory(name,parent,label) {
|
||||
@@ -109,17 +112,6 @@ RED.sidebar.config = (function() {
|
||||
if (A.type > B.type) { return 1;}
|
||||
return 0;
|
||||
});
|
||||
|
||||
unused = nodes.filter(function(n) {
|
||||
return n._def.hasUsers!==false && n.users.length === 0;
|
||||
})
|
||||
|
||||
if (unused.length > 0) {
|
||||
$('#workspace-config-node-delete-all').addClass("selected");
|
||||
} else {
|
||||
$('#workspace-config-node-delete-all').removeClass("selected");
|
||||
}
|
||||
|
||||
if (showUnusedOnly) {
|
||||
var hiddenCount = nodes.length;
|
||||
nodes = nodes.filter(function(n) {
|
||||
@@ -148,21 +140,37 @@ RED.sidebar.config = (function() {
|
||||
}
|
||||
|
||||
var entry = $('<li class="palette_node config_node palette_node_id_'+node.id.replace(/\./g,"-")+'"></li>').appendTo(list);
|
||||
entry.data('node',node.id);
|
||||
$('<div class="palette_label"></div>').text(label).appendTo(entry);
|
||||
if (node._def.hasUsers !== false) {
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container palette_icon_container_right"}).appendTo(entry);
|
||||
var butt = $('<a href="#"/>').click(function(e) { e.preventDefault(); RED.search.show(node.id); }).text(node.users.length).appendTo(iconContainer);
|
||||
if (node.users.length === 0) {
|
||||
iconContainer.text(0);
|
||||
} else {
|
||||
$('<a href="#"/>').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) {
|
||||
entry.addClass("config_node_unused");
|
||||
}
|
||||
}
|
||||
entry.on('click',function(e) {
|
||||
RED.view.select(false);
|
||||
if (e.metaKey) {
|
||||
$(this).toggleClass("selected");
|
||||
} else {
|
||||
$(content).find(".palette_node").removeClass("selected");
|
||||
$(this).addClass("selected");
|
||||
}
|
||||
RED.sidebar.info.refresh(node);
|
||||
});
|
||||
entry.on('dblclick',function(e) {
|
||||
RED.editor.editConfig("", node.type, node.id);
|
||||
});
|
||||
|
||||
var userArray = node.users.map(function(n) { return n.id });
|
||||
entry.on('mouseover',function(e) {
|
||||
RED.nodes.eachNode(function(node) {
|
||||
@@ -233,9 +241,63 @@ RED.sidebar.config = (function() {
|
||||
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:show-config-tab", function() {RED.sidebar.show('config')});
|
||||
RED.actions.add("core:select-all-config-nodes", function() {
|
||||
$(content).find(".palette_node").addClass("selected");
|
||||
})
|
||||
RED.actions.add("core:delete-config-selection", function() {
|
||||
var selectedNodes = [];
|
||||
$(content).find(".palette_node.selected").each(function() {
|
||||
selectedNodes.push($(this).data('node'));
|
||||
});
|
||||
if (selectedNodes.length > 0) {
|
||||
var historyEvent = {
|
||||
t:'delete',
|
||||
nodes:[],
|
||||
changes: {},
|
||||
dirty: RED.nodes.dirty()
|
||||
}
|
||||
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<node.users.length;i++) {
|
||||
var user = node.users[i];
|
||||
historyEvent.changes[user.id] = {
|
||||
changed: user.changed,
|
||||
valid: user.valid
|
||||
};
|
||||
for (var d in user._def.defaults) {
|
||||
if (user._def.defaults.hasOwnProperty(d) && user[d] == id) {
|
||||
historyEvent.changes[user.id][d] = id
|
||||
user[d] = "";
|
||||
user.changed = true;
|
||||
user.dirty = true;
|
||||
}
|
||||
}
|
||||
RED.editor.validateNode(user);
|
||||
}
|
||||
RED.nodes.remove(id);
|
||||
})
|
||||
RED.nodes.dirty(true);
|
||||
RED.view.redraw(true);
|
||||
RED.history.push(historyEvent);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
RED.events.on("view:selection-changed",function() {
|
||||
$(content).find(".palette_node").removeClass("selected");
|
||||
});
|
||||
|
||||
$("#workspace-config-node-collapse-all").on("click", function(e) {
|
||||
e.preventDefault();
|
||||
@@ -255,41 +317,6 @@ RED.sidebar.config = (function() {
|
||||
}
|
||||
}
|
||||
});
|
||||
$("#workspace-config-node-delete-all").on("click", function(e) {
|
||||
e.preventDefault();
|
||||
unused.forEach(function(node) {
|
||||
var configTypeDef = RED.nodes.getType(node.type);
|
||||
if (configTypeDef.oneditdelete) {
|
||||
configTypeDef.oneditdelete.call(node);
|
||||
}
|
||||
var historyEvent = {
|
||||
t:'delete',
|
||||
nodes:[node],
|
||||
changes: {},
|
||||
dirty: RED.nodes.dirty()
|
||||
}
|
||||
for (var i=0; i<node.users.length; i++) {
|
||||
var user = node.users[i];
|
||||
historyEvent.changes[user.id] = {
|
||||
changed: user.changed,
|
||||
valid: user.valid
|
||||
};
|
||||
for (var d in user._def.defaults) {
|
||||
if (user._def.defaults.hasOwnProperty(d) && user[d] == configId) {
|
||||
historyEvent.changes[user.id][d] = configId
|
||||
user[d] = "";
|
||||
user.changed = true;
|
||||
user.dirty = true;
|
||||
}
|
||||
}
|
||||
validateNode(user);
|
||||
}
|
||||
RED.nodes.remove(node.id);
|
||||
RED.nodes.dirty(true);
|
||||
RED.view.redraw(true);
|
||||
RED.history.push(historyEvent);
|
||||
});
|
||||
});
|
||||
$('#workspace-config-node-filter-all').on("click",function(e) {
|
||||
e.preventDefault();
|
||||
if (showUnusedOnly) {
|
||||
@@ -308,8 +335,10 @@ RED.sidebar.config = (function() {
|
||||
refreshConfigNodeList();
|
||||
}
|
||||
});
|
||||
}
|
||||
RED.popover.tooltip($('#workspace-config-node-filter-all'),"Show all config nodes");
|
||||
RED.popover.tooltip($('#workspace-config-node-filter-unused'),"Show all unused config nodes");
|
||||
|
||||
}
|
||||
function show(id) {
|
||||
if (typeof id === 'boolean') {
|
||||
if (id) {
|
||||
@@ -351,7 +380,6 @@ RED.sidebar.config = (function() {
|
||||
}
|
||||
RED.sidebar.show("config");
|
||||
}
|
||||
|
||||
return {
|
||||
init:init,
|
||||
show:show,
|
||||
|
@@ -132,7 +132,8 @@ RED.sidebar.context = (function() {
|
||||
content: content,
|
||||
toolbar: footerToolbar,
|
||||
// pinned: true,
|
||||
enableOnEdit: false
|
||||
enableOnEdit: true,
|
||||
action: "core:show-context-tab"
|
||||
});
|
||||
|
||||
// var toggleLiveButton = $("#sidebar-context-toggle-live");
|
||||
@@ -236,29 +237,83 @@ RED.sidebar.context = (function() {
|
||||
var propRow = $('<tr class="node-info-node-row"><td class="sidebar-context-property"></td><td></td></tr>').appendTo(container);
|
||||
var obj = $(propRow.children()[0]);
|
||||
obj.text(k);
|
||||
var tools = $('<span class="debug-message-tools button-group"></span>').appendTo(obj);
|
||||
var tools = $('<span class="button-group"></span>');
|
||||
|
||||
var refreshItem = $('<button class="editor-button editor-button-small"><i class="fa fa-refresh"></i></button>').appendTo(tools).click(function(e) {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
$.getJSON(baseUrl+"/"+k+"?store="+v.store, function(data) {
|
||||
$(propRow.children()[1]).empty();
|
||||
var payload = data.msg;
|
||||
var format = data.format;
|
||||
payload = RED.utils.decodeObject(payload,format);
|
||||
RED.utils.createObjectElement(payload, {
|
||||
typeHint: data.format,
|
||||
sourceId: id+"."+k
|
||||
}).appendTo(propRow.children()[1]);
|
||||
if (data.msg !== payload || data.format !== format) {
|
||||
payload = data.msg;
|
||||
format = data.format;
|
||||
tools.detach();
|
||||
$(propRow.children()[1]).empty();
|
||||
RED.utils.createObjectElement(RED.utils.decodeObject(payload,format), {
|
||||
typeHint: data.format,
|
||||
sourceId: id+"."+k,
|
||||
tools: tools
|
||||
}).appendTo(propRow.children()[1]);
|
||||
}
|
||||
})
|
||||
});
|
||||
var deleteItem = $('<button class="editor-button editor-button-small"><i class="fa fa-trash"></i></button>').appendTo(tools).click(function(e) {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
var popover = RED.popover.create({
|
||||
trigger: 'modal',
|
||||
target: propRow,
|
||||
direction: "left",
|
||||
content: function() {
|
||||
var content = $('<div>');
|
||||
$('<p data-i18n="sidebar.context.deleteConfirm"></p>').appendTo(content);
|
||||
var row = $('<p>').appendTo(content);
|
||||
var bg = $('<span class="button-group"></span>').appendTo(row);
|
||||
$('<button class="editor-button" data-i18n="common.label.cancel"></button>').appendTo(bg).click(function(e) {
|
||||
e.preventDefault();
|
||||
popover.close();
|
||||
});
|
||||
bg = $('<span class="button-group"></span>').appendTo(row);
|
||||
$('<button class="editor-button primary" data-i18n="common.label.delete"></button>').appendTo(bg).click(function(e) {
|
||||
e.preventDefault();
|
||||
popover.close();
|
||||
$.ajax({
|
||||
url: baseUrl+"/"+k+"?store="+v.store,
|
||||
type: "DELETE"
|
||||
}).done(function(data,textStatus,xhr) {
|
||||
$.getJSON(baseUrl+"/"+k+"?store="+v.store, function(data) {
|
||||
if (data.format === 'undefined') {
|
||||
propRow.remove();
|
||||
if (container.children().length === 0) {
|
||||
$('<tr class="node-info-node-row red-ui-search-empty blank" colspan="2"><td data-i18n="sidebar.context.empty"></td></tr>').appendTo(container).i18n();
|
||||
}
|
||||
} else {
|
||||
payload = data.msg;
|
||||
format = data.format;
|
||||
tools.detach();
|
||||
$(propRow.children()[1]).empty();
|
||||
RED.utils.createObjectElement(RED.utils.decodeObject(payload,format), {
|
||||
typeHint: data.format,
|
||||
sourceId: id+"."+k,
|
||||
tools: tools
|
||||
}).appendTo(propRow.children()[1]);
|
||||
}
|
||||
});
|
||||
}).fail(function(xhr,textStatus,err) {
|
||||
|
||||
})
|
||||
});
|
||||
return content.i18n();
|
||||
}
|
||||
});
|
||||
popover.open();
|
||||
|
||||
});
|
||||
var payload = v.msg;
|
||||
var format = v.format;
|
||||
payload = RED.utils.decodeObject(payload,format);
|
||||
RED.utils.createObjectElement(payload, {
|
||||
RED.utils.createObjectElement(RED.utils.decodeObject(payload,format), {
|
||||
typeHint: v.format,
|
||||
sourceId: id+"."+k
|
||||
sourceId: id+"."+k,
|
||||
tools: tools
|
||||
}).appendTo(propRow.children()[1]);
|
||||
if (contextStores.length > 1) {
|
||||
$("<span>",{class:"sidebar-context-property-storename"}).text(v.store).appendTo($(propRow.children()[0]))
|
||||
|
@@ -92,6 +92,7 @@ RED.sidebar.info = (function() {
|
||||
label: RED._("sidebar.info.label"),
|
||||
name: RED._("sidebar.info.name"),
|
||||
iconClass: "fa fa-info",
|
||||
action:"core:show-info-tab",
|
||||
content: content,
|
||||
pinned: true,
|
||||
enableOnEdit: true
|
||||
@@ -132,6 +133,7 @@ RED.sidebar.info = (function() {
|
||||
|
||||
var table = $('<table class="node-info"></table>').appendTo(propertiesSection.content);
|
||||
var tableBody = $('<tbody>').appendTo(table);
|
||||
|
||||
var subflowNode;
|
||||
var subflowUserCount;
|
||||
|
||||
@@ -140,12 +142,13 @@ RED.sidebar.info = (function() {
|
||||
propRow = $('<tr class="node-info-node-row"><td>Project</td><td></td></tr>').appendTo(tableBody);
|
||||
$(propRow.children()[1]).text(activeProject.name||"");
|
||||
$('<tr class="node-info-property-expand blank"><td colspan="2"></td></tr>').appendTo(tableBody);
|
||||
$('<button class="editor-button editor-button-small" style="position:absolute;right:2px;"><i class="fa fa-ellipsis-h"></i></button>')
|
||||
var editProjectButton = $('<button class="editor-button editor-button-small" style="position:absolute;right:2px;"><i class="fa fa-ellipsis-h"></i></button>')
|
||||
.appendTo(propRow.children()[1])
|
||||
.click(function(evt) {
|
||||
evt.preventDefault();
|
||||
RED.projects.editProject();
|
||||
});
|
||||
RED.popover.tooltip(editProjectButton,RED._('sidebar.project.showProjectSettings'));
|
||||
}
|
||||
propertiesSection.container.show();
|
||||
infoSection.container.show();
|
||||
@@ -155,11 +158,37 @@ RED.sidebar.info = (function() {
|
||||
} else if (Array.isArray(node)) {
|
||||
// Multiple things selected
|
||||
// - hide help and info sections
|
||||
|
||||
var types = {
|
||||
nodes:0,
|
||||
flows:0,
|
||||
subflows:0
|
||||
}
|
||||
node.forEach(function(n) {
|
||||
if (n.type === 'tab') {
|
||||
types.flows++;
|
||||
types.nodes += RED.nodes.filterNodes({z:n.id}).length;
|
||||
} else if (n.type === 'subflow') {
|
||||
types.subflows++;
|
||||
} else {
|
||||
types.nodes++;
|
||||
}
|
||||
});
|
||||
helpSection.container.hide();
|
||||
infoSection.container.hide();
|
||||
// - show the count of selected nodes
|
||||
propRow = $('<tr class="node-info-node-row"><td>'+RED._("sidebar.info.selection")+"</td><td></td></tr>").appendTo(tableBody);
|
||||
$(propRow.children()[1]).text(RED._("sidebar.info.nodes",{count:node.length}))
|
||||
|
||||
var counts = $('<div>').appendTo($(propRow.children()[1]));
|
||||
if (types.flows > 0) {
|
||||
$('<div>').text(RED._("clipboard.flow",{count:types.flows})).appendTo(counts);
|
||||
}
|
||||
if (types.subflows > 0) {
|
||||
$('<div>').text(RED._("clipboard.subflow",{count:types.subflows})).appendTo(counts);
|
||||
}
|
||||
if (types.nodes > 0) {
|
||||
$('<div>').text(RED._("clipboard.node",{count:types.nodes})).appendTo(counts);
|
||||
}
|
||||
} else {
|
||||
// A single 'thing' selected.
|
||||
|
||||
@@ -205,6 +234,7 @@ RED.sidebar.info = (function() {
|
||||
$('<span style="float: right; font-size: 0.8em"><i class="fa fa-warning"></i></span>').prependTo($(propRow.children()[1]))
|
||||
}
|
||||
}
|
||||
var count = 0;
|
||||
if (!m && node.type != "subflow") {
|
||||
var defaults;
|
||||
if (node.type === 'unknown') {
|
||||
@@ -216,9 +246,13 @@ RED.sidebar.info = (function() {
|
||||
})
|
||||
} else if (node._def) {
|
||||
defaults = node._def.defaults;
|
||||
propRow = $('<tr class="node-info-property-row'+(expandedSections.property?"":" hide")+'"><td>'+RED._("sidebar.info.module")+"</td><td></td></tr>").appendTo(tableBody);
|
||||
$(propRow.children()[1]).text(RED.nodes.getType(node.type).set.module);
|
||||
count++;
|
||||
}
|
||||
$('<tr class="node-info-property-expand node-info-property-row blank'+(expandedSections.property?"":" hide")+'"><td colspan="2"></td></tr>').appendTo(tableBody);
|
||||
|
||||
if (defaults) {
|
||||
var count = 0;
|
||||
for (var n in defaults) {
|
||||
if (n != "name" && n != "info" && defaults.hasOwnProperty(n)) {
|
||||
var val = node[n];
|
||||
@@ -252,9 +286,9 @@ RED.sidebar.info = (function() {
|
||||
}
|
||||
}
|
||||
}
|
||||
if (count > 0) {
|
||||
$('<tr class="node-info-property-expand blank"><td colspan="2"><a href="#" class=" node-info-property-header'+(expandedSections.property?" expanded":"")+'"><span class="node-info-property-show-more">'+RED._("sidebar.info.showMore")+'</span><span class="node-info-property-show-less">'+RED._("sidebar.info.showLess")+'</span> <i class="fa fa-caret-down"></i></a></td></tr>').appendTo(tableBody);
|
||||
}
|
||||
}
|
||||
if (count > 0) {
|
||||
$('<tr class="node-info-property-expand blank"><td colspan="2"><a href="#" class=" node-info-property-header'+(expandedSections.property?" expanded":"")+'"><span class="node-info-property-show-more">'+RED._("sidebar.info.showMore")+'</span><span class="node-info-property-show-less">'+RED._("sidebar.info.showLess")+'</span> <i class="fa fa-caret-down"></i></a></td></tr>').appendTo(tableBody);
|
||||
}
|
||||
}
|
||||
if (node.type !== 'tab') {
|
||||
@@ -306,6 +340,20 @@ RED.sidebar.info = (function() {
|
||||
$(".node-info-property-row").toggle(expandedSections["property"]);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
// $('<tr class="blank"><th colspan="2"></th></tr>').appendTo(tableBody);
|
||||
// propRow = $('<tr class="node-info-node-row"><td>Actions</td><td></td></tr>').appendTo(tableBody);
|
||||
// var actionBar = $(propRow.children()[1]);
|
||||
//
|
||||
// // var actionBar = $('<div>',{style:"background: #fefefe; padding: 3px;"}).appendTo(propertiesSection.content);
|
||||
// $('<button type="button" class="editor-button"><i class="fa fa-code"></i></button>').appendTo(actionBar);
|
||||
// $('<button type="button" class="editor-button"><i class="fa fa-code"></i></button>').appendTo(actionBar);
|
||||
// $('<button type="button" class="editor-button"><i class="fa fa-code"></i></button>').appendTo(actionBar);
|
||||
// $('<button type="button" class="editor-button"><i class="fa fa-code"></i></button>').appendTo(actionBar);
|
||||
|
||||
|
||||
|
||||
}
|
||||
function setInfoText(infoText,target) {
|
||||
var info = addTargetToExternalLinks($('<div class="node-help"><span class="bidiAware" dir=\"'+RED.text.bidi.resolveBaseTextDir(infoText)+'">'+infoText+'</span></div>')).appendTo(target);
|
||||
@@ -436,6 +484,8 @@ RED.sidebar.info = (function() {
|
||||
} else {
|
||||
refresh(selection.nodes);
|
||||
}
|
||||
} else if (selection.flows || selection.subflows) {
|
||||
refresh(selection.flows);
|
||||
} else {
|
||||
var activeWS = RED.workspaces.active();
|
||||
|
||||
|
@@ -140,11 +140,12 @@ RED.tray = (function() {
|
||||
|
||||
// tray.body.parent().width(Math.min($("#editor-stack").position().left-8,tray.width));
|
||||
|
||||
|
||||
$("#main-container").scrollLeft(0);
|
||||
el.css({
|
||||
right: -(el.width()+10)+"px",
|
||||
transition: "right 0.25s ease"
|
||||
});
|
||||
$("#workspace").scrollLeft(0);
|
||||
handleWindowResize();
|
||||
openingTray = true;
|
||||
setTimeout(function() {
|
||||
|
@@ -48,7 +48,7 @@ RED.typeSearch = (function() {
|
||||
//shade = $('<div>',{class:"red-ui-type-search-shade"}).appendTo("#main-container");
|
||||
dialog = $("<div>",{id:"red-ui-type-search",class:"red-ui-search red-ui-type-search"}).appendTo("#main-container");
|
||||
var searchDiv = $("<div>",{class:"red-ui-search-container"}).appendTo(dialog);
|
||||
searchInput = $('<input type="text">').attr("placeholder",RED._("search.addNode")).appendTo(searchDiv).searchBox({
|
||||
searchInput = $('<input type="text" id="red-ui-type-search-input">').attr("placeholder",RED._("search.addNode")).appendTo(searchDiv).searchBox({
|
||||
delay: 50,
|
||||
change: function() {
|
||||
search($(this).val());
|
||||
@@ -79,6 +79,19 @@ RED.typeSearch = (function() {
|
||||
$(children[selected]).addClass('selected');
|
||||
ensureSelectedIsVisible();
|
||||
evt.preventDefault();
|
||||
} else if ((evt.metaKey || evt.ctrlKey) && evt.keyCode === 13 ) {
|
||||
// (ctrl or cmd) and enter
|
||||
var index = Math.max(0,selected);
|
||||
if (index < children.length) {
|
||||
var n = $(children[index]).find(".red-ui-editableList-item-content").data('data');
|
||||
typesUsed[n.type] = Date.now();
|
||||
if (n.def.outputs === 0) {
|
||||
confirm(n);
|
||||
} else {
|
||||
addCallback(n.type,true);
|
||||
}
|
||||
$("#red-ui-type-search-input").val("").keyup();
|
||||
}
|
||||
} else if (evt.keyCode === 13) {
|
||||
// Enter
|
||||
var index = Math.max(0,selected);
|
||||
@@ -133,7 +146,7 @@ RED.typeSearch = (function() {
|
||||
nodeDiv.css('backgroundColor',colour);
|
||||
|
||||
var iconContainer = $('<div/>',{class:"palette_icon_container"}).appendTo(nodeDiv);
|
||||
$('<div/>',{class:"palette_icon",style:"background-image: url("+icon_url+")"}).appendTo(iconContainer);
|
||||
RED.utils.createIconElement(icon_url, iconContainer, false);
|
||||
|
||||
if (def.inputs > 0) {
|
||||
$('<div/>',{class:"red-ui-search-result-node-port"}).appendTo(nodeDiv);
|
||||
@@ -191,20 +204,27 @@ RED.typeSearch = (function() {
|
||||
createDialog();
|
||||
}
|
||||
visible = true;
|
||||
setTimeout(function() {
|
||||
$(document).on('mousedown.type-search',handleMouseActivity);
|
||||
$(document).on('mouseup.type-search',handleMouseActivity);
|
||||
$(document).on('click.type-search',handleMouseActivity);
|
||||
},200);
|
||||
} else {
|
||||
dialog.hide();
|
||||
searchResultsDiv.hide();
|
||||
}
|
||||
refreshTypeList();
|
||||
$(document).off('mousedown.type-search');
|
||||
$(document).off('mouseup.type-search');
|
||||
$(document).off('click.type-search');
|
||||
setTimeout(function() {
|
||||
$(document).on('mousedown.type-search',handleMouseActivity);
|
||||
$(document).on('mouseup.type-search',handleMouseActivity);
|
||||
$(document).on('click.type-search',handleMouseActivity);
|
||||
},200);
|
||||
|
||||
refreshTypeList(opts);
|
||||
addCallback = opts.add;
|
||||
closeCallback = opts.close;
|
||||
cancelCallback = opts.cancel;
|
||||
RED.events.emit("type-search:open");
|
||||
//shade.show();
|
||||
if ($("#main-container").height() - opts.y - 150 < 0) {
|
||||
opts.y = opts.y - 235;
|
||||
}
|
||||
dialog.css({left:opts.x+"px",top:opts.y+"px"}).show();
|
||||
searchResultsDiv.slideDown(300);
|
||||
setTimeout(function() {
|
||||
@@ -230,7 +250,6 @@ RED.typeSearch = (function() {
|
||||
$(document).off('click.type-search');
|
||||
}
|
||||
}
|
||||
|
||||
function getTypeLabel(type, def) {
|
||||
var label = type;
|
||||
if (typeof def.paletteLabel !== "undefined") {
|
||||
@@ -254,21 +273,29 @@ RED.typeSearch = (function() {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
function refreshTypeList() {
|
||||
function applyFilter(filter,type,def) {
|
||||
return !filter ||
|
||||
(
|
||||
(!filter.type || type === filter.type) &&
|
||||
(!filter.input || def.inputs > 0) &&
|
||||
(!filter.output || def.outputs > 0)
|
||||
)
|
||||
}
|
||||
function refreshTypeList(opts) {
|
||||
var i;
|
||||
searchResults.editableList('empty');
|
||||
searchInput.searchBox('value','');
|
||||
selected = -1;
|
||||
var common = [
|
||||
'inject','debug','function','change','switch'
|
||||
];
|
||||
].filter(function(t) { return applyFilter(opts.filter,t,RED.nodes.getType(t)); });
|
||||
|
||||
var recentlyUsed = Object.keys(typesUsed);
|
||||
recentlyUsed.sort(function(a,b) {
|
||||
return typesUsed[b]-typesUsed[a];
|
||||
});
|
||||
recentlyUsed = recentlyUsed.filter(function(t) {
|
||||
return common.indexOf(t) === -1;
|
||||
return applyFilter(opts.filter,t,RED.nodes.getType(t)) && common.indexOf(t) === -1;
|
||||
});
|
||||
|
||||
var items = [];
|
||||
@@ -313,8 +340,10 @@ RED.typeSearch = (function() {
|
||||
searchResults.editableList('addItem', item);
|
||||
}
|
||||
for (i=0;i<items.length;i++) {
|
||||
items[i].i = index++;
|
||||
searchResults.editableList('addItem', items[i]);
|
||||
if (applyFilter(opts.filter,items[i].type,items[i].def)) {
|
||||
items[i].i = index++;
|
||||
searchResults.editableList('addItem', items[i]);
|
||||
}
|
||||
}
|
||||
setTimeout(function() {
|
||||
selected = 0;
|
||||
@@ -324,6 +353,7 @@ RED.typeSearch = (function() {
|
||||
|
||||
return {
|
||||
show: show,
|
||||
refresh: refreshTypeList,
|
||||
hide: hide
|
||||
};
|
||||
|
||||
|
@@ -114,7 +114,8 @@ RED.userSettings = (function() {
|
||||
{
|
||||
title: "menu.label.nodes",
|
||||
options: [
|
||||
{setting:"view-node-status",oldSetting:"menu-menu-item-status",label:"menu.label.displayStatus",default: true, toggle:true,onchange:"core:toggle-status"}
|
||||
{setting:"view-node-status",oldSetting:"menu-menu-item-status",label:"menu.label.displayStatus",default: true, toggle:true,onchange:"core:toggle-status"},
|
||||
{setting:"view-node-show-label",label:"menu.label.showNodeLabelDefault",default: true, toggle:true}
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -210,14 +211,14 @@ RED.userSettings = (function() {
|
||||
}
|
||||
}
|
||||
allSettings[opt.setting] = opt;
|
||||
if (opt.onchange) {
|
||||
var value = currentEditorSettings.view[opt.setting];
|
||||
if ((value === null || value === undefined) && opt.hasOwnProperty('default')) {
|
||||
value = opt.default;
|
||||
currentEditorSettings.view[opt.setting] = value;
|
||||
editorSettingsChanged = true;
|
||||
}
|
||||
var value = currentEditorSettings.view[opt.setting];
|
||||
if ((value === null || value === undefined) && opt.hasOwnProperty('default')) {
|
||||
value = opt.default;
|
||||
currentEditorSettings.view[opt.setting] = value;
|
||||
editorSettingsChanged = true;
|
||||
}
|
||||
|
||||
if (opt.onchange) {
|
||||
var callback = opt.onchange;
|
||||
if (typeof callback === 'string') {
|
||||
callback = RED.actions.get(callback);
|
||||
|
@@ -113,7 +113,7 @@ RED.utils = (function() {
|
||||
var pinnedPaths = {};
|
||||
var formattedPaths = {};
|
||||
|
||||
function addMessageControls(obj,sourceId,key,msg,rootPath,strippedKey) {
|
||||
function addMessageControls(obj,sourceId,key,msg,rootPath,strippedKey,extraTools) {
|
||||
if (!pinnedPaths.hasOwnProperty(sourceId)) {
|
||||
pinnedPaths[sourceId] = {}
|
||||
}
|
||||
@@ -150,6 +150,10 @@ RED.utils = (function() {
|
||||
}).toggleClass("selected",isPinned);
|
||||
obj.toggleClass("debug-message-row-pinned",isPinned);
|
||||
}
|
||||
if (extraTools) {
|
||||
extraTools.addClass("debug-message-tools-other");
|
||||
extraTools.appendTo(tools);
|
||||
}
|
||||
}
|
||||
function checkExpanded(strippedKey,expandPaths,minRange,maxRange) {
|
||||
if (expandPaths && expandPaths.length > 0) {
|
||||
@@ -243,6 +247,7 @@ RED.utils = (function() {
|
||||
var expandPaths = options.expandPaths;
|
||||
var ontoggle = options.ontoggle;
|
||||
var exposeApi = options.exposeApi;
|
||||
var tools = options.tools;
|
||||
|
||||
var subElements = {};
|
||||
var i;
|
||||
@@ -262,7 +267,7 @@ RED.utils = (function() {
|
||||
}
|
||||
header = $('<span class="debug-message-row"></span>').appendTo(element);
|
||||
if (sourceId) {
|
||||
addMessageControls(header,sourceId,path,obj,rootPath,strippedKey);
|
||||
addMessageControls(header,sourceId,path,obj,rootPath,strippedKey,tools);
|
||||
}
|
||||
if (!key) {
|
||||
element.addClass("debug-message-top-level");
|
||||
@@ -706,7 +711,11 @@ RED.utils = (function() {
|
||||
function separateIconPath(icon) {
|
||||
var result = {module: "", file: ""};
|
||||
if (icon) {
|
||||
var index = icon.indexOf('/');
|
||||
var index = icon.indexOf('icons/');
|
||||
if (index !== -1) {
|
||||
icon = icon.substring(index+6);
|
||||
}
|
||||
index = icon.indexOf('/');
|
||||
if (index !== -1) {
|
||||
result.module = icon.slice(0, index);
|
||||
result.file = icon.slice(index + 1);
|
||||
@@ -764,17 +773,32 @@ RED.utils = (function() {
|
||||
} else if (node && node.icon) {
|
||||
var iconPath = separateIconPath(node.icon);
|
||||
if (isIconExists(iconPath)) {
|
||||
return RED.settings.apiRootUrl+"icons/" + node.icon;
|
||||
if (iconPath.module === "font-awesome") {
|
||||
return node.icon;
|
||||
} else {
|
||||
return RED.settings.apiRootUrl+"icons/" + node.icon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var iconPath = getDefaultNodeIcon(def, node);
|
||||
if (def.category === 'subflows') {
|
||||
if (!isIconExists(iconPath)) {
|
||||
if (isIconExists(iconPath)) {
|
||||
if (iconPath.module === "font-awesome") {
|
||||
return iconPath.module+"/"+iconPath.file;
|
||||
} else {
|
||||
return RED.settings.apiRootUrl+"icons/"+iconPath.module+"/"+iconPath.file;
|
||||
}
|
||||
} else {
|
||||
// This could be a non-core node trying to use a core icon.
|
||||
iconPath.module = 'node-red';
|
||||
if (isIconExists(iconPath)) {
|
||||
return RED.settings.apiRootUrl+"icons/"+iconPath.module+"/"+iconPath.file;
|
||||
} else if (def.category === 'subflows') {
|
||||
return RED.settings.apiRootUrl+"icons/node-red/subflow.png";
|
||||
} else {
|
||||
return RED.settings.apiRootUrl+"icons/node-red/arrow-in.png";
|
||||
}
|
||||
}
|
||||
return RED.settings.apiRootUrl+"icons/"+iconPath.module+"/"+iconPath.file;
|
||||
}
|
||||
|
||||
function getNodeLabel(node,defaultLabel) {
|
||||
@@ -882,6 +906,40 @@ RED.utils = (function() {
|
||||
return parts;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create or update an icon element and append it to iconContainer.
|
||||
* @param iconUrl - Url of icon.
|
||||
* @param iconContainer - Icon container element with palette_icon_container class.
|
||||
* @param isLarge - Whether the icon size is large.
|
||||
*/
|
||||
function createIconElement(iconUrl, iconContainer, isLarge) {
|
||||
// Removes the previous icon when icon was changed.
|
||||
var iconElement = iconContainer.find(".palette_icon");
|
||||
if (iconElement.length !== 0) {
|
||||
iconElement.remove();
|
||||
}
|
||||
var faIconElement = iconContainer.find("i");
|
||||
if (faIconElement.length !== 0) {
|
||||
faIconElement.remove();
|
||||
}
|
||||
|
||||
// Show either icon image or font-awesome icon
|
||||
var iconPath = separateIconPath(iconUrl);
|
||||
if (iconPath.module === "font-awesome") {
|
||||
var fontAwesomeUnicode = RED.nodes.fontAwesome.getIconUnicode(iconPath.file);
|
||||
if (fontAwesomeUnicode) {
|
||||
var faIconElement = $('<i/>').appendTo(iconContainer);
|
||||
var faLarge = isLarge ? "fa-lg " : "";
|
||||
faIconElement.addClass("palette_icon_fa fa fa-fw " + faLarge + iconPath.file);
|
||||
return;
|
||||
}
|
||||
// If the specified name is not defined in font-awesome, show arrow-in icon.
|
||||
iconUrl = RED.settings.apiRootUrl+"icons/node-red/arrow-in.png"
|
||||
}
|
||||
var imageIconElement = $('<div/>',{class:"palette_icon"}).appendTo(iconContainer);
|
||||
imageIconElement.css("backgroundImage", "url("+iconUrl+")");
|
||||
}
|
||||
|
||||
return {
|
||||
createObjectElement: buildMessageElement,
|
||||
getMessageProperty: getMessageProperty,
|
||||
@@ -894,6 +952,7 @@ RED.utils = (function() {
|
||||
getNodeColor: getNodeColor,
|
||||
addSpinnerOverlay: addSpinnerOverlay,
|
||||
decodeObject: decodeObject,
|
||||
parseContextKey: parseContextKey
|
||||
parseContextKey: parseContextKey,
|
||||
createIconElement: createIconElement
|
||||
}
|
||||
})();
|
||||
|
@@ -108,7 +108,7 @@
|
||||
zIndex: 101,
|
||||
"border-left": "1px solid #ccc",
|
||||
"border-top": "1px solid #ccc",
|
||||
background: "rgba(245,245,245,0.5)",
|
||||
background: "rgba(245,245,245,0.8)",
|
||||
"box-shadow": "-1px 0 3px rgba(0,0,0,0.1)"
|
||||
});
|
||||
|
||||
@@ -158,6 +158,7 @@
|
||||
evt.preventDefault();
|
||||
toggle();
|
||||
})
|
||||
RED.popover.tooltip($("#btn-navigate"),RED._('actions.toggle-navigator'),'core:toggle-navigator');
|
||||
},
|
||||
refresh: refreshNodes,
|
||||
resize: resizeNavBorder,
|
||||
|
137
packages/node_modules/@node-red/editor-client/src/js/ui/view-tools.js
vendored
Normal file
137
packages/node_modules/@node-red/editor-client/src/js/ui/view-tools.js
vendored
Normal file
@@ -0,0 +1,137 @@
|
||||
/**
|
||||
* 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.view.tools = (function() {
|
||||
|
||||
|
||||
function alignToGrid() {
|
||||
var selection = RED.view.selection();
|
||||
if (selection.nodes) {
|
||||
var changedNodes = [];
|
||||
selection.nodes.forEach(function(n) {
|
||||
var x = n.w/2 + Math.round((n.x-n.w/2)/RED.view.gridSize())*RED.view.gridSize();
|
||||
var y = Math.round(n.y/RED.view.gridSize())*RED.view.gridSize();
|
||||
if (n.x !== x || n.y !== y) {
|
||||
changedNodes.push({
|
||||
n:n,
|
||||
ox: n.x,
|
||||
oy: n.y,
|
||||
moved: n.moved
|
||||
});
|
||||
n.x = x;
|
||||
n.y = y;
|
||||
n.dirty = true;
|
||||
n.moved = true;
|
||||
}
|
||||
});
|
||||
if (changedNodes.length > 0) {
|
||||
RED.history.push({t:"move",nodes:changedNodes,dirty:RED.nodes.dirty()});
|
||||
RED.nodes.dirty(true);
|
||||
RED.view.redraw(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var moving_set = null;
|
||||
var endMoveSet = false;
|
||||
function endKeyboardMove() {
|
||||
endMoveSet = false;
|
||||
if (moving_set.length > 0) {
|
||||
var ns = [];
|
||||
for (var i=0;i<moving_set.length;i++) {
|
||||
ns.push({n:moving_set[i].n,ox:moving_set[i].ox,oy:moving_set[i].oy,moved:moving_set[i].moved});
|
||||
moving_set[i].n.moved = true;
|
||||
moving_set[i].n.dirty = true;
|
||||
delete moving_set[i].ox;
|
||||
delete moving_set[i].oy;
|
||||
}
|
||||
RED.view.redraw();
|
||||
RED.history.push({t:"move",nodes:ns,dirty:RED.nodes.dirty()});
|
||||
RED.nodes.dirty(true);
|
||||
moving_set = null;
|
||||
}
|
||||
}
|
||||
|
||||
function moveSelection(dx,dy) {
|
||||
if (moving_set === null) {
|
||||
var selection = RED.view.selection();
|
||||
if (selection.nodes) {
|
||||
moving_set = selection.nodes.map(function(n) { return {n:n}});
|
||||
}
|
||||
}
|
||||
if (moving_set && moving_set.length > 0) {
|
||||
if (!endMoveSet) {
|
||||
$(document).one('keyup',endKeyboardMove);
|
||||
endMoveSet = true;
|
||||
}
|
||||
var minX = 0;
|
||||
var minY = 0;
|
||||
var node;
|
||||
|
||||
for (var i=0;i<moving_set.length;i++) {
|
||||
node = moving_set[i];
|
||||
if (node.ox == null && node.oy == null) {
|
||||
node.ox = node.n.x;
|
||||
node.oy = node.n.y;
|
||||
node.moved = node.n.moved;
|
||||
}
|
||||
node.n.moved = true;
|
||||
node.n.dirty = true;
|
||||
node.n.x += dx;
|
||||
node.n.y += dy;
|
||||
node.n.dirty = true;
|
||||
minX = Math.min(node.n.x-node.n.w/2-5,minX);
|
||||
minY = Math.min(node.n.y-node.n.h/2-5,minY);
|
||||
}
|
||||
|
||||
if (minX !== 0 || minY !== 0) {
|
||||
for (var n = 0; n<moving_set.length; n++) {
|
||||
node = moving_set[n];
|
||||
node.n.x -= minX;
|
||||
node.n.y -= minY;
|
||||
}
|
||||
}
|
||||
RED.view.redraw();
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
init: function() {
|
||||
RED.actions.add("core:align-selection-to-grid", alignToGrid);
|
||||
|
||||
RED.actions.add("core:move-selection-up", function() { moveSelection(0,-1);});
|
||||
RED.actions.add("core:move-selection-right", function() { moveSelection(1,0);});
|
||||
RED.actions.add("core:move-selection-down", function() { moveSelection(0,1);});
|
||||
RED.actions.add("core:move-selection-left", function() { moveSelection(-1,0);});
|
||||
|
||||
RED.actions.add("core:step-selection-up", function() { moveSelection(0,-RED.view.gridSize());});
|
||||
RED.actions.add("core:step-selection-right", function() { moveSelection(RED.view.gridSize(),0);});
|
||||
RED.actions.add("core:step-selection-down", function() { moveSelection(0,RED.view.gridSize());});
|
||||
RED.actions.add("core:step-selection-left", function() { moveSelection(-RED.view.gridSize(),0);});
|
||||
},
|
||||
/**
|
||||
* Aligns all selected nodes to the current grid
|
||||
*/
|
||||
alignSelectionToGrid: alignToGrid,
|
||||
/**
|
||||
* Moves all of the selected nodes by the specified amount
|
||||
* @param {Number} dx
|
||||
* @param {Number} dy
|
||||
*/
|
||||
moveSelection: moveSelection
|
||||
}
|
||||
|
||||
})();
|
File diff suppressed because it is too large
Load Diff
@@ -20,9 +20,9 @@ RED.workspaces = (function() {
|
||||
var activeWorkspace = 0;
|
||||
var workspaceIndex = 0;
|
||||
|
||||
function addWorkspace(ws,skipHistoryEntry) {
|
||||
function addWorkspace(ws,skipHistoryEntry,targetIndex) {
|
||||
if (ws) {
|
||||
workspace_tabs.addTab(ws);
|
||||
workspace_tabs.addTab(ws,targetIndex);
|
||||
workspace_tabs.resize();
|
||||
} else {
|
||||
var tabId = RED.nodes.id();
|
||||
@@ -31,8 +31,8 @@ RED.workspaces = (function() {
|
||||
} while ($("#workspace-tabs a[title='"+RED._('workspace.defaultName',{number:workspaceIndex})+"']").size() !== 0);
|
||||
|
||||
ws = {type:"tab",id:tabId,disabled: false,info:"",label:RED._('workspace.defaultName',{number:workspaceIndex})};
|
||||
RED.nodes.addWorkspace(ws);
|
||||
workspace_tabs.addTab(ws);
|
||||
RED.nodes.addWorkspace(ws,targetIndex);
|
||||
workspace_tabs.addTab(ws,targetIndex);
|
||||
workspace_tabs.activateTab(tabId);
|
||||
if (!skipHistoryEntry) {
|
||||
RED.history.push({t:'add',workspaces:[ws],dirty:RED.nodes.dirty()});
|
||||
@@ -46,6 +46,8 @@ RED.workspaces = (function() {
|
||||
if (workspaceTabCount === 1) {
|
||||
return;
|
||||
}
|
||||
var workspaceOrder = RED.nodes.getWorkspaceOrder();
|
||||
ws._index = workspaceOrder.indexOf(ws.id);
|
||||
removeWorkspace(ws);
|
||||
var historyEvent = RED.nodes.removeWorkspace(ws.id);
|
||||
historyEvent.t = 'delete';
|
||||
@@ -56,7 +58,7 @@ RED.workspaces = (function() {
|
||||
RED.sidebar.config.refresh();
|
||||
}
|
||||
|
||||
function showRenameWorkspaceDialog(id) {
|
||||
function showEditWorkspaceDialog(id) {
|
||||
var workspace = RED.nodes.workspace(id);
|
||||
RED.view.state(RED.state.EDITING);
|
||||
var tabflowEditor;
|
||||
@@ -105,8 +107,8 @@ RED.workspaces = (function() {
|
||||
changed = true;
|
||||
workspace.info = info;
|
||||
}
|
||||
$("#red-ui-tab-"+(workspace.id.replace(".","-"))).toggleClass('workspace-disabled',workspace.disabled);
|
||||
// $("#workspace").toggleClass("workspace-disabled",workspace.disabled);
|
||||
$("#red-ui-tab-"+(workspace.id.replace(".","-"))).toggleClass('workspace-disabled',!!workspace.disabled);
|
||||
$("#workspace").toggleClass("workspace-disabled",!!workspace.disabled);
|
||||
|
||||
if (changed) {
|
||||
var historyEvent = {
|
||||
@@ -123,6 +125,14 @@ RED.workspaces = (function() {
|
||||
if (!selection.nodes && !selection.links) {
|
||||
RED.sidebar.info.refresh(workspace);
|
||||
}
|
||||
if (changes.hasOwnProperty('disabled')) {
|
||||
RED.nodes.eachNode(function(n) {
|
||||
if (n.z === workspace.id) {
|
||||
n.dirty = true;
|
||||
}
|
||||
});
|
||||
RED.view.redraw();
|
||||
}
|
||||
}
|
||||
RED.tray.close();
|
||||
}
|
||||
@@ -136,7 +146,6 @@ RED.workspaces = (function() {
|
||||
height -= $(rows[i]).outerHeight(true);
|
||||
}
|
||||
height -= (parseInt($("#dialog-form").css("marginTop"))+parseInt($("#dialog-form").css("marginBottom")));
|
||||
height -= 28;
|
||||
$(".node-text-editor").css("height",height+"px");
|
||||
tabflowEditor.resize();
|
||||
},
|
||||
@@ -150,13 +159,13 @@ RED.workspaces = (function() {
|
||||
|
||||
$('<div class="form-row">'+
|
||||
'<label for="node-input-disabled-btn" data-i18n="editor:workspace.status"></label>'+
|
||||
'<button id="node-input-disabled-btn" class="editor-button"><i class="fa fa-toggle-on"></i> <span id="node-input-disabled-label"></span></button> '+
|
||||
'<button type="button" id="node-input-disabled-btn" class="editor-button"><i class="fa fa-toggle-on"></i> <span id="node-input-disabled-label"></span></button> '+
|
||||
'<input type="checkbox" id="node-input-disabled" style="display: none;"/>'+
|
||||
'</div>').appendTo(dialogForm);
|
||||
|
||||
$('<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>'+
|
||||
'<div style="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);
|
||||
tabflowEditor = RED.editor.createEditor({
|
||||
id: 'node-input-info',
|
||||
@@ -164,7 +173,22 @@ RED.workspaces = (function() {
|
||||
value: ""
|
||||
});
|
||||
|
||||
$('<div class="form-tips" data-i18n="editor:workspace.tip"></div>').appendTo(dialogForm);
|
||||
$('#node-info-input-info-expand').click(function(e) {
|
||||
e.preventDefault();
|
||||
var value = tabflowEditor.getValue();
|
||||
RED.editor.editMarkdown({
|
||||
value: value,
|
||||
width: "Infinity",
|
||||
cursor: tabflowEditor.getCursorPosition(),
|
||||
complete: function(v,cursor) {
|
||||
tabflowEditor.setValue(v, -1);
|
||||
tabflowEditor.gotoLine(cursor.row+1,cursor.column,false);
|
||||
setTimeout(function() {
|
||||
tabflowEditor.focus();
|
||||
},300);
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
dialogForm.find('#node-input-disabled-btn').on("click",function(e) {
|
||||
var i = $(this).find("i");
|
||||
@@ -224,9 +248,9 @@ RED.workspaces = (function() {
|
||||
}
|
||||
activeWorkspace = tab.id;
|
||||
event.workspace = activeWorkspace;
|
||||
// $("#workspace").toggleClass("workspace-disabled",tab.disabled);
|
||||
RED.events.emit("workspace:change",event);
|
||||
window.location.hash = 'flow/'+tab.id;
|
||||
$("#workspace").toggleClass("workspace-disabled",!!tab.disabled);
|
||||
RED.sidebar.config.refresh();
|
||||
RED.view.focus();
|
||||
},
|
||||
@@ -235,7 +259,7 @@ RED.workspaces = (function() {
|
||||
},
|
||||
ondblclick: function(tab) {
|
||||
if (tab.type != "subflow") {
|
||||
showRenameWorkspaceDialog(tab.id);
|
||||
showEditWorkspaceDialog(tab.id);
|
||||
} else {
|
||||
RED.editor.editSubflow(RED.nodes.subflow(tab.id));
|
||||
}
|
||||
@@ -267,11 +291,25 @@ RED.workspaces = (function() {
|
||||
RED.nodes.dirty(true);
|
||||
setWorkspaceOrder(newOrder);
|
||||
},
|
||||
onselect: function(selectedTabs) {
|
||||
RED.view.select(false)
|
||||
if (selectedTabs.length === 0) {
|
||||
$("#chart svg").css({"pointer-events":"auto",filter:"none"})
|
||||
$("#workspace-toolbar").css({"pointer-events":"auto",filter:"none"})
|
||||
$("#palette-container").css({"pointer-events":"auto",filter:"none"})
|
||||
$(".sidebar-shade").hide();
|
||||
} else {
|
||||
RED.view.select(false)
|
||||
$("#chart svg").css({"pointer-events":"none",filter:"opacity(60%)"})
|
||||
$("#workspace-toolbar").css({"pointer-events":"none",filter:"opacity(60%)"})
|
||||
$("#palette-container").css({"pointer-events":"none",filter:"opacity(60%)"})
|
||||
$(".sidebar-shade").show();
|
||||
}
|
||||
},
|
||||
minimumActiveTabWidth: 150,
|
||||
scrollable: true,
|
||||
addButton: function() {
|
||||
addWorkspace();
|
||||
}
|
||||
addButton: "core:add-flow",
|
||||
addButtonCaption: RED._("workspace.addFlow")
|
||||
});
|
||||
workspaceTabCount = 0;
|
||||
}
|
||||
@@ -301,7 +339,7 @@ RED.workspaces = (function() {
|
||||
workspace_tabs.resize();
|
||||
});
|
||||
|
||||
RED.actions.add("core:add-flow",addWorkspace);
|
||||
RED.actions.add("core:add-flow",function(opts) { addWorkspace(undefined,undefined,opts?opts.index:undefined)});
|
||||
RED.actions.add("core:edit-flow",editWorkspace);
|
||||
RED.actions.add("core:remove-flow",removeWorkspace);
|
||||
|
||||
@@ -309,7 +347,7 @@ RED.workspaces = (function() {
|
||||
}
|
||||
|
||||
function editWorkspace(id) {
|
||||
showRenameWorkspaceDialog(id||activeWorkspace);
|
||||
showEditWorkspaceDialog(id||activeWorkspace);
|
||||
}
|
||||
|
||||
function removeWorkspace(ws) {
|
||||
@@ -319,9 +357,9 @@ RED.workspaces = (function() {
|
||||
if (workspace_tabs.contains(ws.id)) {
|
||||
workspace_tabs.removeTab(ws.id);
|
||||
}
|
||||
}
|
||||
if (ws.id === activeWorkspace) {
|
||||
activeWorkspace = 0;
|
||||
if (ws.id === activeWorkspace) {
|
||||
activeWorkspace = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -347,6 +385,9 @@ RED.workspaces = (function() {
|
||||
active: function() {
|
||||
return activeWorkspace
|
||||
},
|
||||
selection: function() {
|
||||
return workspace_tabs.selection();
|
||||
},
|
||||
show: function(id) {
|
||||
if (!workspace_tabs.contains(id)) {
|
||||
var sf = RED.nodes.subflow(id);
|
||||
|
@@ -6,3 +6,24 @@
|
||||
border-top-right-radius: 4px;
|
||||
border-bottom-right-radius: 4px;
|
||||
}
|
||||
|
||||
#event-log-editor {
|
||||
.ace_scroller {
|
||||
background: #444;
|
||||
color: #dd9;
|
||||
}
|
||||
.ace_active-line {
|
||||
background: #666 !important;
|
||||
}
|
||||
.ace_selection {
|
||||
background: #999 !important;
|
||||
}
|
||||
}
|
||||
|
||||
.ace_tooltip {
|
||||
background-image: none;
|
||||
background: #fcffdc;
|
||||
border-radius: 4px;
|
||||
@include component-shadow;
|
||||
border-color: $primary-border-color;
|
||||
}
|
||||
|
@@ -19,7 +19,3 @@
|
||||
div.btn-group, a.btn {
|
||||
@include disable-selection;
|
||||
}
|
||||
|
||||
.dropdown-menu>li>a {
|
||||
color: #444;
|
||||
}
|
||||
|
@@ -35,6 +35,7 @@ $primary-border-color: #bbbbbb;
|
||||
$secondary-border-color: #dddddd;
|
||||
|
||||
$tab-background-active: #fff;
|
||||
$tab-background-selected: #f9f9f9;
|
||||
$tab-background-inactive: #f0f0f0;
|
||||
$tab-background-hover: #ddd;
|
||||
|
||||
@@ -67,3 +68,6 @@ $editor-button-color: #999;
|
||||
$editor-button-background: #fff;
|
||||
|
||||
$shade-color: rgba(160,160,160,0.5);
|
||||
|
||||
$popover-background: #333;
|
||||
$popover-color: #eee;
|
||||
|
@@ -81,6 +81,9 @@
|
||||
.debug-message-tools-pin {
|
||||
display: inline-block;
|
||||
}
|
||||
.debug-message-tools-other {
|
||||
display: inline-block;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -134,6 +137,9 @@
|
||||
.debug-message-tools-copy {
|
||||
display: none;
|
||||
}
|
||||
.debug-message-tools-other {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
.debug-message-payload {
|
||||
display: block;
|
||||
|
@@ -257,6 +257,11 @@
|
||||
background-position: 49% 50%;
|
||||
width: 15px;
|
||||
}
|
||||
.palette_icon_fa {
|
||||
position: relative;
|
||||
top: -2.5px;
|
||||
left: 0px;
|
||||
}
|
||||
.palette_icon_container {
|
||||
width: 18px;
|
||||
}
|
||||
@@ -562,9 +567,15 @@ ul.node-dialog-configm-deploy-list {
|
||||
td.lineno {
|
||||
font-family: monospace;
|
||||
text-align: right;
|
||||
color: #aaa;
|
||||
color: #999;
|
||||
background: #f6f6f6;
|
||||
padding: 1px 5px;
|
||||
&.added {
|
||||
background: #c0f6c0;
|
||||
}
|
||||
&.removed {
|
||||
background: #ffcccc;
|
||||
}
|
||||
}
|
||||
td.lineno:nth-child(3) {
|
||||
border-left: 1px solid $secondary-border-color;
|
||||
@@ -573,12 +584,20 @@ ul.node-dialog-configm-deploy-list {
|
||||
font-family: monospace;
|
||||
white-space: pre-wrap;
|
||||
padding: 1px 5px;
|
||||
border-left: 1px solid #ccc;
|
||||
span.prefix {
|
||||
width: 30px;
|
||||
display: inline-block;
|
||||
text-align: center;
|
||||
color: #999;
|
||||
}
|
||||
|
||||
&.added {
|
||||
border-left-color: #aaeeaa
|
||||
}
|
||||
&.removed {
|
||||
border-left-color: #eebbbb
|
||||
}
|
||||
}
|
||||
td.blank {
|
||||
background: #f6f6f6;
|
||||
@@ -587,7 +606,7 @@ ul.node-dialog-configm-deploy-list {
|
||||
background: #eefaee;
|
||||
}
|
||||
td.removed {
|
||||
background: #fadddd;
|
||||
background: #ffecec;
|
||||
}
|
||||
tr.mergeHeader td {
|
||||
color: #800080;
|
||||
|
@@ -19,6 +19,15 @@
|
||||
background: #999;
|
||||
}
|
||||
|
||||
.dropdown-menu {
|
||||
background: #f3f3f3;
|
||||
border-color: $secondary-border-color;
|
||||
&>li>a {
|
||||
color: #444;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.dropdown-menu * .fa-check-square {
|
||||
display: none;
|
||||
color: #e0e0e0;
|
||||
|
@@ -57,6 +57,10 @@
|
||||
.editor-tray-content {
|
||||
overflow: auto;
|
||||
position: relative;
|
||||
.palette_icon_fa {
|
||||
top: 6px;
|
||||
left: 4px;
|
||||
}
|
||||
}
|
||||
.editor-tray-header {
|
||||
@include disable-selection;
|
||||
@@ -205,11 +209,28 @@
|
||||
}
|
||||
|
||||
.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-radius:5px;
|
||||
overflow: hidden;
|
||||
font-size: 14px !important;
|
||||
font-family: Menlo, Consolas, 'DejaVu Sans Mono', Courier, monospace !important;
|
||||
height: 100%;
|
||||
|
||||
&.node-text-editor-container-toolbar {
|
||||
height: calc(100% - 40px);
|
||||
}
|
||||
}
|
||||
|
||||
.editor-button {
|
||||
@@ -317,20 +338,29 @@
|
||||
margin: 0;
|
||||
height: 100%;
|
||||
.red-ui-panel {
|
||||
&:first-child {
|
||||
padding: 20px 20px 0;
|
||||
}
|
||||
padding: 20px 20px 10px;
|
||||
&:last-child {
|
||||
padding-bottom: 20px;
|
||||
padding-top: 60px;
|
||||
background: #f9f9f9;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
.node-input-markdown-panel-preview {
|
||||
padding: 10px;
|
||||
border:1px solid #ccc;
|
||||
border-radius:5px;
|
||||
height: calc(100% - 21px);
|
||||
overflow-y: scroll;
|
||||
background: #fff;
|
||||
}
|
||||
|
||||
#clipboard-hidden {
|
||||
position: absolute;
|
||||
top: -3000px;
|
||||
}
|
||||
.node-label-form-row {
|
||||
margin: 5px 0;
|
||||
margin: 5px 0 0 50px;
|
||||
label {
|
||||
margin-right: 20px;
|
||||
text-align: right;
|
||||
@@ -365,6 +395,16 @@
|
||||
}
|
||||
|
||||
}
|
||||
#node-settings-icon-button {
|
||||
position: relative;
|
||||
padding-left: 30px;
|
||||
width: calc(100% - 150px);
|
||||
.red-ui-search-result-node {
|
||||
position: absolute;
|
||||
top: 2px;
|
||||
left: 2px;
|
||||
}
|
||||
}
|
||||
#node-settings-icon {
|
||||
margin-left: 10px;
|
||||
width: calc(100% - 163px);
|
||||
@@ -403,6 +443,10 @@
|
||||
border-color: white;
|
||||
}
|
||||
}
|
||||
.palette_icon_fa {
|
||||
top: 6px;
|
||||
left: 3px;
|
||||
}
|
||||
}
|
||||
.red-ui-icon-list-module {
|
||||
background: $palette-header-background;
|
||||
|
@@ -92,6 +92,14 @@
|
||||
stroke-dasharray:10,4;
|
||||
stroke: #f33;
|
||||
}
|
||||
.node_placeholder {
|
||||
stroke-dasharray:10,4;
|
||||
stroke: #aaa;
|
||||
fill: #eee;
|
||||
opacity: 0.5;
|
||||
stroke-width: 2;
|
||||
}
|
||||
|
||||
.tool_arrow {
|
||||
stroke-width: 1;
|
||||
stroke: #999;
|
||||
@@ -169,7 +177,16 @@
|
||||
.node_subflow .node {
|
||||
stroke-dasharray:8, 3;
|
||||
}
|
||||
|
||||
.workspace-disabled {
|
||||
.link_line {
|
||||
stroke-dasharray: 10,5 !important;
|
||||
stroke-width: 2 !important;
|
||||
stroke: $link-subflow-color;
|
||||
}
|
||||
.node {
|
||||
stroke-dasharray: 10,4;
|
||||
}
|
||||
}
|
||||
|
||||
.node_quickadd * {
|
||||
stroke-dasharray: 12,3;
|
||||
@@ -185,8 +202,8 @@
|
||||
}
|
||||
|
||||
.port_hovered {
|
||||
stroke: $port-selected-color;
|
||||
fill: $port-selected-color;
|
||||
stroke: $port-selected-color !important;
|
||||
fill: $port-selected-color !important;
|
||||
}
|
||||
|
||||
.port_quick_link {
|
||||
@@ -202,7 +219,7 @@
|
||||
}
|
||||
|
||||
.drag_line {
|
||||
stroke: $node-selected-color;
|
||||
stroke: $node-selected-color !important;
|
||||
stroke-width: 3;
|
||||
fill: none;
|
||||
pointer-events: none;
|
||||
@@ -227,10 +244,10 @@
|
||||
stroke: $link-link-color;
|
||||
fill: none;
|
||||
stroke-dasharray: 15,2;
|
||||
pointer-events: none;
|
||||
// pointer-events: none;
|
||||
}
|
||||
.link_port {
|
||||
fill: #fff;
|
||||
fill: #eee;
|
||||
stroke: $link-link-color;
|
||||
stroke-width: 1;
|
||||
}
|
||||
@@ -281,14 +298,14 @@ g.link_unknown path.link_line {
|
||||
pointer-events: none;
|
||||
|
||||
path {
|
||||
fill: white;
|
||||
stroke: #999;
|
||||
fill: $popover-background;
|
||||
stroke: $popover-background;
|
||||
stroke-width: 1;
|
||||
}
|
||||
}
|
||||
.port_tooltip_label {
|
||||
stroke-width: 0;
|
||||
fill: #666;
|
||||
fill: $popover-color;
|
||||
font-size: 12px;
|
||||
pointer-events: none;
|
||||
-webkit-touch-callout: none;
|
||||
|
@@ -202,6 +202,7 @@ span.logo {
|
||||
|
||||
#header ul.dropdown-menu {
|
||||
background: $headerMenuBackground;
|
||||
border: 1px solid rgba(0,0,0,0.2);
|
||||
width: 250px !important;
|
||||
margin-top: 0;
|
||||
}
|
||||
|
@@ -31,3 +31,20 @@
|
||||
#node-select-library li.list-hover {
|
||||
background: #ffffd0;
|
||||
}
|
||||
|
||||
.clipboard-import-error {
|
||||
pre {
|
||||
margin: 10px 0;
|
||||
border: none;
|
||||
color: #666;
|
||||
span {
|
||||
padding: 5px 0;
|
||||
}
|
||||
span.error {
|
||||
padding: 5px;
|
||||
background: #e25151;
|
||||
color: white;
|
||||
margin: 0 1px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user