Released v5.2.0

This commit is contained in:
jos 2016-03-20 18:19:13 +01:00
parent bfad6f5e7b
commit aeca44405e
13 changed files with 1091 additions and 952 deletions

View File

@ -3,7 +3,7 @@
https://github.com/josdejong/jsoneditor
## not yet released, version 5.2.0
## 2016-03-20, version 5.2.0
- Implemented method `editor.destroy()` to properly cleanup the editor (#278).
- Fixed #268: JSONEditor now trims text in fields and values.

View File

@ -24,8 +24,8 @@
* Copyright (c) 2011-2016 Jos de Jong, http://jsoneditoronline.org
*
* @author Jos de Jong, <wjosdejong@gmail.com>
* @version 5.1.5
* @date 2016-02-15
* @version 5.2.0
* @date 2016-03-20
*/
(function webpackUniversalModuleDefinition(root, factory) {
if(typeof exports === 'object' && typeof module === 'object')
@ -215,10 +215,9 @@ return /******/ (function(modules) { // webpackBootstrap
};
/**
* Detach the editor from the DOM
* @private
* Destroy the editor. Clean up DOM, event listeners, and web workers.
*/
JSONEditor.prototype._delete = function () {};
JSONEditor.prototype.destroy = function () {};
/**
* Set JSON object in editor
@ -292,7 +291,7 @@ return /******/ (function(modules) { // webpackBootstrap
name = this.getName();
data = this[asText ? 'getText' : 'get'](); // get text or json
this._delete();
this.destroy();
util.clear(this);
util.extend(this, config.mixin);
this.create(container, options);
@ -465,7 +464,7 @@ return /******/ (function(modules) { // webpackBootstrap
var SearchBox = __webpack_require__(6);
var ContextMenu = __webpack_require__(7);
var Node = __webpack_require__(8);
var modeswitcher = __webpack_require__(9);
var ModeSwitcher = __webpack_require__(9);
var util = __webpack_require__(3);
// create a mixin with the functions for tree mode
@ -505,6 +504,8 @@ return /******/ (function(modules) { // webpackBootstrap
this.validateSchema = null; // will be set in .setSchema(schema)
this.errorNodes = [];
this.node = null;
this.focusTarget = null;
this._setOptions(options);
@ -517,12 +518,39 @@ return /******/ (function(modules) { // webpackBootstrap
};
/**
* Detach the editor from the DOM
* @private
* Destroy the editor. Clean up DOM, event listeners, and web workers.
*/
treemode._delete = function () {
treemode.destroy = function () {
if (this.frame && this.container && this.frame.parentNode == this.container) {
this.container.removeChild(this.frame);
this.frame = null;
}
this.container = null;
this.dom = null;
this.clear();
this.node = null;
this.focusTarget = null;
this.selection = null;
this.multiselection = null;
this.errorNodes = null;
this.validateSchema = null;
this._debouncedValidate = null;
if (this.history) {
this.history.destroy();
this.history = null;
}
if (this.searchBox) {
this.searchBox.destroy();
this.searchBox = null;
}
if (this.modeSwitcher) {
this.modeSwitcher.destroy();
this.modeSwitcher = null;
}
};
@ -556,12 +584,6 @@ return /******/ (function(modules) { // webpackBootstrap
this._debouncedValidate = util.debounce(this.validate.bind(this), this.DEBOUNCE_INTERVAL);
};
// node currently being edited
var focusNode = undefined;
// dom having focus
var domFocus = null;
/**
* Set JSON object in editor
* @param {Object | undefined} json JSON data
@ -618,8 +640,8 @@ return /******/ (function(modules) { // webpackBootstrap
*/
treemode.get = function () {
// remove focus from currently edited node
if (focusNode) {
focusNode.blur();
if (this.focusTarget) {
this.focusTarget.blur();
}
if (this.node) {
@ -982,7 +1004,7 @@ return /******/ (function(modules) { // webpackBootstrap
}
return {
dom: domFocus,
dom: this.focusTarget,
range: range,
nodes: this.multiselection.nodes.slice(0),
scrollTop: this.content ? this.content.scrollTop : 0
@ -1148,9 +1170,14 @@ return /******/ (function(modules) { // webpackBootstrap
// create mode box
if (this.options && this.options.modes && this.options.modes.length) {
var modeBox = modeswitcher.create(this, this.options.modes, this.options.mode);
this.menu.appendChild(modeBox);
this.dom.modeBox = modeBox;
var me = this;
this.modeSwitcher = new ModeSwitcher(this.menu, this.options.modes, this.options.mode, function onSwitch(mode) {
me.modeSwitcher.destroy();
// switch mode and restore focus
me.setMode(mode);
me.modeSwitcher.focus();
});
}
// create search box
@ -1198,7 +1225,7 @@ return /******/ (function(modules) { // webpackBootstrap
}
if (event.type == 'focus') {
domFocus = event.target;
this.focusTarget = event.target;
}
if (event.type == 'mousedown') {
@ -1471,9 +1498,10 @@ return /******/ (function(modules) { // webpackBootstrap
var handled = false;
if (keynum == 9) { // Tab or Shift+Tab
var me = this;
setTimeout(function () {
// select all text when moving focus to an editable div
util.selectContentEditable(domFocus);
util.selectContentEditable(me.focusTarget);
}, 0);
}
@ -1624,7 +1652,7 @@ return /******/ (function(modules) { // webpackBootstrap
// failed to load ace, no problem, we will fall back to plain text
}
var modeswitcher = __webpack_require__(9);
var ModeSwitcher = __webpack_require__(9);
var util = __webpack_require__(3);
// create a mixin with the functions for text mode
@ -1741,9 +1769,13 @@ return /******/ (function(modules) { // webpackBootstrap
// create mode box
if (this.options && this.options.modes && this.options.modes.length) {
var modeBox = modeswitcher.create(this, this.options.modes, this.options.mode);
this.menu.appendChild(modeBox);
this.dom.modeBox = modeBox;
this.modeSwitcher = new ModeSwitcher(this.menu, this.options.modes, this.options.mode, function onSwitch(mode) {
me.modeSwitcher.destroy();
// switch mode and restore focus
me.setMode(mode);
me.modeSwitcher.focus();
});
}
this.content = document.createElement('div');
@ -1871,18 +1903,27 @@ return /******/ (function(modules) { // webpackBootstrap
};
/**
* Detach the editor from the DOM
* @private
* Destroy the editor. Clean up DOM, event listeners, and web workers.
*/
textmode._delete = function () {
textmode.destroy = function () {
// remove old ace editor
if (this.aceEditor) {
this.aceEditor.destroy();
this.aceEditor = null;
}
if (this.frame && this.container && this.frame.parentNode == this.container) {
this.container.removeChild(this.frame);
}
if (this.modeSwitcher) {
this.modeSwitcher.destroy();
this.modeSwitcher = null;
}
this.textarea = null;
this._debouncedValidate = null;
};
/**
@ -2966,6 +3007,9 @@ return /******/ (function(modules) { // webpackBootstrap
*/
function History (editor) {
this.editor = editor;
this.history = [];
this.index = -1;
this.clear();
// map with all supported actions
@ -3208,6 +3252,16 @@ return /******/ (function(modules) { // webpackBootstrap
}
};
/**
* Destroy history
*/
History.prototype.destroy = function () {
this.editor = null;
this.history = [];
this.index = -1;
};
module.exports = History;
@ -3509,6 +3563,21 @@ return /******/ (function(modules) { // webpackBootstrap
this._onSearch();
};
/**
* Destroy the search box
*/
SearchBox.prototype.destroy = function () {
this.editor = null;
this.dom.container.removeChild(this.dom.table);
this.dom = null;
this.results = null;
this.activeResult = null;
this._clearDelay();
};
module.exports = SearchBox;
@ -6052,7 +6121,6 @@ return /******/ (function(modules) { // webpackBootstrap
target = event.target || event.srcElement,
dom = this.dom,
node = this,
focusNode,
expandable = this._hasChilds();
// check if mouse is on menu or on dragarea.
@ -6101,10 +6169,6 @@ return /******/ (function(modules) { // webpackBootstrap
if (target == domValue) {
//noinspection FallthroughInSwitchStatementJS
switch (type) {
case 'focus':
focusNode = this;
break;
case 'blur':
case 'change':
this._getDomValue(true);
@ -6154,10 +6218,6 @@ return /******/ (function(modules) { // webpackBootstrap
var domField = dom.field;
if (target == domField) {
switch (type) {
case 'focus':
focusNode = this;
break;
case 'blur':
case 'change':
this._getDomField(true);
@ -7323,7 +7383,7 @@ return /******/ (function(modules) { // webpackBootstrap
* @private
*/
Node.prototype._unescapeHTML = function (escapedText) {
var json = '"' + this._escapeJSON(escapedText) + '"';
var json = '"' + this._escapeJSON(escapedText.trim()) + '"';
var htmlEscaped = util.parse(json);
return htmlEscaped
@ -7387,64 +7447,48 @@ return /******/ (function(modules) { // webpackBootstrap
/**
* Create a select box to be used in the editor menu's, which allows to switch mode
* @param {Object} editor
* @param {HTMLElement} container
* @param {String[]} modes Available modes: 'code', 'form', 'text', 'tree', 'view'
* @param {String} current Available modes: 'code', 'form', 'text', 'tree', 'view'
* @returns {HTMLElement} box
* @param {function(mode: string)} onSwitch Callback invoked on switch
* @constructor
*/
function createModeSwitcher(editor, modes, current) {
// TODO: decouple mode switcher from editor
/**
* Switch the mode of the editor
* @param {String} mode
*/
function switchMode(mode) {
// switch mode
editor.setMode(mode);
// restore focus on mode box
var modeBox = editor.dom && editor.dom.modeBox;
if (modeBox) {
modeBox.focus();
}
}
function ModeSwitcher(container, modes, current, onSwitch) {
// available modes
var availableModes = {
code: {
'text': 'Code',
'title': 'Switch to code highlighter',
'click': function () {
switchMode('code')
onSwitch('code')
}
},
form: {
'text': 'Form',
'title': 'Switch to form editor',
'click': function () {
switchMode('form');
onSwitch('form');
}
},
text: {
'text': 'Text',
'title': 'Switch to plain text editor',
'click': function () {
switchMode('text');
onSwitch('text');
}
},
tree: {
'text': 'Tree',
'title': 'Switch to tree editor',
'click': function () {
switchMode('tree');
onSwitch('tree');
}
},
view: {
'text': 'View',
'title': 'Switch to tree view',
'click': function () {
switchMode('view');
onSwitch('view');
}
}
};
@ -7479,15 +7523,38 @@ return /******/ (function(modules) { // webpackBootstrap
menu.show(box);
};
var div = document.createElement('div');
div.className = 'jsoneditor-modes';
div.style.position = 'relative';
div.appendChild(box);
var frame = document.createElement('div');
frame.className = 'jsoneditor-modes';
frame.style.position = 'relative';
frame.appendChild(box);
return div;
container.appendChild(frame);
this.dom = {
container: container,
box: box,
frame: frame
};
}
exports.create = createModeSwitcher;
/**
* Set focus to switcher
*/
ModeSwitcher.prototype.focus = function () {
this.dom.box.focus();
};
/**
* Destroy the ModeSwitcher, remove from DOM
*/
ModeSwitcher.prototype.destroy = function () {
if (this.dom && this.dom.frame && this.dom.frame.parentNode) {
this.dom.frame.parentNode.removeChild(this.dom.frame);
}
this.dom = null;
};
module.exports = ModeSwitcher;
/***/ },

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

30
dist/jsoneditor.css vendored
View File

@ -47,11 +47,18 @@ div.jsoneditor-value.jsoneditor-empty::after {
content: "value";
}
div.jsoneditor-value.jsoneditor-url {
div.jsoneditor-value.jsoneditor-url,
a.jsoneditor-value.jsoneditor-url {
color: green;
text-decoration: underline;
}
a.jsoneditor-value.jsoneditor-url {
display: inline-block;
padding: 2px;
margin: 2px;
}
a.jsoneditor-value.jsoneditor-url:hover,
a.jsoneditor-value.jsoneditor-url:focus {
color: #ee422e;
@ -483,6 +490,9 @@ div.jsoneditor-contextmenu ul li button {
cursor: pointer;
color: #4d4d4d;
background: transparent;
font-size: 10pt;
font-family: arial, sans-serif;
box-sizing: border-box;
line-height: 26px;
text-align: left;
}
@ -809,10 +819,18 @@ table.jsoneditor-search div.jsoneditor-results {
/* For Firefox */
}
table.jsoneditor-search div.jsoneditor-results {
color: white;
padding-right: 5px;
line-height: 24px;
}
table.jsoneditor-search {
position: absolute;
right: 2px;
top: 2px;
right: 4px;
top: 4px;
border-collapse: collapse;
border-spacing: 0;
}
table.jsoneditor-search div.jsoneditor-frame {
@ -834,12 +852,6 @@ table.jsoneditor-search input {
line-height: 20px;
}
table.jsoneditor-search .jsoneditor-results {
color: #4d4d4d;
padding-right: 5px;
line-height: 24px;
}
table.jsoneditor-search button {
width: 16px;
height: 24px;

1715
dist/jsoneditor.js vendored

File diff suppressed because it is too large Load Diff

2
dist/jsoneditor.map vendored

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -6,7 +6,7 @@
<link href="../dist/jsoneditor.css" rel="stylesheet" type="text/css">
<script src="../dist/jsoneditor.js"></script>
<script src="http://bgrins.github.io/filereader.js"></script>
<script src="https://bgrins.github.io/filereader.js/filereader.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/2014-11-29/FileSaver.min.js"></script>
<style>

View File

@ -1,6 +1,6 @@
{
"name": "jsoneditor",
"version": "5.1.5",
"version": "5.2.0",
"main": "./index",
"description": "A web-based tool to view, edit, format, and validate JSON",
"tags": [

View File

@ -2121,10 +2121,6 @@ Node.prototype.onEvent = function (event) {
if (target == domValue) {
//noinspection FallthroughInSwitchStatementJS
switch (type) {
case 'focus':
this.editor.focusNode = this;
break;
case 'blur':
case 'change':
this._getDomValue(true);
@ -2174,10 +2170,6 @@ Node.prototype.onEvent = function (event) {
var domField = dom.field;
if (target == domField) {
switch (type) {
case 'focus':
this.editor.focusNode = this;
break;
case 'blur':
case 'change':
this._getDomField(true);

View File

@ -44,7 +44,7 @@ treemode.create = function (container, options) {
this.errorNodes = [];
this.node = null;
this.focusNode = null;
this.focusTarget = null;
this._setOptions(options);
@ -70,7 +70,7 @@ treemode.destroy = function () {
this.clear();
this.node = null;
this.focusNode = null;
this.focusTarget = null;
this.selection = null;
this.multiselection = null;
this.errorNodes = null;
@ -179,8 +179,8 @@ treemode.set = function (json, name) {
*/
treemode.get = function () {
// remove focus from currently edited node
if (this.focusNode) {
this.focusNode.blur();
if (this.focusTarget) {
this.focusTarget.blur();
}
if (this.node) {
@ -543,7 +543,7 @@ treemode.getSelection = function () {
}
return {
dom: this.dom.focus,
dom: this.focusTarget,
range: range,
nodes: this.multiselection.nodes.slice(0),
scrollTop: this.content ? this.content.scrollTop : 0
@ -764,7 +764,7 @@ treemode._onEvent = function (event) {
}
if (event.type == 'focus') {
this.dom.focus = event.target;
this.focusTarget = event.target;
}
if (event.type == 'mousedown') {
@ -1037,9 +1037,10 @@ treemode._onKeyDown = function (event) {
var handled = false;
if (keynum == 9) { // Tab or Shift+Tab
var me = this;
setTimeout(function () {
// select all text when moving focus to an editable div
util.selectContentEditable(this.dom.focus);
util.selectContentEditable(me.focusTarget);
}, 0);
}