examples load fix

This commit is contained in:
Ali Abid 2020-07-21 07:24:38 -07:00
parent d63eca24b7
commit 7934d8e27e
17 changed files with 2052 additions and 10 deletions

3
.gitignore vendored
View File

@ -19,4 +19,5 @@ __pycache__/
demo/models/*
dist/*
*.h5
docs.json
docs.json
*.bak

View File

@ -208,6 +208,95 @@ class KeyValues(AbstractOutput):
}
class HighlightedText(AbstractOutput):
'''
Component creates text that contains spans that are highlighted by category or numerical value.
Output is represent as a list of Tuple pairs, where the first element represents the span of text represented by the tuple, and the second element represents the category or value of the text.
Output type: List[Tuple[str, Union[float, str]]]
'''
def __init__(self, category_colors=None, label=None):
'''
Parameters:
category_colors (Dict[str, float]):
label (str): component name in interface.
'''
super().__init__(label)
def get_template_context(self):
return {
**super().get_template_context()
}
@classmethod
def get_shortcut_implementations(cls):
return {
"highlight": {},
}
def postprocess(self, prediction):
if isinstance(prediction, str) or isinstance(prediction, int) or isinstance(prediction, float):
return str(prediction)
else:
raise ValueError("The `Textbox` output interface expects an output that is one of: a string, or"
"an int/float that can be converted to a string.")
class JSON(AbstractOutput):
'''
Used for JSON output. Expects a JSON string or a Python dictionary or list that can be converted to JSON.
Output type: Union[str, Dict[str, Any], List[Any]]
'''
def __init__(self, label=None):
'''
Parameters:
label (str): component name in interface.
'''
super().__init__(label)
def postprocess(self, prediction):
if isinstance(prediction, dict) or isinstance(prediction, list):
return json.dumps(prediction)
elif isinstance(prediction, str):
return prediction
else:
raise ValueError("The `JSON` output interface expects an output that is a dictionary or list "
"or a preformatted JSON string.")
@classmethod
def get_shortcut_implementations(cls):
return {
"json": {},
}
class HTML(AbstractOutput):
'''
Used for HTML output. Expects a JSON string or a Python dictionary or list that can be converted to JSON.
Output type: str
'''
def __init__(self, label=None):
'''
Parameters:
label (str): component name in interface.
'''
super().__init__(label)
def postprocess(self, prediction):
if isinstance(prediction, str):
return prediction
else:
raise ValueError("The `HTML` output interface expects an output that is a str.")
@classmethod
def get_shortcut_implementations(cls):
return {
"html": {},
}
# Automatically adds all shortcut implementations in AbstractInput into a dictionary.
shortcuts = {}
for cls in AbstractOutput.__subclasses__():

View File

@ -65,6 +65,7 @@ button.secondary {
background-color: whitesmoke;
border-right: solid 4px whitesmoke;
border-left: solid 4px whitesmoke;
border-bottom: solid 4px whitesmoke;
}
#examples th {
padding: 8px 16px;

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="11" height="22"><defs><linearGradient id="a"><stop offset="0"/><stop offset="1" stop-opacity="0"/></linearGradient><radialGradient xlink:href="#a" cx="9.739" cy="9.716" fx="9.739" fy="9.716" r="3.709" gradientUnits="userSpaceOnUse"/></defs><g stroke="#000" fill="none"><g transform="translate(-129.5 -333.862) translate(0 .188)"><rect transform="matrix(.962 0 0 .971 4.943 11.548)" ry="2" rx="2" y="332.362" x="130" height="10.337" width="10.432" opacity=".5"/><g><path d="M132 339.175h6" opacity=".5"/><path d="M135 336.175v6" opacity=".5"/></g></g><g transform="translate(-129.5 -333.862)"><rect width="10.432" height="10.337" x="130" y="332.362" rx="2" ry="2" transform="matrix(.962 0 0 .971 4.943 22.736)" opacity=".5"/><path d="M132 350.362h6" opacity=".5"/></g></g></svg>

After

Width:  |  Height:  |  Size: 867 B

View File

@ -0,0 +1,107 @@
/*
* JSON Tree Viewer
* http://github.com/summerstyle/jsonTreeViewer
*
* Copyright 2017 Vera Lobacheva (http://iamvera.com)
* Released under the MIT license (LICENSE.txt)
*/
/* Background for the tree. May use for <body> element */
.jsontree_bg {
background: #FFF;
}
/* Styles for the container of the tree (e.g. fonts, margins etc.) */
.jsontree_tree {
margin-left: 30px;
font-family: 'PT Mono', monospace;
font-size: 14px;
}
/* Styles for a list of child nodes */
.jsontree_child-nodes {
display: none;
margin-left: 35px;
margin-bottom: 5px;
line-height: 2;
}
.jsontree_node_expanded > .jsontree_value-wrapper > .jsontree_value > .jsontree_child-nodes {
display: block;
}
/* Styles for labels */
.jsontree_label-wrapper {
float: left;
margin-right: 8px;
}
.jsontree_label {
font-weight: normal;
vertical-align: top;
color: #000;
position: relative;
padding: 1px;
border-radius: 4px;
cursor: default;
}
.jsontree_node_marked > .jsontree_label-wrapper > .jsontree_label {
background: #fff2aa;
}
/* Styles for values */
.jsontree_value-wrapper {
display: block;
overflow: hidden;
}
.jsontree_node_complex > .jsontree_value-wrapper {
overflow: inherit;
}
.jsontree_value {
vertical-align: top;
display: inline;
}
.jsontree_value_null {
color: #777;
font-weight: bold;
}
.jsontree_value_string {
color: #025900;
font-weight: bold;
}
.jsontree_value_number {
color: #000E59;
font-weight: bold;
}
.jsontree_value_boolean {
color: #600100;
font-weight: bold;
}
/* Styles for active elements */
.jsontree_expand-button {
position: absolute;
top: 3px;
left: -15px;
display: block;
width: 11px;
height: 11px;
background-image: url('icons.svg');
}
.jsontree_node_expanded > .jsontree_label-wrapper > .jsontree_label > .jsontree_expand-button {
background-position: 0 -11px;
}
.jsontree_show-more {
cursor: pointer;
}
.jsontree_node_expanded > .jsontree_value-wrapper > .jsontree_value > .jsontree_show-more {
display: none;
}
.jsontree_node_empty > .jsontree_label-wrapper > .jsontree_label > .jsontree_expand-button,
.jsontree_node_empty > .jsontree_value-wrapper > .jsontree_value > .jsontree_show-more {
display: none !important;
}
.jsontree_node_complex > .jsontree_label-wrapper > .jsontree_label {
cursor: pointer;
}
.jsontree_node_empty > .jsontree_label-wrapper > .jsontree_label {
cursor: default !important;
}

View File

@ -23,5 +23,6 @@ const dropdown = {
load_example: function(data) {
let child = this.choices.indexOf(data) + 1;
this.target.find("option:nth-child(" + child + ")").prop("selected", true);
this.target.find(".dropdown").selectmenu("refresh");
}
}

View File

@ -38,7 +38,7 @@ const slider = {
this.target.find("input").val(this.default);
},
load_example: function(data) {
this.target.find("input").val(data);
this.target.find(".value").text(data);
this.target.find(".slider").slider("option", "value", data)
this.target.find(".ui-slider-handle").text(data);
}
}

View File

@ -0,0 +1,819 @@
/**
* JSON Tree library (a part of jsonTreeViewer)
* http://github.com/summerstyle/jsonTreeViewer
*
* Copyright 2017 Vera Lobacheva (http://iamvera.com)
* Released under the MIT license (LICENSE.txt)
*/
var jsonTree = (function() {
/* ---------- Utilities ---------- */
var utils = {
/*
* Returns js-"class" of value
*
* @param val {any type} - value
* @returns {string} - for example, "[object Function]"
*/
getClass : function(val) {
return Object.prototype.toString.call(val);
},
/**
* Checks for a type of value (for valid JSON data types).
* In other cases - throws an exception
*
* @param val {any type} - the value for new node
* @returns {string} ("object" | "array" | "null" | "boolean" | "number" | "string")
*/
getType : function(val) {
if (val === null) {
return 'null';
}
switch (typeof val) {
case 'number':
return 'number';
case 'string':
return 'string';
case 'boolean':
return 'boolean';
}
switch(utils.getClass(val)) {
case '[object Array]':
return 'array';
case '[object Object]':
return 'object';
}
throw new Error('Bad type: ' + utils.getClass(val));
},
/**
* Applies for each item of list some function
* and checks for last element of the list
*
* @param obj {Object | Array} - a list or a dict with child nodes
* @param func {Function} - the function for each item
*/
forEachNode : function(obj, func) {
var type = utils.getType(obj),
isLast;
switch (type) {
case 'array':
isLast = obj.length - 1;
obj.forEach(function(item, i) {
func(i, item, i === isLast);
});
break;
case 'object':
var keys = Object.keys(obj).sort();
isLast = keys.length - 1;
keys.forEach(function(item, i) {
func(item, obj[item], i === isLast);
});
break;
}
},
/**
* Implements the kind of an inheritance by
* using parent prototype and
* creating intermediate constructor
*
* @param Child {Function} - a child constructor
* @param Parent {Function} - a parent constructor
*/
inherits : (function() {
var F = function() {};
return function(Child, Parent) {
F.prototype = Parent.prototype;
Child.prototype = new F();
Child.prototype.constructor = Child;
};
})(),
/*
* Checks for a valid type of root node*
*
* @param {any type} jsonObj - a value for root node
* @returns {boolean} - true for an object or an array, false otherwise
*/
isValidRoot : function(jsonObj) {
switch (utils.getType(jsonObj)) {
case 'object':
case 'array':
return true;
default:
return false;
}
},
/**
* Extends some object
*/
extend : function(targetObj, sourceObj) {
for (var prop in sourceObj) {
if (sourceObj.hasOwnProperty(prop)) {
targetObj[prop] = sourceObj[prop];
}
}
}
};
/* ---------- Node constructors ---------- */
/**
* The factory for creating nodes of defined type.
*
* ~~~ Node ~~~ is a structure element of an onject or an array
* with own label (a key of an object or an index of an array)
* and value of any json data type. The root object or array
* is a node without label.
* {...
* [+] "label": value,
* ...}
*
* Markup:
* <li class="jsontree_node [jsontree_node_expanded]">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">
* <span class="jsontree_expand-button" />
* "label"
* </span>
* :
* </span>
* <(div|span) class="jsontree_value jsontree_value_(object|array|boolean|null|number|string)">
* ...
* </(div|span)>
* </li>
*
* @param label {string} - key name
* @param val {Object | Array | string | number | boolean | null} - a value of node
* @param isLast {boolean} - true if node is last in list of siblings
*
* @return {Node}
*/
function Node(label, val, isLast) {
var nodeType = utils.getType(val);
if (nodeType in Node.CONSTRUCTORS) {
return new Node.CONSTRUCTORS[nodeType](label, val, isLast);
} else {
throw new Error('Bad type: ' + utils.getClass(val));
}
}
Node.CONSTRUCTORS = {
'boolean' : NodeBoolean,
'number' : NodeNumber,
'string' : NodeString,
'null' : NodeNull,
'object' : NodeObject,
'array' : NodeArray
};
/*
* The constructor for simple types (string, number, boolean, null)
* {...
* [+] "label": value,
* ...}
* value = string || number || boolean || null
*
* Markup:
* <li class="jsontree_node">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">"age"</span>
* :
* </span>
* <span class="jsontree_value jsontree_value_(number|boolean|string|null)">25</span>
* ,
* </li>
*
* @abstract
* @param label {string} - key name
* @param val {string | number | boolean | null} - a value of simple types
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function _NodeSimple(label, val, isLast) {
if (this.constructor === _NodeSimple) {
throw new Error('This is abstract class');
}
var self = this,
el = document.createElement('li'),
labelEl,
template = function(label, val) {
var str = '\
<span class="jsontree_label-wrapper">\
<span class="jsontree_label">"' +
label +
'"</span> : \
</span>\
<span class="jsontree_value-wrapper">\
<span class="jsontree_value jsontree_value_' + self.type + '">' +
val +
'</span>' +
(!isLast ? ',' : '') +
'</span>';
return str;
};
self.label = label;
self.isComplex = false;
el.classList.add('jsontree_node');
el.innerHTML = template(label, val);
self.el = el;
labelEl = el.querySelector('.jsontree_label');
labelEl.addEventListener('click', function(e) {
if (e.altKey) {
self.toggleMarked();
return;
}
if (e.shiftKey) {
document.getSelection().removeAllRanges();
alert(self.getJSONPath());
return;
}
}, false);
}
_NodeSimple.prototype = {
constructor : _NodeSimple,
/**
* Mark node
*/
mark : function() {
this.el.classList.add('jsontree_node_marked');
},
/**
* Unmark node
*/
unmark : function() {
this.el.classList.remove('jsontree_node_marked');
},
/**
* Mark or unmark node
*/
toggleMarked : function() {
this.el.classList.toggle('jsontree_node_marked');
},
/**
* Expands parent node of this node
*
* @param isRecursive {boolean} - if true, expands all parent nodes
* (from node to root)
*/
expandParent : function(isRecursive) {
if (!this.parent) {
return;
}
this.parent.expand();
this.parent.expandParent(isRecursive);
},
/**
* Returns JSON-path of this
*
* @param isInDotNotation {boolean} - kind of notation for returned json-path
* (by default, in bracket notation)
* @returns {string}
*/
getJSONPath : function(isInDotNotation) {
if (this.isRoot) {
return "$";
}
var currentPath;
if (this.parent.type === 'array') {
currentPath = "[" + this.label + "]";
} else {
currentPath = isInDotNotation ? "." + this.label : "['" + this.label + "']";
}
return this.parent.getJSONPath(isInDotNotation) + currentPath;
}
};
/*
* The constructor for boolean values
* {...
* [+] "label": boolean,
* ...}
* boolean = true || false
*
* @constructor
* @param label {string} - key name
* @param val {boolean} - value of boolean type, true or false
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeBoolean(label, val, isLast) {
this.type = "boolean";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeBoolean,_NodeSimple);
/*
* The constructor for number values
* {...
* [+] "label": number,
* ...}
* number = 123
*
* @constructor
* @param label {string} - key name
* @param val {number} - value of number type, for example 123
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeNumber(label, val, isLast) {
this.type = "number";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeNumber,_NodeSimple);
/*
* The constructor for string values
* {...
* [+] "label": string,
* ...}
* string = "abc"
*
* @constructor
* @param label {string} - key name
* @param val {string} - value of string type, for example "abc"
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeString(label, val, isLast) {
this.type = "string";
_NodeSimple.call(this, label, '"' + val + '"', isLast);
}
utils.inherits(NodeString,_NodeSimple);
/*
* The constructor for null values
* {...
* [+] "label": null,
* ...}
*
* @constructor
* @param label {string} - key name
* @param val {null} - value (only null)
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeNull(label, val, isLast) {
this.type = "null";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeNull,_NodeSimple);
/*
* The constructor for complex types (object, array)
* {...
* [+] "label": value,
* ...}
* value = object || array
*
* Markup:
* <li class="jsontree_node jsontree_node_(object|array) [expanded]">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">
* <span class="jsontree_expand-button" />
* "label"
* </span>
* :
* </span>
* <div class="jsontree_value">
* <b>{</b>
* <ul class="jsontree_child-nodes" />
* <b>}</b>
* ,
* </div>
* </li>
*
* @abstract
* @param label {string} - key name
* @param val {Object | Array} - a value of complex types, object or array
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function _NodeComplex(label, val, isLast) {
if (this.constructor === _NodeComplex) {
throw new Error('This is abstract class');
}
var self = this,
el = document.createElement('li'),
template = function(label, sym) {
var comma = (!isLast) ? ',' : '',
str = '\
<div class="jsontree_value-wrapper">\
<div class="jsontree_value jsontree_value_' + self.type + '">\
<b>' + sym[0] + '</b>\
<span class="jsontree_show-more">&hellip;</span>\
<ul class="jsontree_child-nodes"></ul>\
<b>' + sym[1] + '</b>' +
'</div>' + comma +
'</div>';
if (label !== null) {
str = '\
<span class="jsontree_label-wrapper">\
<span class="jsontree_label">' +
'<span class="jsontree_expand-button"></span>' +
'"' + label +
'"</span> : \
</span>' + str;
}
return str;
},
childNodesUl,
labelEl,
moreContentEl,
childNodes = [];
self.label = label;
self.isComplex = true;
el.classList.add('jsontree_node');
el.classList.add('jsontree_node_complex');
el.innerHTML = template(label, self.sym);
childNodesUl = el.querySelector('.jsontree_child-nodes');
if (label !== null) {
labelEl = el.querySelector('.jsontree_label');
moreContentEl = el.querySelector('.jsontree_show-more');
labelEl.addEventListener('click', function(e) {
if (e.altKey) {
self.toggleMarked();
return;
}
if (e.shiftKey) {
document.getSelection().removeAllRanges();
alert(self.getJSONPath());
return;
}
self.toggle(e.ctrlKey || e.metaKey);
}, false);
moreContentEl.addEventListener('click', function(e) {
self.toggle(e.ctrlKey || e.metaKey);
}, false);
self.isRoot = false;
} else {
self.isRoot = true;
self.parent = null;
el.classList.add('jsontree_node_expanded');
}
self.el = el;
self.childNodes = childNodes;
self.childNodesUl = childNodesUl;
utils.forEachNode(val, function(label, node, isLast) {
self.addChild(new Node(label, node, isLast));
});
self.isEmpty = !Boolean(childNodes.length);
if (self.isEmpty) {
el.classList.add('jsontree_node_empty');
}
}
utils.inherits(_NodeComplex, _NodeSimple);
utils.extend(_NodeComplex.prototype, {
constructor : _NodeComplex,
/*
* Add child node to list of child nodes
*
* @param child {Node} - child node
*/
addChild : function(child) {
this.childNodes.push(child);
this.childNodesUl.appendChild(child.el);
child.parent = this;
},
/*
* Expands this list of node child nodes
*
* @param isRecursive {boolean} - if true, expands all child nodes
*/
expand : function(isRecursive){
if (this.isEmpty) {
return;
}
if (!this.isRoot) {
this.el.classList.add('jsontree_node_expanded');
}
if (isRecursive) {
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item.expand(isRecursive);
}
});
}
},
/*
* Collapses this list of node child nodes
*
* @param isRecursive {boolean} - if true, collapses all child nodes
*/
collapse : function(isRecursive) {
if (this.isEmpty) {
return;
}
if (!this.isRoot) {
this.el.classList.remove('jsontree_node_expanded');
}
if (isRecursive) {
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item.collapse(isRecursive);
}
});
}
},
/*
* Expands collapsed or collapses expanded node
*
* @param {boolean} isRecursive - Expand all child nodes if this node is expanded
* and collapse it otherwise
*/
toggle : function(isRecursive) {
if (this.isEmpty) {
return;
}
this.el.classList.toggle('jsontree_node_expanded');
if (isRecursive) {
var isExpanded = this.el.classList.contains('jsontree_node_expanded');
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item[isExpanded ? 'expand' : 'collapse'](isRecursive);
}
});
}
},
/**
* Find child nodes that match some conditions and handle it
*
* @param {Function} matcher
* @param {Function} handler
* @param {boolean} isRecursive
*/
findChildren : function(matcher, handler, isRecursive) {
if (this.isEmpty) {
return;
}
this.childNodes.forEach(function(item, i) {
if (matcher(item)) {
handler(item);
}
if (item.isComplex && isRecursive) {
item.findChildren(matcher, handler, isRecursive);
}
});
}
});
/*
* The constructor for object values
* {...
* [+] "label": object,
* ...}
* object = {"abc": "def"}
*
* @constructor
* @param label {string} - key name
* @param val {Object} - value of object type, {"abc": "def"}
* @param isLast {boolean} - true if node is last in list of siblings
*/
function NodeObject(label, val, isLast) {
this.sym = ['{', '}'];
this.type = "object";
_NodeComplex.call(this, label, val, isLast);
}
utils.inherits(NodeObject,_NodeComplex);
/*
* The constructor for array values
* {...
* [+] "label": array,
* ...}
* array = [1,2,3]
*
* @constructor
* @param label {string} - key name
* @param val {Array} - value of array type, [1,2,3]
* @param isLast {boolean} - true if node is last in list of siblings
*/
function NodeArray(label, val, isLast) {
this.sym = ['[', ']'];
this.type = "array";
_NodeComplex.call(this, label, val, isLast);
}
utils.inherits(NodeArray, _NodeComplex);
/* ---------- The tree constructor ---------- */
/*
* The constructor for json tree.
* It contains only one Node (Array or Object), without property name.
* CSS-styles of .tree define main tree styles like font-family,
* font-size and own margins.
*
* Markup:
* <ul class="jsontree_tree clearfix">
* {Node}
* </ul>
*
* @constructor
* @param jsonObj {Object | Array} - data for tree
* @param domEl {DOMElement} - DOM-element, wrapper for tree
*/
function Tree(jsonObj, domEl) {
this.wrapper = document.createElement('ul');
this.wrapper.className = 'jsontree_tree clearfix';
this.rootNode = null;
this.sourceJSONObj = jsonObj;
this.loadData(jsonObj);
this.appendTo(domEl);
}
Tree.prototype = {
constructor : Tree,
/**
* Fill new data in current json tree
*
* @param {Object | Array} jsonObj - json-data
*/
loadData : function(jsonObj) {
if (!utils.isValidRoot(jsonObj)) {
alert('The root should be an object or an array');
return;
}
this.sourceJSONObj = jsonObj;
this.rootNode = new Node(null, jsonObj, 'last');
this.wrapper.innerHTML = '';
this.wrapper.appendChild(this.rootNode.el);
},
/**
* Appends tree to DOM-element (or move it to new place)
*
* @param {DOMElement} domEl
*/
appendTo : function(domEl) {
domEl.appendChild(this.wrapper);
},
/**
* Expands all tree nodes (objects or arrays) recursively
*
* @param {Function} filterFunc - 'true' if this node should be expanded
*/
expand : function(filterFunc) {
if (this.rootNode.isComplex) {
if (typeof filterFunc == 'function') {
this.rootNode.childNodes.forEach(function(item, i) {
if (item.isComplex && filterFunc(item)) {
item.expand();
}
});
} else {
this.rootNode.expand('recursive');
}
}
},
/**
* Collapses all tree nodes (objects or arrays) recursively
*/
collapse : function() {
if (typeof this.rootNode.collapse === 'function') {
this.rootNode.collapse('recursive');
}
},
/**
* Returns the source json-string (pretty-printed)
*
* @param {boolean} isPrettyPrinted - 'true' for pretty-printed string
* @returns {string} - for exemple, '{"a":2,"b":3}'
*/
toSourceJSON : function(isPrettyPrinted) {
if (!isPrettyPrinted) {
return JSON.stringify(this.sourceJSONObj);
}
var DELIMETER = "[%^$#$%^%]",
jsonStr = JSON.stringify(this.sourceJSONObj, null, DELIMETER);
jsonStr = jsonStr.split("\n").join("<br />");
jsonStr = jsonStr.split(DELIMETER).join("&nbsp;&nbsp;&nbsp;&nbsp;");
return jsonStr;
},
/**
* Find all nodes that match some conditions and handle it
*/
findAndHandle : function(matcher, handler) {
this.rootNode.findChildren(matcher, handler, 'isRecursive');
},
/**
* Unmark all nodes
*/
unmarkAll : function() {
this.rootNode.findChildren(function(node) {
return true;
}, function(node) {
node.unmark();
}, 'isRecursive');
}
};
/* ---------- Public methods ---------- */
return {
/**
* Creates new tree by data and appends it to the DOM-element
*
* @param jsonObj {Object | Array} - json-data
* @param domEl {DOMElement} - the wrapper element
* @returns {Tree}
*/
create : function(jsonObj, domEl) {
return new Tree(jsonObj, domEl);
}
};
})();

View File

@ -12,13 +12,15 @@ def flip2(image):
start = time()
return np.fliplr(image)
def flip10(i1, i2, i3, i4, i5):
return i1 + i2
gr.Interface(flip,
gr.inputs.Image(),
gr.Interface(flip10,
["image"] * 5,
["image"],
examples=[
["images/cheetah1.jpg"],
["images/cheetah2.jpg"],
["images/lion.jpg"],
["images/cheetah1.jpg"] * 5,
["images/cheetah2.jpg"] * 5,
["images/lion.jpg"] * 5,
]
).launch()

View File

@ -33,7 +33,9 @@ gradio/static/css/interfaces/output/image.css
gradio/static/css/interfaces/output/key_values.css
gradio/static/css/interfaces/output/label.css
gradio/static/css/interfaces/output/textbox.css
gradio/static/css/vendor/icons.svg
gradio/static/css/vendor/jquery-ui.css
gradio/static/css/vendor/jsonTree.css
gradio/static/css/vendor/tui-color-picker.css
gradio/static/css/vendor/tui-image-editor.css
gradio/static/css/vendor/images/ui-bg_flat_0_aaaaaa_40x100.png
@ -81,6 +83,7 @@ gradio/static/js/vendor/html2canvas.min.js
gradio/static/js/vendor/jquery-ui.min.js
gradio/static/js/vendor/jquery.min.js
gradio/static/js/vendor/jquery.ui.touch-punch.js
gradio/static/js/vendor/jsonTree.js
gradio/static/js/vendor/p5.dom.min.js
gradio/static/js/vendor/p5.min.js
gradio/static/js/vendor/p5.sound.min.js

View File

@ -208,6 +208,95 @@ class KeyValues(AbstractOutput):
}
class HighlightedText(AbstractOutput):
'''
Component creates text that contains spans that are highlighted by category or numerical value.
Output is represent as a list of Tuple pairs, where the first element represents the span of text represented by the tuple, and the second element represents the category or value of the text.
Output type: List[Tuple[str, Union[float, str]]]
'''
def __init__(self, category_colors=None, label=None):
'''
Parameters:
category_colors (Dict[str, float]):
label (str): component name in interface.
'''
super().__init__(label)
def get_template_context(self):
return {
**super().get_template_context()
}
@classmethod
def get_shortcut_implementations(cls):
return {
"highlight": {},
}
def postprocess(self, prediction):
if isinstance(prediction, str) or isinstance(prediction, int) or isinstance(prediction, float):
return str(prediction)
else:
raise ValueError("The `Textbox` output interface expects an output that is one of: a string, or"
"an int/float that can be converted to a string.")
class JSON(AbstractOutput):
'''
Used for JSON output. Expects a JSON string or a Python dictionary or list that can be converted to JSON.
Output type: Union[str, Dict[str, Any], List[Any]]
'''
def __init__(self, label=None):
'''
Parameters:
label (str): component name in interface.
'''
super().__init__(label)
def postprocess(self, prediction):
if isinstance(prediction, dict) or isinstance(prediction, list):
return json.dumps(prediction)
elif isinstance(prediction, str):
return prediction
else:
raise ValueError("The `JSON` output interface expects an output that is a dictionary or list "
"or a preformatted JSON string.")
@classmethod
def get_shortcut_implementations(cls):
return {
"json": {},
}
class HTML(AbstractOutput):
'''
Used for HTML output. Expects a JSON string or a Python dictionary or list that can be converted to JSON.
Output type: str
'''
def __init__(self, label=None):
'''
Parameters:
label (str): component name in interface.
'''
super().__init__(label)
def postprocess(self, prediction):
if isinstance(prediction, str):
return prediction
else:
raise ValueError("The `HTML` output interface expects an output that is a str.")
@classmethod
def get_shortcut_implementations(cls):
return {
"html": {},
}
# Automatically adds all shortcut implementations in AbstractInput into a dictionary.
shortcuts = {}
for cls in AbstractOutput.__subclasses__():

View File

@ -65,6 +65,7 @@ button.secondary {
background-color: whitesmoke;
border-right: solid 4px whitesmoke;
border-left: solid 4px whitesmoke;
border-bottom: solid 4px whitesmoke;
}
#examples th {
padding: 8px 16px;

1
gradio/static/css/vendor/icons.svg vendored Normal file
View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="11" height="22"><defs><linearGradient id="a"><stop offset="0"/><stop offset="1" stop-opacity="0"/></linearGradient><radialGradient xlink:href="#a" cx="9.739" cy="9.716" fx="9.739" fy="9.716" r="3.709" gradientUnits="userSpaceOnUse"/></defs><g stroke="#000" fill="none"><g transform="translate(-129.5 -333.862) translate(0 .188)"><rect transform="matrix(.962 0 0 .971 4.943 11.548)" ry="2" rx="2" y="332.362" x="130" height="10.337" width="10.432" opacity=".5"/><g><path d="M132 339.175h6" opacity=".5"/><path d="M135 336.175v6" opacity=".5"/></g></g><g transform="translate(-129.5 -333.862)"><rect width="10.432" height="10.337" x="130" y="332.362" rx="2" ry="2" transform="matrix(.962 0 0 .971 4.943 22.736)" opacity=".5"/><path d="M132 350.362h6" opacity=".5"/></g></g></svg>

After

Width:  |  Height:  |  Size: 867 B

107
gradio/static/css/vendor/jsonTree.css vendored Normal file
View File

@ -0,0 +1,107 @@
/*
* JSON Tree Viewer
* http://github.com/summerstyle/jsonTreeViewer
*
* Copyright 2017 Vera Lobacheva (http://iamvera.com)
* Released under the MIT license (LICENSE.txt)
*/
/* Background for the tree. May use for <body> element */
.jsontree_bg {
background: #FFF;
}
/* Styles for the container of the tree (e.g. fonts, margins etc.) */
.jsontree_tree {
margin-left: 30px;
font-family: 'PT Mono', monospace;
font-size: 14px;
}
/* Styles for a list of child nodes */
.jsontree_child-nodes {
display: none;
margin-left: 35px;
margin-bottom: 5px;
line-height: 2;
}
.jsontree_node_expanded > .jsontree_value-wrapper > .jsontree_value > .jsontree_child-nodes {
display: block;
}
/* Styles for labels */
.jsontree_label-wrapper {
float: left;
margin-right: 8px;
}
.jsontree_label {
font-weight: normal;
vertical-align: top;
color: #000;
position: relative;
padding: 1px;
border-radius: 4px;
cursor: default;
}
.jsontree_node_marked > .jsontree_label-wrapper > .jsontree_label {
background: #fff2aa;
}
/* Styles for values */
.jsontree_value-wrapper {
display: block;
overflow: hidden;
}
.jsontree_node_complex > .jsontree_value-wrapper {
overflow: inherit;
}
.jsontree_value {
vertical-align: top;
display: inline;
}
.jsontree_value_null {
color: #777;
font-weight: bold;
}
.jsontree_value_string {
color: #025900;
font-weight: bold;
}
.jsontree_value_number {
color: #000E59;
font-weight: bold;
}
.jsontree_value_boolean {
color: #600100;
font-weight: bold;
}
/* Styles for active elements */
.jsontree_expand-button {
position: absolute;
top: 3px;
left: -15px;
display: block;
width: 11px;
height: 11px;
background-image: url('icons.svg');
}
.jsontree_node_expanded > .jsontree_label-wrapper > .jsontree_label > .jsontree_expand-button {
background-position: 0 -11px;
}
.jsontree_show-more {
cursor: pointer;
}
.jsontree_node_expanded > .jsontree_value-wrapper > .jsontree_value > .jsontree_show-more {
display: none;
}
.jsontree_node_empty > .jsontree_label-wrapper > .jsontree_label > .jsontree_expand-button,
.jsontree_node_empty > .jsontree_value-wrapper > .jsontree_value > .jsontree_show-more {
display: none !important;
}
.jsontree_node_complex > .jsontree_label-wrapper > .jsontree_label {
cursor: pointer;
}
.jsontree_node_empty > .jsontree_label-wrapper > .jsontree_label {
cursor: default !important;
}

View File

@ -23,5 +23,6 @@ const dropdown = {
load_example: function(data) {
let child = this.choices.indexOf(data) + 1;
this.target.find("option:nth-child(" + child + ")").prop("selected", true);
this.target.find(".dropdown").selectmenu("refresh");
}
}

View File

@ -38,7 +38,7 @@ const slider = {
this.target.find("input").val(this.default);
},
load_example: function(data) {
this.target.find("input").val(data);
this.target.find(".value").text(data);
this.target.find(".slider").slider("option", "value", data)
this.target.find(".ui-slider-handle").text(data);
}
}

819
gradio/static/js/vendor/jsonTree.js vendored Normal file
View File

@ -0,0 +1,819 @@
/**
* JSON Tree library (a part of jsonTreeViewer)
* http://github.com/summerstyle/jsonTreeViewer
*
* Copyright 2017 Vera Lobacheva (http://iamvera.com)
* Released under the MIT license (LICENSE.txt)
*/
var jsonTree = (function() {
/* ---------- Utilities ---------- */
var utils = {
/*
* Returns js-"class" of value
*
* @param val {any type} - value
* @returns {string} - for example, "[object Function]"
*/
getClass : function(val) {
return Object.prototype.toString.call(val);
},
/**
* Checks for a type of value (for valid JSON data types).
* In other cases - throws an exception
*
* @param val {any type} - the value for new node
* @returns {string} ("object" | "array" | "null" | "boolean" | "number" | "string")
*/
getType : function(val) {
if (val === null) {
return 'null';
}
switch (typeof val) {
case 'number':
return 'number';
case 'string':
return 'string';
case 'boolean':
return 'boolean';
}
switch(utils.getClass(val)) {
case '[object Array]':
return 'array';
case '[object Object]':
return 'object';
}
throw new Error('Bad type: ' + utils.getClass(val));
},
/**
* Applies for each item of list some function
* and checks for last element of the list
*
* @param obj {Object | Array} - a list or a dict with child nodes
* @param func {Function} - the function for each item
*/
forEachNode : function(obj, func) {
var type = utils.getType(obj),
isLast;
switch (type) {
case 'array':
isLast = obj.length - 1;
obj.forEach(function(item, i) {
func(i, item, i === isLast);
});
break;
case 'object':
var keys = Object.keys(obj).sort();
isLast = keys.length - 1;
keys.forEach(function(item, i) {
func(item, obj[item], i === isLast);
});
break;
}
},
/**
* Implements the kind of an inheritance by
* using parent prototype and
* creating intermediate constructor
*
* @param Child {Function} - a child constructor
* @param Parent {Function} - a parent constructor
*/
inherits : (function() {
var F = function() {};
return function(Child, Parent) {
F.prototype = Parent.prototype;
Child.prototype = new F();
Child.prototype.constructor = Child;
};
})(),
/*
* Checks for a valid type of root node*
*
* @param {any type} jsonObj - a value for root node
* @returns {boolean} - true for an object or an array, false otherwise
*/
isValidRoot : function(jsonObj) {
switch (utils.getType(jsonObj)) {
case 'object':
case 'array':
return true;
default:
return false;
}
},
/**
* Extends some object
*/
extend : function(targetObj, sourceObj) {
for (var prop in sourceObj) {
if (sourceObj.hasOwnProperty(prop)) {
targetObj[prop] = sourceObj[prop];
}
}
}
};
/* ---------- Node constructors ---------- */
/**
* The factory for creating nodes of defined type.
*
* ~~~ Node ~~~ is a structure element of an onject or an array
* with own label (a key of an object or an index of an array)
* and value of any json data type. The root object or array
* is a node without label.
* {...
* [+] "label": value,
* ...}
*
* Markup:
* <li class="jsontree_node [jsontree_node_expanded]">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">
* <span class="jsontree_expand-button" />
* "label"
* </span>
* :
* </span>
* <(div|span) class="jsontree_value jsontree_value_(object|array|boolean|null|number|string)">
* ...
* </(div|span)>
* </li>
*
* @param label {string} - key name
* @param val {Object | Array | string | number | boolean | null} - a value of node
* @param isLast {boolean} - true if node is last in list of siblings
*
* @return {Node}
*/
function Node(label, val, isLast) {
var nodeType = utils.getType(val);
if (nodeType in Node.CONSTRUCTORS) {
return new Node.CONSTRUCTORS[nodeType](label, val, isLast);
} else {
throw new Error('Bad type: ' + utils.getClass(val));
}
}
Node.CONSTRUCTORS = {
'boolean' : NodeBoolean,
'number' : NodeNumber,
'string' : NodeString,
'null' : NodeNull,
'object' : NodeObject,
'array' : NodeArray
};
/*
* The constructor for simple types (string, number, boolean, null)
* {...
* [+] "label": value,
* ...}
* value = string || number || boolean || null
*
* Markup:
* <li class="jsontree_node">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">"age"</span>
* :
* </span>
* <span class="jsontree_value jsontree_value_(number|boolean|string|null)">25</span>
* ,
* </li>
*
* @abstract
* @param label {string} - key name
* @param val {string | number | boolean | null} - a value of simple types
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function _NodeSimple(label, val, isLast) {
if (this.constructor === _NodeSimple) {
throw new Error('This is abstract class');
}
var self = this,
el = document.createElement('li'),
labelEl,
template = function(label, val) {
var str = '\
<span class="jsontree_label-wrapper">\
<span class="jsontree_label">"' +
label +
'"</span> : \
</span>\
<span class="jsontree_value-wrapper">\
<span class="jsontree_value jsontree_value_' + self.type + '">' +
val +
'</span>' +
(!isLast ? ',' : '') +
'</span>';
return str;
};
self.label = label;
self.isComplex = false;
el.classList.add('jsontree_node');
el.innerHTML = template(label, val);
self.el = el;
labelEl = el.querySelector('.jsontree_label');
labelEl.addEventListener('click', function(e) {
if (e.altKey) {
self.toggleMarked();
return;
}
if (e.shiftKey) {
document.getSelection().removeAllRanges();
alert(self.getJSONPath());
return;
}
}, false);
}
_NodeSimple.prototype = {
constructor : _NodeSimple,
/**
* Mark node
*/
mark : function() {
this.el.classList.add('jsontree_node_marked');
},
/**
* Unmark node
*/
unmark : function() {
this.el.classList.remove('jsontree_node_marked');
},
/**
* Mark or unmark node
*/
toggleMarked : function() {
this.el.classList.toggle('jsontree_node_marked');
},
/**
* Expands parent node of this node
*
* @param isRecursive {boolean} - if true, expands all parent nodes
* (from node to root)
*/
expandParent : function(isRecursive) {
if (!this.parent) {
return;
}
this.parent.expand();
this.parent.expandParent(isRecursive);
},
/**
* Returns JSON-path of this
*
* @param isInDotNotation {boolean} - kind of notation for returned json-path
* (by default, in bracket notation)
* @returns {string}
*/
getJSONPath : function(isInDotNotation) {
if (this.isRoot) {
return "$";
}
var currentPath;
if (this.parent.type === 'array') {
currentPath = "[" + this.label + "]";
} else {
currentPath = isInDotNotation ? "." + this.label : "['" + this.label + "']";
}
return this.parent.getJSONPath(isInDotNotation) + currentPath;
}
};
/*
* The constructor for boolean values
* {...
* [+] "label": boolean,
* ...}
* boolean = true || false
*
* @constructor
* @param label {string} - key name
* @param val {boolean} - value of boolean type, true or false
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeBoolean(label, val, isLast) {
this.type = "boolean";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeBoolean,_NodeSimple);
/*
* The constructor for number values
* {...
* [+] "label": number,
* ...}
* number = 123
*
* @constructor
* @param label {string} - key name
* @param val {number} - value of number type, for example 123
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeNumber(label, val, isLast) {
this.type = "number";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeNumber,_NodeSimple);
/*
* The constructor for string values
* {...
* [+] "label": string,
* ...}
* string = "abc"
*
* @constructor
* @param label {string} - key name
* @param val {string} - value of string type, for example "abc"
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeString(label, val, isLast) {
this.type = "string";
_NodeSimple.call(this, label, '"' + val + '"', isLast);
}
utils.inherits(NodeString,_NodeSimple);
/*
* The constructor for null values
* {...
* [+] "label": null,
* ...}
*
* @constructor
* @param label {string} - key name
* @param val {null} - value (only null)
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function NodeNull(label, val, isLast) {
this.type = "null";
_NodeSimple.call(this, label, val, isLast);
}
utils.inherits(NodeNull,_NodeSimple);
/*
* The constructor for complex types (object, array)
* {...
* [+] "label": value,
* ...}
* value = object || array
*
* Markup:
* <li class="jsontree_node jsontree_node_(object|array) [expanded]">
* <span class="jsontree_label-wrapper">
* <span class="jsontree_label">
* <span class="jsontree_expand-button" />
* "label"
* </span>
* :
* </span>
* <div class="jsontree_value">
* <b>{</b>
* <ul class="jsontree_child-nodes" />
* <b>}</b>
* ,
* </div>
* </li>
*
* @abstract
* @param label {string} - key name
* @param val {Object | Array} - a value of complex types, object or array
* @param isLast {boolean} - true if node is last in list of parent childNodes
*/
function _NodeComplex(label, val, isLast) {
if (this.constructor === _NodeComplex) {
throw new Error('This is abstract class');
}
var self = this,
el = document.createElement('li'),
template = function(label, sym) {
var comma = (!isLast) ? ',' : '',
str = '\
<div class="jsontree_value-wrapper">\
<div class="jsontree_value jsontree_value_' + self.type + '">\
<b>' + sym[0] + '</b>\
<span class="jsontree_show-more">&hellip;</span>\
<ul class="jsontree_child-nodes"></ul>\
<b>' + sym[1] + '</b>' +
'</div>' + comma +
'</div>';
if (label !== null) {
str = '\
<span class="jsontree_label-wrapper">\
<span class="jsontree_label">' +
'<span class="jsontree_expand-button"></span>' +
'"' + label +
'"</span> : \
</span>' + str;
}
return str;
},
childNodesUl,
labelEl,
moreContentEl,
childNodes = [];
self.label = label;
self.isComplex = true;
el.classList.add('jsontree_node');
el.classList.add('jsontree_node_complex');
el.innerHTML = template(label, self.sym);
childNodesUl = el.querySelector('.jsontree_child-nodes');
if (label !== null) {
labelEl = el.querySelector('.jsontree_label');
moreContentEl = el.querySelector('.jsontree_show-more');
labelEl.addEventListener('click', function(e) {
if (e.altKey) {
self.toggleMarked();
return;
}
if (e.shiftKey) {
document.getSelection().removeAllRanges();
alert(self.getJSONPath());
return;
}
self.toggle(e.ctrlKey || e.metaKey);
}, false);
moreContentEl.addEventListener('click', function(e) {
self.toggle(e.ctrlKey || e.metaKey);
}, false);
self.isRoot = false;
} else {
self.isRoot = true;
self.parent = null;
el.classList.add('jsontree_node_expanded');
}
self.el = el;
self.childNodes = childNodes;
self.childNodesUl = childNodesUl;
utils.forEachNode(val, function(label, node, isLast) {
self.addChild(new Node(label, node, isLast));
});
self.isEmpty = !Boolean(childNodes.length);
if (self.isEmpty) {
el.classList.add('jsontree_node_empty');
}
}
utils.inherits(_NodeComplex, _NodeSimple);
utils.extend(_NodeComplex.prototype, {
constructor : _NodeComplex,
/*
* Add child node to list of child nodes
*
* @param child {Node} - child node
*/
addChild : function(child) {
this.childNodes.push(child);
this.childNodesUl.appendChild(child.el);
child.parent = this;
},
/*
* Expands this list of node child nodes
*
* @param isRecursive {boolean} - if true, expands all child nodes
*/
expand : function(isRecursive){
if (this.isEmpty) {
return;
}
if (!this.isRoot) {
this.el.classList.add('jsontree_node_expanded');
}
if (isRecursive) {
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item.expand(isRecursive);
}
});
}
},
/*
* Collapses this list of node child nodes
*
* @param isRecursive {boolean} - if true, collapses all child nodes
*/
collapse : function(isRecursive) {
if (this.isEmpty) {
return;
}
if (!this.isRoot) {
this.el.classList.remove('jsontree_node_expanded');
}
if (isRecursive) {
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item.collapse(isRecursive);
}
});
}
},
/*
* Expands collapsed or collapses expanded node
*
* @param {boolean} isRecursive - Expand all child nodes if this node is expanded
* and collapse it otherwise
*/
toggle : function(isRecursive) {
if (this.isEmpty) {
return;
}
this.el.classList.toggle('jsontree_node_expanded');
if (isRecursive) {
var isExpanded = this.el.classList.contains('jsontree_node_expanded');
this.childNodes.forEach(function(item, i) {
if (item.isComplex) {
item[isExpanded ? 'expand' : 'collapse'](isRecursive);
}
});
}
},
/**
* Find child nodes that match some conditions and handle it
*
* @param {Function} matcher
* @param {Function} handler
* @param {boolean} isRecursive
*/
findChildren : function(matcher, handler, isRecursive) {
if (this.isEmpty) {
return;
}
this.childNodes.forEach(function(item, i) {
if (matcher(item)) {
handler(item);
}
if (item.isComplex && isRecursive) {
item.findChildren(matcher, handler, isRecursive);
}
});
}
});
/*
* The constructor for object values
* {...
* [+] "label": object,
* ...}
* object = {"abc": "def"}
*
* @constructor
* @param label {string} - key name
* @param val {Object} - value of object type, {"abc": "def"}
* @param isLast {boolean} - true if node is last in list of siblings
*/
function NodeObject(label, val, isLast) {
this.sym = ['{', '}'];
this.type = "object";
_NodeComplex.call(this, label, val, isLast);
}
utils.inherits(NodeObject,_NodeComplex);
/*
* The constructor for array values
* {...
* [+] "label": array,
* ...}
* array = [1,2,3]
*
* @constructor
* @param label {string} - key name
* @param val {Array} - value of array type, [1,2,3]
* @param isLast {boolean} - true if node is last in list of siblings
*/
function NodeArray(label, val, isLast) {
this.sym = ['[', ']'];
this.type = "array";
_NodeComplex.call(this, label, val, isLast);
}
utils.inherits(NodeArray, _NodeComplex);
/* ---------- The tree constructor ---------- */
/*
* The constructor for json tree.
* It contains only one Node (Array or Object), without property name.
* CSS-styles of .tree define main tree styles like font-family,
* font-size and own margins.
*
* Markup:
* <ul class="jsontree_tree clearfix">
* {Node}
* </ul>
*
* @constructor
* @param jsonObj {Object | Array} - data for tree
* @param domEl {DOMElement} - DOM-element, wrapper for tree
*/
function Tree(jsonObj, domEl) {
this.wrapper = document.createElement('ul');
this.wrapper.className = 'jsontree_tree clearfix';
this.rootNode = null;
this.sourceJSONObj = jsonObj;
this.loadData(jsonObj);
this.appendTo(domEl);
}
Tree.prototype = {
constructor : Tree,
/**
* Fill new data in current json tree
*
* @param {Object | Array} jsonObj - json-data
*/
loadData : function(jsonObj) {
if (!utils.isValidRoot(jsonObj)) {
alert('The root should be an object or an array');
return;
}
this.sourceJSONObj = jsonObj;
this.rootNode = new Node(null, jsonObj, 'last');
this.wrapper.innerHTML = '';
this.wrapper.appendChild(this.rootNode.el);
},
/**
* Appends tree to DOM-element (or move it to new place)
*
* @param {DOMElement} domEl
*/
appendTo : function(domEl) {
domEl.appendChild(this.wrapper);
},
/**
* Expands all tree nodes (objects or arrays) recursively
*
* @param {Function} filterFunc - 'true' if this node should be expanded
*/
expand : function(filterFunc) {
if (this.rootNode.isComplex) {
if (typeof filterFunc == 'function') {
this.rootNode.childNodes.forEach(function(item, i) {
if (item.isComplex && filterFunc(item)) {
item.expand();
}
});
} else {
this.rootNode.expand('recursive');
}
}
},
/**
* Collapses all tree nodes (objects or arrays) recursively
*/
collapse : function() {
if (typeof this.rootNode.collapse === 'function') {
this.rootNode.collapse('recursive');
}
},
/**
* Returns the source json-string (pretty-printed)
*
* @param {boolean} isPrettyPrinted - 'true' for pretty-printed string
* @returns {string} - for exemple, '{"a":2,"b":3}'
*/
toSourceJSON : function(isPrettyPrinted) {
if (!isPrettyPrinted) {
return JSON.stringify(this.sourceJSONObj);
}
var DELIMETER = "[%^$#$%^%]",
jsonStr = JSON.stringify(this.sourceJSONObj, null, DELIMETER);
jsonStr = jsonStr.split("\n").join("<br />");
jsonStr = jsonStr.split(DELIMETER).join("&nbsp;&nbsp;&nbsp;&nbsp;");
return jsonStr;
},
/**
* Find all nodes that match some conditions and handle it
*/
findAndHandle : function(matcher, handler) {
this.rootNode.findChildren(matcher, handler, 'isRecursive');
},
/**
* Unmark all nodes
*/
unmarkAll : function() {
this.rootNode.findChildren(function(node) {
return true;
}, function(node) {
node.unmark();
}, 'isRecursive');
}
};
/* ---------- Public methods ---------- */
return {
/**
* Creates new tree by data and appends it to the DOM-element
*
* @param jsonObj {Object | Array} - json-data
* @param domEl {DOMElement} - the wrapper element
* @returns {Tree}
*/
create : function(jsonObj, domEl) {
return new Tree(jsonObj, domEl);
}
};
})();