From 89ec0a5f5437f4cee93dc2dbbe66efceffccc3c8 Mon Sep 17 00:00:00 2001 From: Shawn Murphy Date: Fri, 9 Aug 2019 13:50:12 +0200 Subject: [PATCH] remove the old decaffeinated .js from the build --- lib/huviz.js | 23008 ++++++++++++++++++++++++------------------------- 1 file changed, 11094 insertions(+), 11914 deletions(-) diff --git a/lib/huviz.js b/lib/huviz.js index 2c768675c..9f75e34e4 100644 --- a/lib/huviz.js +++ b/lib/huviz.js @@ -1461,5925 +1461,4747 @@ OnceRunner.prototype.makeWrapper = function(callback) { }; } return this.require.define; -}).call(this)({"angliciser": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS102: Remove unnecessary code created because of implicit returns - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ +}).call(this)({"angliciser": function(exports, require, module) {(function() { + var angliciser; + + angliciser = function(lst, and_or_or) { + var b, english, lstlen; + b = and_or_or; + and_or_or = (and_or_or == null) && " and " || and_or_or; + if ((b != null) && and_or_or !== b) { + throw "and_or_or failing " + b; + } + english = ""; + lstlen = lst.length; + lst.forEach((function(_this) { + return function(itm, i) { + if (lstlen > 1) { + if ((lstlen - 1) === i) { + english += and_or_or; + } else { + if (i > 0) { + english += ', '; + } + } + } + return english += itm; + }; + })(this)); + return english; + }; + (typeof exports !== "undefined" && exports !== null ? exports : this).angliciser = angliciser; -// angliciser(['a','b','c']) ==> "a, b and c" -// angliciser(['a','b']) ==> "a and b" -// angliciser(['a']) ==> "a"# -// angliciser([]) ==> "" +}).call(this); +}, "coloredtreepicker": function(exports, require, module) {(function() { + var ColoredTreePicker, L_emphasizing, L_showing, L_unshowing, S_all, TreePicker, verbose, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, + __hasProp = {}.hasOwnProperty, + __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; }; -const angliciser = function(lst, and_or_or) { - const b = and_or_or; - and_or_or = ((and_or_or == null) && " and ") || and_or_or; // uh really?! so one can pass in " or " - if ((b != null) && (and_or_or !== b)) { - throw `and_or_or failing ${b}`; - } - let english = ""; - //console.log lst - const lstlen = lst.length; - lst.forEach((itm,i) => { - //console.log english - if (lstlen > 1) { - if ((lstlen - 1) === i) { - english += and_or_or; - } else { - if (i > 0) { - english += ', '; - } - } - } - return english += itm; - }); - //console.log "'"+english+"'" - return english; -}; - -(typeof exports !== 'undefined' && exports !== null ? exports : this).angliciser = angliciser;}, "coloredtreepicker": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS001: Remove Babel/TypeScript constructor workaround - * DS101: Remove unnecessary use of Array.from - * DS102: Remove unnecessary code created because of implicit returns - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ + TreePicker = require('treepicker').TreePicker; -const { TreePicker } = require('treepicker'); -/* - * ColoredTreePicker is a widget for displaying and manipulating a hierarchy - * and displaying and manipulating the selectedness of branches and nodes. - * - * The terminology below is a bit screwy because the motivating hierarchy - * was a taxonomy controller which determined which nodes in a graph - * are 'shown' as selected. Perhaps better terminology would be to have - * 'shown' called 'marked' and 'unshown' called 'unmarked'. - * - * ▼ 0x25bc - * ▶ 0x25b6 - * - * Expanded Collapsed - * +-----------------+ +-----------------+ - * | parent ▼ | | parent ▶ | - * | +------------+| +-----------------+ - * | | child 1 || - * | +------------+| - * | | child 2 || - * | +------------+| - * +-----------------+ - * - * Clicking an expanded parent should cycle thru selection and deselection - * of only its direct instances, if there are any. - * - * Clicking a collapsed parent should cycle thru selection and deselection - * of its direct instances as well as those of all its children. - * - * The coloring of expanded parents cycles thru the three states: - * Mixed - some of the direct instances are selected - * On - all of the direct instances are selected - * Off - none of the direct instances are selected - * - * The coloring of a collapsed parent cycles thru the three states: - * Mixed - some descendant instances are selected (direct or indirect) - * On - all descendant instances are selected (direct or indirect) - * Off - no descendant instances are selected (direct or indirect) - * - * Indirect instances are the instances of subclasses. - * - * The states: - * showing everything is "shown" (ie marked) - * mixed some things are shown (ie a mixure of marked and unmarked) - * unshowing though there are things, none are shown (ie unmarked) - * empty a mid-level branch which itself has no direct instances - * (motivated by the taxon_picker which often has levels - * in its hierarchy which themselves have no direct instances) - * hidden a leaf or whole branch which (at the moment) has no instances - * (motivated by the predicate_picker which needs to hide - * whole branches which currently contain nothing) - * - * Non-leaf levels in a treepicker can have indirect states different - * from their direct states. The direct state relates to the direct instances. - * The indirect state spans the direct state of a level and all its children. - * Leaf levels should always have equal direct and indirect states. - * - */ + /* + * ColoredTreePicker is a widget for displaying and manipulating a hierarchy + * and displaying and manipulating the selectedness of branches and nodes. + * + * The terminology below is a bit screwy because the motivating hierarchy + * was a taxonomy controller which determined which nodes in a graph + * are 'shown' as selected. Perhaps better terminology would be to have + * 'shown' called 'marked' and 'unshown' called 'unmarked'. + * + * ▼ 0x25bc + * ▶ 0x25b6 + * + * Expanded Collapsed + * +-----------------+ +-----------------+ + * | parent ▼ | | parent ▶ | + * | +------------+| +-----------------+ + * | | child 1 || + * | +------------+| + * | | child 2 || + * | +------------+| + * +-----------------+ + * + * Clicking an expanded parent should cycle thru selection and deselection + * of only its direct instances, if there are any. + * + * Clicking a collapsed parent should cycle thru selection and deselection + * of its direct instances as well as those of all its children. + * + * The coloring of expanded parents cycles thru the three states: + * Mixed - some of the direct instances are selected + * On - all of the direct instances are selected + * Off - none of the direct instances are selected + * + * The coloring of a collapsed parent cycles thru the three states: + * Mixed - some descendant instances are selected (direct or indirect) + * On - all descendant instances are selected (direct or indirect) + * Off - no descendant instances are selected (direct or indirect) + * + * Indirect instances are the instances of subclasses. + * + * The states: + * showing everything is "shown" (ie marked) + * mixed some things are shown (ie a mixure of marked and unmarked) + * unshowing though there are things, none are shown (ie unmarked) + * empty a mid-level branch which itself has no direct instances + * (motivated by the taxon_picker which often has levels + * in its hierarchy which themselves have no direct instances) + * hidden a leaf or whole branch which (at the moment) has no instances + * (motivated by the predicate_picker which needs to hide + * whole branches which currently contain nothing) + * + * Non-leaf levels in a treepicker can have indirect states different + * from their direct states. The direct state relates to the direct instances. + * The indirect state spans the direct state of a level and all its children. + * Leaf levels should always have equal direct and indirect states. + * + */ -const L_unshowing = 0.93; -const L_showing = 0.75; -const L_emphasizing = 0.5; -const S_all = 0.5; -const verbose = false; + L_unshowing = 0.93; -class ColoredTreePicker extends TreePicker { - static initClass() { - this.prototype.container_regex = new RegExp("container"); - this.prototype.contents_regex = new RegExp("contents"); - } - constructor() { - { - // Hack: trick Babel/TypeScript into allowing this before super. - if (false) { super(); } - let thisFn = (() => { return this; }).toString(); - let thisName = thisFn.match(/return (?:_assertThisInitialized\()*(\w+)\)*;/)[1]; - eval(`${thisName} = this;`); - } - this.recolor_now = this.recolor_now.bind(this); - this.click_handler = this.click_handler.bind(this); - super(...arguments); - this.id_to_colors = {}; - } - add(id,parent_id,name,listener) { - return super.add(id,parent_id,name,listener); - } - // FIXME @recolor_now() unless handled externally - recolor_now() { - this.id_to_colors = this.recolor(); - return this.update_css(); - } - get_my_style_id() { - return `${this.get_my_id()}_colors`; - } - update_css() { - if ((this.style_sheet == null)) { - this.style_sheet = this.elem.append("style"); - } - // .attr("id", @get_my_style_id()) - let styles = `// ${this.get_my_id()}`; - let ctxSel = this.style_context_selector; - if (ctxSel) { - ctxSel += ' '; // put a space after ctxSel if it has content - } - if (ctxSel == null) { ctxSel = ''; } - for (let id in this.id_to_colors) { - const colors = this.id_to_colors[id]; - const nc = colors.unshowing; - const sc = colors.showing; - styles += `\ - -${ctxSel}#${id}.treepicker-showing { - background-color:${sc}; -} -${ctxSel}#${id}.treepicker-unshowing { - background-color:${nc}; -} -${ctxSel}#${id}.treepicker-mixed, -${ctxSel}#${id}.treepicker-indirect-mixed.treepicker-collapse { - background: linear-gradient(45deg, ${nc}, ${sc}, ${nc}, ${sc}, ${nc}, ${sc}, ${nc}, ${sc}); - background-color: transparent; -}\ -`; + L_showing = 0.75; + + L_emphasizing = 0.5; + + S_all = 0.5; + + verbose = false; + + ColoredTreePicker = (function(_super) { + __extends(ColoredTreePicker, _super); + + function ColoredTreePicker() { + this.click_handler = __bind(this.click_handler, this); + this.recolor_now = __bind(this.recolor_now, this); + ColoredTreePicker.__super__.constructor.apply(this, arguments); + this.id_to_colors = {}; } - this.style_sheet.html(styles); - if (false) { // cross-check the stylesheets to ensure proper loading - if (this.style_sheet.html().length !== styles.length) { - console.error("style_sheet_length error:", this.style_sheet.html().length, "<>", styles.length); - } else { - console.info("style_sheet_length good:",this.style_sheet.html().length, "==", styles.length); + + ColoredTreePicker.prototype.add = function(id, parent_id, name, listener) { + return ColoredTreePicker.__super__.add.call(this, id, parent_id, name, listener); + }; + + ColoredTreePicker.prototype.recolor_now = function() { + this.id_to_colors = this.recolor(); + return this.update_css(); + }; + + ColoredTreePicker.prototype.get_my_style_id = function() { + return "" + (this.get_my_id()) + "_colors"; + }; + + ColoredTreePicker.prototype.update_css = function() { + var colors, ctxSel, id, nc, sc, styles, _ref; + if (this.style_sheet == null) { + this.style_sheet = this.elem.append("style"); } - } - } - recolor() { - const recursor = { - count: Object.keys(this.id_to_elem).length - this.get_abstract_count(), - i: 0 - }; - const retval = {}; - if (verbose) { - console.log("RECOLOR"); - } - const branch = this.elem[0][0].children[0]; - this.recolor_recurse_DOM(retval, recursor, branch, ""); - return retval; - } - recolor_recurse_DOM(retval, recursor, branch, indent) { - const branch_id = branch.getAttribute("id"); - let class_str = branch.getAttribute("class"); - if (verbose) { - console.log(indent+"-recolor_recurse(",branch_id,class_str,")",branch); - } - if (branch_id) { - // should this go after recursion so color range can be picked up? - this.recolor_node(retval, recursor, branch_id, branch, indent); - } - if (branch.children.length > 0) { - for (let elem of Array.from(branch.children)) { - if (elem != null) { - class_str = elem.getAttribute("class"); - if (class_str.indexOf("treepicker-label") > -1) { - continue; - } - this.recolor_recurse_DOM(retval, recursor, elem, indent + " |"); + styles = "// " + (this.get_my_id()); + ctxSel = this.style_context_selector; + if (ctxSel) { + ctxSel += ' '; + } + if (ctxSel == null) { + ctxSel = ''; + } + _ref = this.id_to_colors; + for (id in _ref) { + colors = _ref[id]; + nc = colors.unshowing; + sc = colors.showing; + styles += "\n" + ctxSel + "#" + id + ".treepicker-showing {\n background-color:" + sc + ";\n}\n" + ctxSel + "#" + id + ".treepicker-unshowing {\n background-color:" + nc + ";\n}\n" + ctxSel + "#" + id + ".treepicker-mixed,\n" + ctxSel + "#" + id + ".treepicker-indirect-mixed.treepicker-collapse {\n background: linear-gradient(45deg, " + nc + ", " + sc + ", " + nc + ", " + sc + ", " + nc + ", " + sc + ", " + nc + ", " + sc + ");\n background-color: transparent;\n}"; + } + this.style_sheet.html(styles); + if (false) { + if (this.style_sheet.html().length !== styles.length) { + console.error("style_sheet_length error:", this.style_sheet.html().length, "<>", styles.length); + } else { + console.info("style_sheet_length good:", this.style_sheet.html().length, "==", styles.length); } } - } - return retval; - } - recolor_node(retval, recursor, id, elem_raw, indent) { - const elem = d3.select(elem_raw); - if (this.is_abstract(id)) { - retval[id] = { - unshowing: hsl2rgb(0, 0, L_unshowing), - showing: hsl2rgb(0, 0, L_showing), - emphasizing: hsl2rgb(0, 0, L_emphasizing) - }; - } else { - // https://en.wikipedia.org/wiki/HSL_and_HSV#HSL - // Adding .5 ensures hues are centered in their range, not at top. - // Adding 1 ensures different first and last colors, since 0 == 360 - const hue = ((recursor.i + .5)/(recursor.count + 1)) * 360; - recursor.i++; // post-increment to stay in the range below 360 - retval[id] = { - unshowing: hsl2rgb(hue, S_all, L_unshowing), - showing: hsl2rgb(hue, S_all, L_showing), - emphasizing: hsl2rgb(hue, S_all, L_emphasizing) + }; + + ColoredTreePicker.prototype.recolor = function() { + var branch, recursor, retval; + recursor = { + count: Object.keys(this.id_to_elem).length - this.get_abstract_count(), + i: 0 }; - if (verbose && [1, recursor.count + 1].includes(recursor.i)) { - console.info(id, recursor, hue, retval[id]); + retval = {}; + if (verbose) { + console.log("RECOLOR"); } - } - if (verbose) { - return console.log(indent + " - - - recolor_node("+id+")",retval[id].unshowing); - } - } - get_current_color_forId(id) { - const state = this.id_to_state[true][id]; - return this.get_color_forId_byName(id, state); - } - get_color_forId_byName(id, state_name) { - id = this.uri_to_js_id(id); - const colors = this.id_to_colors[id]; - if (colors != null) { - return colors[state_name]; - } - } - //else - // msg = "get_color_forId_byName(" + id + ") failed because @id_to_colors[id] not found" - // return 'pink' - click_handler() { - const id = super.click_handler(); - return this.style_with_kid_color_summary_if_needed(id); - } - style_with_kid_color_summary_if_needed(id) { - if (this.should_be_colored_by_kid_summary(id)) { - return this.style_with_kid_color_summary(id); - } - } - should_be_colored_by_kid_summary(id) { - return !this.is_leaf(id) && this.id_is_collapsed[id]; - } - collapse_by_id(id) { - super.collapse_by_id(id); - return this.style_with_kid_color_summary_if_needed(id); - } - expand_by_id(id) { - if (this.should_be_colored_by_kid_summary(id)) { - this.id_to_elem[id].attr("style", ""); // clear style set by set_gradient_style - } - return super.expand_by_id(id); - } - summarize_kid_colors(id, color_list) { - color_list = color_list || []; - const kids = this.id_to_children[id]; - if (!this.is_abstract[id]) { - const color = this.get_current_color_forId(id); - if (color != null) { - color_list.push(color); + branch = this.elem[0][0].children[0]; + this.recolor_recurse_DOM(retval, recursor, branch, ""); + return retval; + }; + + ColoredTreePicker.prototype.recolor_recurse_DOM = function(retval, recursor, branch, indent) { + var branch_id, class_str, elem, _i, _len, _ref; + branch_id = branch.getAttribute("id"); + class_str = branch.getAttribute("class"); + if (verbose) { + console.log(indent + "-recolor_recurse(", branch_id, class_str, ")", branch); } - } - if (kids != null) { - for (let kid_id of Array.from(kids)) { - this.summarize_kid_colors(kid_id, color_list); + if (branch_id) { + this.recolor_node(retval, recursor, branch_id, branch, indent); } - } - return color_list; - } - style_with_kid_color_summary(id) { - const color_list = this.summarize_kid_colors(id); - if (color_list.length === 1) { - color_list.push(color_list[0]); - } - if (color_list.length) { - return this.set_gradient_style(id,color_list); - } - } - set_gradient_style(id, kid_colors) { - const colors = kid_colors.join(', '); - let style = "background-color: transparent;"; - style += ` background: linear-gradient(45deg, ${colors})`; - return this.id_to_elem[id].attr("style", style); - } - set_payload(id, value) { - super.set_payload(id, value); - // REVIEW it works but is this the right time to do this? - // ensure collapsed nodes have summary colors updated - return this.style_with_kid_color_summary_if_needed(id); - } -} -ColoredTreePicker.initClass(); + if (branch.children.length > 0) { + _ref = branch.children; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + elem = _ref[_i]; + if (elem != null) { + class_str = elem.getAttribute("class"); + if (class_str.indexOf("treepicker-label") > -1) { + continue; + } + this.recolor_recurse_DOM(retval, recursor, elem, indent + " |"); + } + } + } + return retval; + }; + ColoredTreePicker.prototype.container_regex = new RegExp("container"); -(typeof exports !== 'undefined' && exports !== null ? exports : this).ColoredTreePicker = ColoredTreePicker; -}, "deprecated": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS001: Remove Babel/TypeScript constructor workaround - * DS102: Remove unnecessary code created because of implicit returns - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -const { Huviz } = require('huviz'); - - -class Deprecated extends Huviz { - - constructor(...args) { - { - // Hack: trick Babel/TypeScript into allowing this before super. - if (false) { super(); } - let thisFn = (() => { return this; }).toString(); - let thisName = thisFn.match(/return (?:_assertThisInitialized\()*(\w+)\)*;/)[1]; - eval(`${thisName} = this;`); - } - this.onnextsubject = this.onnextsubject.bind(this); - this.onnextsubject = this.onnextsubject.bind(this); - super(...args); - } + ColoredTreePicker.prototype.contents_regex = new RegExp("contents"); - hide_all_links() { - this.nodes.forEach(node => { - //node.linked = false; - //node.fixed = false; - this.shelved_set.acquire(node); - node.links_shown = []; - node.showing_links = "none"; - this.shelved_set.acquire(node); - return this.update_showing_links(node); - }); + ColoredTreePicker.prototype.recolor_node = function(retval, recursor, id, elem_raw, indent) { + var elem, hue, _ref; + elem = d3.select(elem_raw); + if (this.is_abstract(id)) { + retval[id] = { + unshowing: hsl2rgb(0, 0, L_unshowing), + showing: hsl2rgb(0, 0, L_showing), + emphasizing: hsl2rgb(0, 0, L_emphasizing) + }; + } else { + hue = ((recursor.i + .5) / (recursor.count + 1)) * 360; + recursor.i++; + retval[id] = { + unshowing: hsl2rgb(hue, S_all, L_unshowing), + showing: hsl2rgb(hue, S_all, L_showing), + emphasizing: hsl2rgb(hue, S_all, L_emphasizing) + }; + if (verbose && ((_ref = recursor.i) === 1 || _ref === (recursor.count + 1))) { + console.info(id, recursor, hue, retval[id]); + } + } + if (verbose) { + return console.log(indent + " - - - recolor_node(" + id + ")", retval[id].unshowing); + } + }; - this.links_set.forEach(link => { - return this.remove_ghosts(link); - }); + ColoredTreePicker.prototype.get_current_color_forId = function(id) { + var state; + state = this.id_to_state[true][id]; + return this.get_color_forId_byName(id, state); + }; - this.links_set.clear(); - this.chosen_set.clear(); - - // It should not be neccessary to clear discarded_set or hidden_set() - // because shelved_set.acquire() should have accomplished that - return this.restart(); - } + ColoredTreePicker.prototype.get_color_forId_byName = function(id, state_name) { + var colors; + id = this.uri_to_js_id(id); + colors = this.id_to_colors[id]; + if (colors != null) { + return colors[state_name]; + } + }; - toggle_links() { - //console.log("links",force.links()); - if (!this.links_set.length) { - this.make_links(G); - this.restart(); - } - return this.force.links().length; - } + ColoredTreePicker.prototype.click_handler = function() { + var id; + id = ColoredTreePicker.__super__.click_handler.call(this); + return this.style_with_kid_color_summary_if_needed(id); + }; - fire_nextsubject_event(oldquad,newquad) { - //console.log "fire_nextsubject_event",oldquad - return window.dispatchEvent( - new CustomEvent('nextsubject', { - detail: { - old: oldquad, - new: newquad - }, - bubbles: true, - cancelable: true - }) - ); - } + ColoredTreePicker.prototype.style_with_kid_color_summary_if_needed = function(id) { + if (this.should_be_colored_by_kid_summary(id)) { + return this.style_with_kid_color_summary(id); + } + }; + + ColoredTreePicker.prototype.should_be_colored_by_kid_summary = function(id) { + return !this.is_leaf(id) && this.id_is_collapsed[id]; + }; + + ColoredTreePicker.prototype.collapse_by_id = function(id) { + ColoredTreePicker.__super__.collapse_by_id.call(this, id); + return this.style_with_kid_color_summary_if_needed(id); + }; - onnextsubject(e) { - alert("sproing"); - //console.log "onnextsubject: called",e - // The event 'nextsubject' is fired when the subject of add_quad() - // is different from the last call to add_quad(). It will also be - // called when the data source has been exhausted. Our purpose - // in listening for this situation is that this is when we ought - // to check to see whether there is now enough information to create - // a node. A node must have an ID, a name and a type for it to - // be worth making a node for it (at least in the orlando situation). - // The ID is the uri (or the id if a BNode) - this.calls_to_onnextsubject++; - //console.log "count:",@calls_to_onnextsubject - if (e.detail.old != null) { - const subject = this.my_graph.subjects[e.detail.old.s.raw]; // FIXME why is raw still here? - this.set_type_if_possible(subject,e.detail.old,true); - if (this.is_ready(subject)) { - this.get_or_create_node(subject); - return this.tick(); + ColoredTreePicker.prototype.expand_by_id = function(id) { + if (this.should_be_colored_by_kid_summary(id)) { + this.id_to_elem[id].attr("style", ""); } - } - } - - show_found_links() { - for (let sub_id in this.G.subjects) { - var subj = this.G.subjects[sub_id]; - subj.getValues("f:name").forEach(name => { - if (name.match(this.search_regex)) { - const node = this.get_or_make_node(subj, [cx,cy]); - if (node) { return this.show_node_links(node); } + return ColoredTreePicker.__super__.expand_by_id.call(this, id); + }; + + ColoredTreePicker.prototype.summarize_kid_colors = function(id, color_list) { + var color, kid_id, kids, _i, _len; + color_list = color_list || []; + kids = this.id_to_children[id]; + if (!this.is_abstract[id]) { + color = this.get_current_color_forId(id); + if (color != null) { + color_list.push(color); } - }); - } - return this.restart(); - } + } + if (kids != null) { + for (_i = 0, _len = kids.length; _i < _len; _i++) { + kid_id = kids[_i]; + this.summarize_kid_colors(kid_id, color_list); + } + } + return color_list; + }; - // deprecated in favour of get_or_create_node - get_or_make_node(subject, start_point, linked, into_set) { - if (!subject) { return; } - let d = this.get_node_by_id(subject.id); - if (d) { return d; } - start_point = start_point || [ - this.width / 2, - this.height / 2 - ]; - linked = (typeof linked === "undefined") || linked || false; - const name_obj = subject.predicates[FOAF_name].objects[0]; - const name = ((name_obj.value != null) && name_obj.value) || name_obj; - //name = subject.predicates[FOAF_name].objects[0].value - d = new Node(subject.id); - d.s = subject; - d.name = name; - d.point(start_point); - d.prev_point([start_point[0]*1.01,start_point[1]*1.01]); - - this.assign_types(d); - d.color = this.color_by_type(d); - - this.add_node_ghosts(d); - //n_idx = @add_to_array(d, @nodes) - let n_idx = this.nodes.add(d); - this.id2n[subject.id] = n_idx; - if (false) { - if (!linked) { - n_idx = this.shelved_set.acquire(d); - this.id2u[subject.id] = n_idx; - } else { - this.id2u[subject.id] = this.graphed_set.acquire(d); + ColoredTreePicker.prototype.style_with_kid_color_summary = function(id) { + var color_list; + color_list = this.summarize_kid_colors(id); + if (color_list.length === 1) { + color_list.push(color_list[0]); } - } else { - into_set = ((into_set != null) && into_set) || (linked && this.graphed_set) || this.get_default_set_by_type(d); - into_set.acquire(d); - } - this.update_showing_links(d); - return d; - } - - find_links_from_node(node) { - let target = undefined; - const subj = node.s; - const x = node.x || (width / 2); - const y = node.y || (height / 2); - const pnt = [x,y]; - let oi = undefined; - if (subj) { - for (let p_name in subj.predicates) { - this.ensure_predicate(p_name); - const predicate = subj.predicates[p_name]; - oi = 0; - predicate.objects.forEach((obj,i) => { - if (obj.type === RDF_object) { - target = this.get_or_make_node(this.G.subjects[obj.value], pnt); - } - if (target) { - return this.add_link( new Edge(node, target)); - } - }); + if (color_list.length) { + return this.set_gradient_style(id, color_list); } - } - return node.links_from_found = true; - } + }; - find_links_to_node(d) { - const subj = d.s; - if (subj) { - const parent_point = [d.x,d.y]; - this.G.get_incoming_predicates(subj).forEach(sid_pred => { - const sid = sid_pred[0]; - const pred = sid_pred[1]; - const src = this.get_or_make_node(this.G.subjects[sid], parent_point); - return this.add_link( new Edge(src, d)); - }); - } - return d.links_to_found = true; - } + ColoredTreePicker.prototype.set_gradient_style = function(id, kid_colors) { + var colors, style; + colors = kid_colors.join(', '); + style = "background-color: transparent;"; + style += " background: linear-gradient(45deg, " + colors + ")"; + return this.id_to_elem[id].attr("style", style); + }; - set_type_if_possible(subj,quad,force) { - // This is a hack, ideally we would look on the subject for type at coloring - // and taxonomy assignment time but more thought is needed on how to - // integrate the semantic perspective with the coloring and the 'taxonomy'. - force = !(force == null) && force; - if ((subj.type == null) && (subj.type !== ORLANDO_writer) && !force) { - return; - } - //console.log "set_type_if_possible",force,subj.type,subj.id - const pred_id = quad.p.raw; - if ([RDF_type,'a'].includes(pred_id) && (quad.o.value === FOAF_Group)) { - subj.type = ORLANDO_org; - } else if (force && subj.id[0].match(this.bnode_regex)) { - subj.type = ORLANDO_other; - } else if (force) { - subj.type = ORLANDO_writer; - } - if (subj.type != null) { - let name; - return name = ((subj.predicates[FOAF_name] != null) && subj.predicates[FOAF_name].objects[0]) || subj.id; - } - } - //console.log " ",subj.type - - hide_all_links() { - this.nodes.forEach(node => { - //node.linked = false; - //node.fixed = false; - this.shelved_set.acquire(node); - node.links_shown = []; - node.showing_links = "none"; - this.shelved_set.acquire(node); - return this.update_showing_links(node); - }); + ColoredTreePicker.prototype.set_payload = function(id, value) { + ColoredTreePicker.__super__.set_payload.call(this, id, value); + return this.style_with_kid_color_summary_if_needed(id); + }; - this.links_set.forEach(link => { - return this.remove_ghosts(link); - }); + return ColoredTreePicker; - this.links_set.clear(); - this.chosen_set.clear(); - - // It should not be neccessary to clear discarded_set or hidden_set() - // because shelved_set.acquire() should have accomplished that - return this.restart(); - } + })(TreePicker); - toggle_links() { - //console.log("links",force.links()); - if (!this.links_set.length) { - this.make_links(G); - this.restart(); + (typeof exports !== "undefined" && exports !== null ? exports : this).ColoredTreePicker = ColoredTreePicker; + +}).call(this); +}, "deprecated": function(exports, require, module) {(function() { + var Deprecated, Huviz, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, + __hasProp = {}.hasOwnProperty, + __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; }; + + Huviz = require('huviz').Huviz; + + Deprecated = (function(_super) { + __extends(Deprecated, _super); + + function Deprecated() { + this.onnextsubject = __bind(this.onnextsubject, this); + this.onnextsubject = __bind(this.onnextsubject, this); + return Deprecated.__super__.constructor.apply(this, arguments); } - return this.force.links().length; - } - fire_nextsubject_event(oldquad,newquad) { - //console.log "fire_nextsubject_event",oldquad - return window.dispatchEvent( - new CustomEvent('nextsubject', { + Deprecated.prototype.hide_all_links = function() { + this.nodes.forEach((function(_this) { + return function(node) { + _this.shelved_set.acquire(node); + node.links_shown = []; + node.showing_links = "none"; + _this.shelved_set.acquire(node); + return _this.update_showing_links(node); + }; + })(this)); + this.links_set.forEach((function(_this) { + return function(link) { + return _this.remove_ghosts(link); + }; + })(this)); + this.links_set.clear(); + this.chosen_set.clear(); + return this.restart(); + }; + + Deprecated.prototype.toggle_links = function() { + if (!this.links_set.length) { + this.make_links(G); + this.restart(); + } + return this.force.links().length; + }; + + Deprecated.prototype.fire_nextsubject_event = function(oldquad, newquad) { + return window.dispatchEvent(new CustomEvent('nextsubject', { detail: { old: oldquad, - new: newquad + "new": newquad }, bubbles: true, cancelable: true - }) - ); - } + })); + }; - onnextsubject(e) { - alert("sproing"); - //console.log "onnextsubject: called",e - // The event 'nextsubject' is fired when the subject of add_quad() - // is different from the last call to add_quad(). It will also be - // called when the data source has been exhausted. Our purpose - // in listening for this situation is that this is when we ought - // to check to see whether there is now enough information to create - // a node. A node must have an ID, a name and a type for it to - // be worth making a node for it (at least in the orlando situation). - // The ID is the uri (or the id if a BNode) - this.calls_to_onnextsubject++; - //console.log "count:",@calls_to_onnextsubject - if (e.detail.old != null) { - const subject = this.my_graph.subjects[e.detail.old.s.raw]; // FIXME why is raw still here? - this.set_type_if_possible(subject,e.detail.old,true); - if (this.is_ready(subject)) { - this.get_or_create_node(subject); - return this.tick(); - } - } - } - - show_found_links() { - for (let sub_id in this.G.subjects) { - var subj = this.G.subjects[sub_id]; - subj.getValues("f:name").forEach(name => { - if (name.match(this.search_regex)) { - const node = this.get_or_make_node(subj, [cx,cy]); - if (node) { return this.show_node_links(node); } + Deprecated.prototype.onnextsubject = function(e) { + var subject; + alert("sproing"); + this.calls_to_onnextsubject++; + if (e.detail.old != null) { + subject = this.my_graph.subjects[e.detail.old.s.raw]; + this.set_type_if_possible(subject, e.detail.old, true); + if (this.is_ready(subject)) { + this.get_or_create_node(subject); + return this.tick(); } - }); - } - return this.restart(); - } + } + }; - // deprecated in favour of get_or_create_node - get_or_make_node(subject, start_point, linked, into_set) { - if (!subject) { return; } - let d = this.get_node_by_id(subject.id); - if (d) { return d; } - start_point = start_point || [ - this.width / 2, - this.height / 2 - ]; - linked = (typeof linked === "undefined") || linked || false; - const name_obj = subject.predicates[FOAF_name].objects[0]; - const name = ((name_obj.value != null) && name_obj.value) || name_obj; - //name = subject.predicates[FOAF_name].objects[0].value - d = new Node(subject.id); - d.s = subject; - d.name = name; - d.point(start_point); - d.prev_point([start_point[0]*1.01,start_point[1]*1.01]); - - this.assign_types(d); - d.color = this.color_by_type(d); - - this.add_node_ghosts(d); - //n_idx = @add_to_array(d, @nodes) - let n_idx = this.nodes.add(d); - this.id2n[subject.id] = n_idx; - if (false) { - if (!linked) { - n_idx = this.shelved_set.acquire(d); - this.id2u[subject.id] = n_idx; + Deprecated.prototype.show_found_links = function() { + var sub_id, subj; + for (sub_id in this.G.subjects) { + subj = this.G.subjects[sub_id]; + subj.getValues("f:name").forEach((function(_this) { + return function(name) { + var node; + if (name.match(_this.search_regex)) { + node = _this.get_or_make_node(subj, [cx, cy]); + if (node) { + return _this.show_node_links(node); + } + } + }; + })(this)); + } + return this.restart(); + }; + + Deprecated.prototype.get_or_make_node = function(subject, start_point, linked, into_set) { + var d, n_idx, name, name_obj; + if (!subject) { + return; + } + d = this.get_node_by_id(subject.id); + if (d) { + return d; + } + start_point = start_point || [this.width / 2, this.height / 2]; + linked = typeof linked === "undefined" || linked || false; + name_obj = subject.predicates[FOAF_name].objects[0]; + name = (name_obj.value != null) && name_obj.value || name_obj; + d = new Node(subject.id); + d.s = subject; + d.name = name; + d.point(start_point); + d.prev_point([start_point[0] * 1.01, start_point[1] * 1.01]); + this.assign_types(d); + d.color = this.color_by_type(d); + this.add_node_ghosts(d); + n_idx = this.nodes.add(d); + this.id2n[subject.id] = n_idx; + if (false) { + if (!linked) { + n_idx = this.shelved_set.acquire(d); + this.id2u[subject.id] = n_idx; + } else { + this.id2u[subject.id] = this.graphed_set.acquire(d); + } } else { - this.id2u[subject.id] = this.graphed_set.acquire(d); + into_set = (into_set != null) && into_set || linked && this.graphed_set || this.get_default_set_by_type(d); + into_set.acquire(d); } - } else { - into_set = ((into_set != null) && into_set) || (linked && this.graphed_set) || this.get_default_set_by_type(d); - into_set.acquire(d); - } - this.update_showing_links(d); - return d; - } - - find_links_from_node(node) { - let target = undefined; - const subj = node.s; - const x = node.x || (width / 2); - const y = node.y || (height / 2); - const pnt = [x,y]; - let oi = undefined; - if (subj) { - for (let p_name in subj.predicates) { - this.ensure_predicate(p_name); - const predicate = subj.predicates[p_name]; - oi = 0; - predicate.objects.forEach((obj,i) => { - if (obj.type === RDF_object) { - target = this.get_or_make_node(this.G.subjects[obj.value], pnt); - } - if (target) { - return this.add_link( new Edge(node, target)); - } - }); + this.update_showing_links(d); + return d; + }; + + Deprecated.prototype.find_links_from_node = function(node) { + var oi, p_name, pnt, predicate, subj, target, x, y; + target = void 0; + subj = node.s; + x = node.x || width / 2; + y = node.y || height / 2; + pnt = [x, y]; + oi = void 0; + if (subj) { + for (p_name in subj.predicates) { + this.ensure_predicate(p_name); + predicate = subj.predicates[p_name]; + oi = 0; + predicate.objects.forEach((function(_this) { + return function(obj, i) { + if (obj.type === RDF_object) { + target = _this.get_or_make_node(_this.G.subjects[obj.value], pnt); + } + if (target) { + return _this.add_link(new Edge(node, target)); + } + }; + })(this)); + } } - } - return node.links_from_found = true; - } + return node.links_from_found = true; + }; - find_links_to_node(d) { - const subj = d.s; - if (subj) { - const parent_point = [d.x,d.y]; - this.G.get_incoming_predicates(subj).forEach(sid_pred => { - const sid = sid_pred[0]; - const pred = sid_pred[1]; - const src = this.get_or_make_node(this.G.subjects[sid], parent_point); - return this.add_link( new Edge(src, d)); - }); - } - return d.links_to_found = true; - } - - set_type_if_possible(subj,quad,force) { - // This is a hack, ideally we would look on the subject for type at coloring - // and taxonomy assignment time but more thought is needed on how to - // integrate the semantic perspective with the coloring and the 'taxonomy'. - force = !(force == null) && force; - if ((subj.type == null) && (subj.type !== ORLANDO_writer) && !force) { - return; - } - //console.log "set_type_if_possible",force,subj.type,subj.id - const pred_id = quad.p.raw; - if ([RDF_type,'a'].includes(pred_id) && (quad.o.value === FOAF_Group)) { - subj.type = ORLANDO_org; - } else if (force && subj.id[0].match(this.bnode_regex)) { - subj.type = ORLANDO_other; - } else if (force) { - subj.type = ORLANDO_writer; - } - if (subj.type != null) { - let name; - return name = ((subj.predicates[FOAF_name] != null) && subj.predicates[FOAF_name].objects[0]) || subj.id; - } - } -} - //console.log " ",subj.type - -(typeof exports !== 'undefined' && exports !== null ? exports : this).Deprecated = Deprecated; -}, "edge": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS102: Remove unnecessary code created because of implicit returns - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -class Edge { - static initClass() { - this.prototype.color = "lightgrey"; - } - constructor(source, target, predicate, graph) { - // FIXME if everything already has .lid then remove the test "not a.lid?" - this.source = source; - this.target = target; - this.predicate = predicate; - this.graph = graph; - this.id = ([this.source, this.predicate, this.target].map((a) => ((a.lid == null) && a.id) || a.lid)).join(' '); - this.lid = this.id; - this.register(); - this.contexts = []; - this; - } - register() { - return this.predicate.add_inst(this); - } - register_context(context) { - return this.contexts.push(context); - } - // context.register_context_for(this) # FIXME to see all assertions in a context - isSelected() { - return (this.source.selected != null) || (this.target.selected != null); - } - show() { - return this.predicate.update_state(this, 'show'); - } - unshow() { - return this.predicate.update_state(this, 'unshow'); - } - an_end_is_selected() { - return (this.target.selected != null) || (this.source.selected != null); - } - unselect() { - return this.predicate.update_state(this, 'unselect'); - } - select() { - return this.predicate.update_state(this, 'select'); - } -} -Edge.initClass(); - -(typeof exports !== 'undefined' && exports !== null ? exports : this).Edge = Edge; -}, "editui": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS001: Remove Babel/TypeScript constructor workaround - * DS101: Remove unnecessary use of Array.from - * DS102: Remove unnecessary code created because of implicit returns - * DS202: Simplify dynamic range loops - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -// Edit UI - Jan 2017 + Deprecated.prototype.find_links_to_node = function(d) { + var parent_point, subj; + subj = d.s; + if (subj) { + parent_point = [d.x, d.y]; + this.G.get_incoming_predicates(subj).forEach((function(_this) { + return function(sid_pred) { + var pred, sid, src; + sid = sid_pred[0]; + pred = sid_pred[1]; + src = _this.get_or_make_node(_this.G.subjects[sid], parent_point); + return _this.add_link(new Edge(src, d)); + }; + })(this)); + } + return d.links_to_found = true; + }; -const { FiniteStateMachine } = require('fsm'); -const indexdDBstore = require('indexeddbstoragecontroller'); + Deprecated.prototype.set_type_if_possible = function(subj, quad, force) { + var name, pred_id; + force = !(force == null) && force; + if ((subj.type == null) && subj.type !== ORLANDO_writer && !force) { + return; + } + pred_id = quad.p.raw; + if ((pred_id === RDF_type || pred_id === 'a') && quad.o.value === FOAF_Group) { + subj.type = ORLANDO_org; + } else if (force && subj.id[0].match(this.bnode_regex)) { + subj.type = ORLANDO_other; + } else if (force) { + subj.type = ORLANDO_writer; + } + if (subj.type != null) { + return name = (subj.predicates[FOAF_name] != null) && subj.predicates[FOAF_name].objects[0] || subj.id; + } + }; -class EditController extends FiniteStateMachine { - static initClass() { - - (typeof exports !== 'undefined' && exports !== null ? exports : this).EditController = EditController; - } - constructor(huviz) { - //TODO EditController should be loaded and checked when a dataset is loaded - { - // Hack: trick Babel/TypeScript into allowing this before super. - if (false) { super(); } - let thisFn = (() => { return this; }).toString(); - let thisName = thisFn.match(/return (?:_assertThisInitialized\()*(\w+)\)*;/)[1]; - eval(`${thisName} = this;`); - } - this.toggle_edit_form = this.toggle_edit_form.bind(this); - this.huviz = huviz; - this.userValid = true; //TODO this needs to be hooked into authentication -- remove to huviz.coffee to validate against dataloaded and authentication - //@userValid = false - this.ensure_verbs(); - this.build_transitions(); - this.state = null; - } + Deprecated.prototype.hide_all_links = function() { + this.nodes.forEach((function(_this) { + return function(node) { + _this.shelved_set.acquire(node); + node.links_shown = []; + node.showing_links = "none"; + _this.shelved_set.acquire(node); + return _this.update_showing_links(node); + }; + })(this)); + this.links_set.forEach((function(_this) { + return function(link) { + return _this.remove_ghosts(link); + }; + })(this)); + this.links_set.clear(); + this.chosen_set.clear(); + return this.restart(); + }; - build_transitions() { - return this.transitions = { - prepare: { - target: 'prepared' - }, - disable: { - target: 'disabled' - }, - enable: { - target: 'prepared' + Deprecated.prototype.toggle_links = function() { + if (!this.links_set.length) { + this.make_links(G); + this.restart(); } + return this.force.links().length; }; - } - on__prepare() { - if ((this.userValid === true) && !this.con) { //document.getElementsByClassName("edit-controls")[0] is undefined - this.con = document.createElement("div"); - this.con.className = "edit-controls loggedIn"; - this.con.setAttribute("edit", "no"); - //@huviz.set_edit_mode(false) - const viscanvas = this.huviz.args.viscanvas_sel; - const new_viscanvas = viscanvas.replace('#',''); - document.getElementById(new_viscanvas).appendChild(this.con); - this.con.innerHTML = "
VIEW
CONTRIBUTE
(Alpha)
"; - this.create_edit_form(this.con); - this.con.getElementsByClassName("slider")[0].onclick = this.toggle_edit_form; - //console.log(con.getElementsByTagName("form")[0]) - //console.log(con.getElementsByClassName("slider")[0]) - this.formFields = this.con.getElementsByTagName("form")[0]; - const clearForm = this.formFields.getElementsByClassName("clearForm")[0]; //TODO How are these working? - const saveForm = this.formFields.getElementsByClassName("saveForm")[0]; - const validateForm = this.formFields.getElementsByTagName('input'); - validateForm[0].addEventListener("input", this.validate_edit_form); - validateForm[1].addEventListener("input", this.validate_edit_form); - validateForm[2].addEventListener("input", this.validate_edit_form); - clearForm.addEventListener("click", this.clear_edit_form); - saveForm.addEventListener("click", this.save_edit_form); - this.proposed_quad = null; - this.controls = this.formFields; - this.subject_input = this.formFields[0]; - this.predicate_input = this.formFields[1]; - return this.object_input = this.formFields[2]; - } - } + Deprecated.prototype.fire_nextsubject_event = function(oldquad, newquad) { + return window.dispatchEvent(new CustomEvent('nextsubject', { + detail: { + old: oldquad, + "new": newquad + }, + bubbles: true, + cancelable: true + })); + }; - hide() { - return $(this.con).hide(); - } - show() { - return $(this.con).show(); - } + Deprecated.prototype.onnextsubject = function(e) { + var subject; + alert("sproing"); + this.calls_to_onnextsubject++; + if (e.detail.old != null) { + subject = this.my_graph.subjects[e.detail.old.s.raw]; + this.set_type_if_possible(subject, e.detail.old, true); + if (this.is_ready(subject)) { + this.get_or_create_node(subject); + return this.tick(); + } + } + }; - on__disable() { - this.hide_verbs(); - return this.hide_form(); - } + Deprecated.prototype.show_found_links = function() { + var sub_id, subj; + for (sub_id in this.G.subjects) { + subj = this.G.subjects[sub_id]; + subj.getValues("f:name").forEach((function(_this) { + return function(name) { + var node; + if (name.match(_this.search_regex)) { + node = _this.get_or_make_node(subj, [cx, cy]); + if (node) { + return _this.show_node_links(node); + } + } + }; + })(this)); + } + return this.restart(); + }; - on__enable() { - this.show_verbs(); - return this.show_form(); - } + Deprecated.prototype.get_or_make_node = function(subject, start_point, linked, into_set) { + var d, n_idx, name, name_obj; + if (!subject) { + return; + } + d = this.get_node_by_id(subject.id); + if (d) { + return d; + } + start_point = start_point || [this.width / 2, this.height / 2]; + linked = typeof linked === "undefined" || linked || false; + name_obj = subject.predicates[FOAF_name].objects[0]; + name = (name_obj.value != null) && name_obj.value || name_obj; + d = new Node(subject.id); + d.s = subject; + d.name = name; + d.point(start_point); + d.prev_point([start_point[0] * 1.01, start_point[1] * 1.01]); + this.assign_types(d); + d.color = this.color_by_type(d); + this.add_node_ghosts(d); + n_idx = this.nodes.add(d); + this.id2n[subject.id] = n_idx; + if (false) { + if (!linked) { + n_idx = this.shelved_set.acquire(d); + this.id2u[subject.id] = n_idx; + } else { + this.id2u[subject.id] = this.graphed_set.acquire(d); + } + } else { + into_set = (into_set != null) && into_set || linked && this.graphed_set || this.get_default_set_by_type(d); + into_set.acquire(d); + } + this.update_showing_links(d); + return d; + }; - get_verb_set() { - return { - connect: this.huviz.human_term.connect, // aka link - spawn: this.huviz.human_term.spawn, // aka instantiate - specialize: this.huviz.human_term.specialize, // aka subclass / subpropertize - annotate: this.huviz.human_term.annotate - }; - } + Deprecated.prototype.find_links_from_node = function(node) { + var oi, p_name, pnt, predicate, subj, target, x, y; + target = void 0; + subj = node.s; + x = node.x || width / 2; + y = node.y || height / 2; + pnt = [x, y]; + oi = void 0; + if (subj) { + for (p_name in subj.predicates) { + this.ensure_predicate(p_name); + predicate = subj.predicates[p_name]; + oi = 0; + predicate.objects.forEach((function(_this) { + return function(obj, i) { + if (obj.type === RDF_object) { + target = _this.get_or_make_node(_this.G.subjects[obj.value], pnt); + } + if (target) { + return _this.add_link(new Edge(node, target)); + } + }; + })(this)); + } + } + return node.links_from_found = true; + }; - add_verbs() { - let prepend; - const vset = this.get_verb_set(); - this.huviz.gclui.verb_sets.unshift(vset); - return this.huviz.gclui.add_verb_set(vset, (prepend = true)); - } + Deprecated.prototype.find_links_to_node = function(d) { + var parent_point, subj; + subj = d.s; + if (subj) { + parent_point = [d.x, d.y]; + this.G.get_incoming_predicates(subj).forEach((function(_this) { + return function(sid_pred) { + var pred, sid, src; + sid = sid_pred[0]; + pred = sid_pred[1]; + src = _this.get_or_make_node(_this.G.subjects[sid], parent_point); + return _this.add_link(new Edge(src, d)); + }; + })(this)); + } + return d.links_to_found = true; + }; - ensure_verbs() { - if (!this.my_verbs) { - this.my_verbs = this.add_verbs(); - return this.hide_verbs(); - } - } + Deprecated.prototype.set_type_if_possible = function(subj, quad, force) { + var name, pred_id; + force = !(force == null) && force; + if ((subj.type == null) && subj.type !== ORLANDO_writer && !force) { + return; + } + pred_id = quad.p.raw; + if ((pred_id === RDF_type || pred_id === 'a') && quad.o.value === FOAF_Group) { + subj.type = ORLANDO_org; + } else if (force && subj.id[0].match(this.bnode_regex)) { + subj.type = ORLANDO_other; + } else if (force) { + subj.type = ORLANDO_writer; + } + if (subj.type != null) { + return name = (subj.predicates[FOAF_name] != null) && subj.predicates[FOAF_name].objects[0] || subj.id; + } + }; - hide_verbs() { - return this.my_verbs.style('display','none'); - } + return Deprecated; - show_verbs() { - return this.my_verbs.style('display','flex'); - } + })(Huviz); - create_edit_form(toggleEdit) { - const formNode = document.createElement('form'); - formNode.classList.add("cntrl-set", "edit-form"); - formNode.innerHTML = ''; - formNode.innerHTML += ''; - formNode.innerHTML += ''; - toggleEdit.appendChild(formNode); - return this.set_predicate_selector(); - } + (typeof exports !== "undefined" && exports !== null ? exports : this).Deprecated = Deprecated; - set_predicate_selector() { - //console.log("setting predicate selector in edit form") - // Add predicates from Ontology for autocomplete box in edit form - //pred_array = @huviz.predicate_set - let availablePredicates = []; - if (this.huviz.predicate_set) { - for (let predicate of Array.from(this.huviz.predicate_set)) { - availablePredicates.push(predicate.lid); - } - availablePredicates.push("literal"); - } else { - availablePredicates = [ - "A", - "literal" - ]; +}).call(this); +}, "edge": function(exports, require, module) {(function() { + var Edge; + + Edge = (function() { + function Edge(source, target, predicate, graph) { + var a; + this.source = source; + this.target = target; + this.predicate = predicate; + this.graph = graph; + this.id = ((function() { + var _i, _len, _ref, _results; + _ref = [this.source, this.predicate, this.target]; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + a = _ref[_i]; + _results.push((a.lid == null) && a.id || a.lid); + } + return _results; + }).call(this)).join(' '); + this.lid = this.id; + this.register(); + this.contexts = []; + this; } - return $("#predicate").autocomplete({ - source: availablePredicates, - open: this.update_predicate_picked, - close: this.update_predicate_picked, - change: this.update_predicate_picked, - position: { - my: "left bottom", - at: "left top" - } - }); - } - update_predicate_picked(event, ui) { - //if event.type is 'autocompletechange' - const new_pred_value = this.predicate_input.value; - console.log(`${new_pred_value} is new predicate`); - return this.validate_proposed_edge(); - } + Edge.prototype.color = "lightgrey"; - hide_form() { - this.con.setAttribute("edit","no"); - return this.con.classList.remove("edit-mode"); - } - //@huviz.set_edit_mode(false) + Edge.prototype.register = function() { + return this.predicate.add_inst(this); + }; - show_form() { - this.con.setAttribute("edit","yes"); - return this.con.classList.add("edit-mode"); - } - //@huviz.set_edit_mode(true) + Edge.prototype.register_context = function(context) { + return this.contexts.push(context); + }; - toggle_edit_form() { - const toggleEditMode = this.con.getAttribute("edit"); - //console.log("error") #debugger - if (toggleEditMode === 'no') { //toggle switched to edit mode, then show form - this.show_verbs(); - this.show_form(); - } - if (toggleEditMode === 'yes') { //toggle switched to normal mode, then hide form - this.hide_verbs(); - return this.hide_form(); - } - } + Edge.prototype.isSelected = function() { + return (this.source.selected != null) || (this.target.selected != null); + }; - validate_edit_form(evt) { - const form = this.controls; - const inputFields = form.getElementsByTagName('input'); - const saveButton = form.getElementsByTagName('button')[0]; - for (let i = 0, end = inputFields.length-1, asc = 0 <= end; asc ? i <= end : i >= end; asc ? i++ : i--) { - const elem = form.elements[i]; - if (elem.value === '') { - saveButton.disabled = 'disabled'; - break; - } else { - saveButton.disabled = false; - } - } - return this.adjust_object_datatype(); - } + Edge.prototype.show = function() { + return this.predicate.update_state(this, 'show'); + }; - predicate_is_DatatypeProperty() { - // The job of figuring this out is best done in a method because: - // * a search up the superclasses of the predicate is needed - // * caching that answer might be needed for efficiency - // * heuristics in case of ambiguity might be required - // - // We can get started on this by just responding to magic values in the predicate. - //console.log("predicate_is_Datatype has been called") - if (this.predicate_input) { - window.THINGY = this.predicate_input; - const current_value = this.predicate_input.value; - return current_value === 'literal'; - } - return false; - } + Edge.prototype.unshow = function() { + return this.predicate.update_state(this, 'unshow'); + }; - adjust_object_datatype() { - let placeholder_label; - if (this.predicate_is_DatatypeProperty()) { - this.object_datatype_is_literal = true; - placeholder_label = "a literal value"; - } else { - this.object_datatype_is_literal = false; - placeholder_label = "object"; - } - return this.object_input.setAttribute("placeholder", placeholder_label); - } + Edge.prototype.an_end_is_selected = function() { + return (this.target.selected != null) || (this.source.selected != null); + }; - // if the predicate is of DatatypeProperty then - // 0. replace placeholder to reflect data type needed in object - // 1. object field will only accpet input according to appropriate type (i.e. literal string, number or date) - - save_edit_form() { - let i; - let asc, end; - const form = this.controls; - const inputFields = form.getElementsByTagName('input'); - const tuple = []; - for (i = 0, end = inputFields.length-1, asc = 0 <= end; asc ? i <= end : i >= end; asc ? i++ : i--) { - const elem = form.elements[i]; - console.log(elem.name + ": " + elem.value); - tuple.push(elem.value); - } - const assrtSave = new indexdDBstore.IndexedDBStorageController(this.huviz); - console.log(assrtSave); - const quad = { - s: tuple[0], - p: tuple[1], - o: tuple[2] - }; - this.latest_quad = quad; // REMOVE ONCE saving to the indexedDB is working - this.huviz.set_proposed_edge(null); // set to nothing, ie stop flagging the edge as proposed - //@huviz.dbsstorage.assert(quad) - //assrtSave.assert(quad) - const saveButton = form.getElementsByTagName('button')[0]; - for (i in inputFields) { - form.elements[i].value = ''; - } - return saveButton.disabled = true; - } - //@proposed_quad = null #set to false (no focused edge) - - clear_edit_form() { - const form = this.controls; - const inputFields = form.getElementsByTagName('input'); - const saveButton = form.getElementsByTagName('button')[0]; - for (let i in inputFields) { - form.elements[i].value = ''; - } - if (this.proposed_quad) { - console.log("@proposed_quad:", this.proposed_quad); - //@huviz.set_proposed_edge(null) - this.remove_proposed_quad(); // clear existing edge clear from display - } - this.set_subject_node(); - this.set_object_node(); - return saveButton.disabled = true; - } - // TODO why on calling this function does the ability to drag nodes to fill form disabled? + Edge.prototype.unselect = function() { + return this.predicate.update_state(this, 'unselect'); + }; - set_subject_node(node) { - if (this.subject_node === node) { - return; - } - this.subject_node = node; - const new_value = (node && node.id) || ""; - console.log(`set_subject_node() id:'${new_value}'`); - this.subject_input.setAttribute("value",new_value); - this.validate_edit_form(); - return this.validate_proposed_edge(); - } + Edge.prototype.select = function() { + return this.predicate.update_state(this, 'select'); + }; + + return Edge; + + })(); + + (typeof exports !== "undefined" && exports !== null ? exports : this).Edge = Edge; + +}).call(this); +}, "editui": function(exports, require, module) {(function() { + var EditController, FiniteStateMachine, indexdDBstore, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, + __hasProp = {}.hasOwnProperty, + __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; }; + + FiniteStateMachine = require('fsm').FiniteStateMachine; + + indexdDBstore = require('indexeddbstoragecontroller'); - set_object_node(node) { // either a node or undefined - if (this.object_node === node) { - return; // ignore if there is no change + EditController = (function(_super) { + __extends(EditController, _super); + + function EditController(huviz) { + this.huviz = huviz; + this.toggle_edit_form = __bind(this.toggle_edit_form, this); + this.userValid = true; + this.ensure_verbs(); + this.build_transitions(); + this.state = null; } - this.object_node = node; // might be null - const new_value = (node && node.id) || ""; - console.log(`set_object_node() id:'${new_value}'`); - this.object_input.setAttribute("value",new_value); - this.validate_edit_form(); - return this.validate_proposed_edge(); - } - validate_proposed_edge() { // type = subject or object - console.log('validate_proposed_edge()'); - // What are the proposed subject node, object node and predicate? - // Subject and Object fields must have values (IDs of Nodes) - // Make a quad out of current subject and object (predicate if it is filled) - //subject_id = @editui.subject_input.value - const RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; - const RDF_literal = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; - - const subject_id = this.subject_input.value; - const object_id = this.object_input.value; - const predicate_val = this.predicate_input.value; - - // propose a new quad once there is a subject and an object - if (subject_id && object_id) { - const obj_type = predicate_val === 'literal' ? RDF_literal : RDF_object; - const q = { - s: subject_id, - p: predicate_val || "anything", - o: { // keys: type,value[,language] - type: obj_type, - value: object_id + EditController.prototype.build_transitions = function() { + return this.transitions = { + prepare: { + target: 'prepared' + }, + disable: { + target: 'disabled' }, - g: `http://${Date.now()}` + enable: { + target: 'prepared' + } }; - // Don't process any edge proposal if it is just the same as the current proposal - // Ignore requests for edges that are identical to the last edge requested - if ((this.proposed_quad != null) && this.quads_match(q, this.proposed_quad)) { - console.log(`... skipping: matches old`); - return; + }; + + EditController.prototype.on__prepare = function() { + var clearForm, new_viscanvas, saveForm, validateForm, viscanvas; + if (this.userValid === true && !this.con) { + this.con = document.createElement("div"); + this.con.className = "edit-controls loggedIn"; + this.con.setAttribute("edit", "no"); + viscanvas = this.huviz.args.viscanvas_sel; + new_viscanvas = viscanvas.replace('#', ''); + document.getElementById(new_viscanvas).appendChild(this.con); + this.con.innerHTML = "
VIEW
CONTRIBUTE
(Alpha)
"; + this.create_edit_form(this.con); + this.con.getElementsByClassName("slider")[0].onclick = this.toggle_edit_form; + this.formFields = this.con.getElementsByTagName("form")[0]; + clearForm = this.formFields.getElementsByClassName("clearForm")[0]; + saveForm = this.formFields.getElementsByClassName("saveForm")[0]; + validateForm = this.formFields.getElementsByTagName('input'); + validateForm[0].addEventListener("input", this.validate_edit_form); + validateForm[1].addEventListener("input", this.validate_edit_form); + validateForm[2].addEventListener("input", this.validate_edit_form); + clearForm.addEventListener("click", this.clear_edit_form); + saveForm.addEventListener("click", this.save_edit_form); + this.proposed_quad = null; + this.controls = this.formFields; + this.subject_input = this.formFields[0]; + this.predicate_input = this.formFields[1]; + return this.object_input = this.formFields[2]; } - console.log(`... accepting: `); - return this.set_proposed_quad(q); - } - } + }; - quads_match(a, b) { - return (a.s === b.s) && (a.p === b.p) && (a.o.value === b.o.value); - } + EditController.prototype.hide = function() { + return $(this.con).hide(); + }; - set_proposed_quad(new_q) { - console.log("set_proposed_quad()"); - // If there is an existing edge remove it before setting a new proposed edge - if (this.proposed_quad) { // There can only be one, so get rid of old proposed edge - this.remove_proposed_quad(); - } - this.add_proposed_quad(new_q); - this.huviz.tick(); // tell the graph to repaint itself - return console.log("Tick in editui.coffee set_proposed_quad"); - } + EditController.prototype.show = function() { + return $(this.con).show(); + }; - add_proposed_quad(q) { - console.log((`add_proposed_quad() ${q.s} ${q.p} ${q.o.value}`)); - const edge = this.huviz.add_quad(q); - if (!edge) { - console.log("error"); //debugger - } - this.huviz.set_proposed_edge(edge); - this.huviz.show_link(edge); - return this.proposed_quad = q; - } + EditController.prototype.on__disable = function() { + this.hide_verbs(); + return this.hide_form(); + }; - remove_proposed_quad() { - const old_edge = this.huviz.proposed_edge; - if (old_edge) { - const edge_id = old_edge.id; - this.huviz.set_proposed_edge(null); - //@huviz.remove_link(edge_id) - //@huviz.unshow_link(old_edge) - this.huviz.delete_edge(old_edge); - } - //delete @huviz.edges_by_id[old_edge] - return this.proposed_quad = null; - } -} -EditController.initClass(); -}, "fsm": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -// FiniteStateMachine implements a simple abstract engine for running state machines. -// -// It supports optional methods for every transition and for become/leav a state. -// -// There are three kinds of methods: -// 1. on__TRANSITID called upon the commencement of the transition -// 2. exit__STATEID called when leaving a state -// 3. enter__STATEID called when becoming a state -// -// All three kinds of methods are optional. If no method of any kind is found -// during a transition then a message is either thrown, logged or ignored based -// on the value of this.throw_log_or_ignore -// -// If there is an array at this.trace then the names of the method are pushed -// onto it as they are called. -// -// # Usage -// -// class MyFSM extends FiniteStateMachine -// constructor: (anything, you want) -> -// # you can do anything you want on your FSM constructor -// throw_log_or_ignore: 'ignore' -// transitions: -// start: -// target: 'ready' -// stop: -// source: 'ready' # TODO respect source by raising error if an illegal transit is tried -// target: 'stopped' -// on__start: -> -// console.log('on "start"') -// exit__ready: -> -// console.log('leave "ready"') -// enter__stopped: -> -// console.log('become "stopped"') -// -// myFSM = new MyFSM() -// myFSM.transit('start') ==> 'on "start"', 'leave "ready"' -// myFSM.get_state() ==> 'ready' -// myFSM.transit('stop') ==> 'become "stopped"' -// - -// Notes: -// suitable for use as a mixin -// https://coffeescript-cookbook.github.io/chapters/classes_and_objects/mixins -class FiniteStateMachine { - call_method_by_name(meth_name) { - let meth; - if (meth = this[meth_name]) { - //if (meth = Reflect.get(this, meth_name)) - meth.call(this); - if (this.trace) { - this.trace.push(meth_name); - } - return true; - } - return false; - } - set_state(state) { - // call a method when arriving at the new state, if it exists - const called = this.call_method_by_name(`enter__${state}`); - this.state = state; // set after calling meth_name so the old state is available to it - return called; - } - exit_state() { - // call a method when leaving the old state, if it exists - return this.call_method_by_name(`exit__${this.state}`); - } - get_state() { - return this.state; - } - is_state(candidate) { - return this.state === candidate; - } - make_noop_msg(trans_id, old_state, new_state) { - return this.constructor.name + " had neither " + - `on__${trans_id} exit__${old_state} or enter__${new_state}`; - } - throw_log_or_ignore_msg(msg) { - const throw_log_or_ignore = this.throw_log_or_ignore || 'ignore'; - if (throw_log_or_ignore === 'throw') { - throw new Error(msg); - } else if (throw_log_or_ignore === 'log') { - console.warn(msg); - } - } - transit(trans_id) { - let transition; - if (this.transitions == null) { this.transitions = {}; } - if (transition = this.transitions[trans_id]) { - let target_id; - const initial_state = this.state; - let called = this.call_method_by_name(`on__${trans_id}`); - called = this.exit_state() || called; - if (target_id = transition.target) { - called = this.set_state(target_id) || called; - } - if (!called) { - const msg = this.make_noop_msg(trans_id, initial_state, target_id); - this.throw_log_or_ignore_msg(msg); + EditController.prototype.on__enable = function() { + this.show_verbs(); + return this.show_form(); + }; + + EditController.prototype.get_verb_set = function() { + return { + connect: this.huviz.human_term.connect, + spawn: this.huviz.human_term.spawn, + specialize: this.huviz.human_term.specialize, + annotate: this.huviz.human_term.annotate + }; + }; + + EditController.prototype.add_verbs = function() { + var prepend, vset; + vset = this.get_verb_set(); + this.huviz.gclui.verb_sets.unshift(vset); + return this.huviz.gclui.add_verb_set(vset, (prepend = true)); + }; + + EditController.prototype.ensure_verbs = function() { + if (!this.my_verbs) { + this.my_verbs = this.add_verbs(); + return this.hide_verbs(); } - } else { - this.throw_log_or_ignore_msg(`${this.constructor.name} has no transition with id ${trans_id}`); - } - } -} + }; -(typeof exports !== 'undefined' && exports !== null ? exports : this).FiniteStateMachine = FiniteStateMachine; -}, "gclui": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS101: Remove unnecessary use of Array.from - * DS102: Remove unnecessary code created because of implicit returns - * DS205: Consider reworking code to avoid use of IIFEs - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ + EditController.prototype.hide_verbs = function() { + return this.my_verbs.style('display', 'none'); + }; -/* - * verbs: choose,label,discard,shelve,unlabel - * classes: writers,others,people,orgs # places,titles - * like: - * ids: - * - * choose,label/unlabel,discard,shelve,expand - * - */ -window.toggle_suspend_updates = function(val) { - console.log("toggle_suspend_updates(#val)"); - if ((window.suspend_updates == null) || !window.suspend_updates) { - window.suspend_updates = true; - } else { - window.suspend_updates = false; - } - if (val != null) { - window.suspend_updates = val; - } - //console.warn "suspend_updates",window.suspend_updates - return window.suspend_updates; -}; -const getRandomId = function(prefix) { - const max = 10000000000; - prefix = prefix || 'id'; - return prefix + Math.floor(Math.random() * Math.floor(max)); -}; + EditController.prototype.show_verbs = function() { + return this.my_verbs.style('display', 'flex'); + }; -const gcl = require('graphcommandlanguage'); -const { ColoredTreePicker } = require('coloredtreepicker'); -const { QueryManager } = require('querymanager'); -const { TreePicker } = require('treepicker'); - -class CommandController { - static initClass() { - //, - // print: 'print' - // redact: 'redact' - // peek: 'peek' - //, # FIXME the edge related commands must be reviewed - // show: 'reveal' - // suppress: 'suppress' - // specify: 'specify' - //emphasize: 'emphasize' - - this.prototype.auto_change_verb_tests = { - select(node) { - if (node.selected != null) { - return 'unselect'; - } - }, - unselect(node) { - if ((node.selected == null)) { - return 'select'; - } - }, - choose(node) { - if (node.chosen != null) { - return 'unchoose'; - } - }, - unchoose(node, engagedVerb) { - if ((node.chosen == null)) { - return 'choose' || engagedVerb; - } - }, - wander(node) { - if (node.chosen != null) { - return 'wander'; - } - }, - walk(node) { - if (node.chosen != null) { - return 'walk'; - } - }, - label(node) { - if (node.labelled) { - return 'unlabel'; - } - }, - unlabel(node) { - if (!node.labelled) { - return 'label'; - } - }, - unpin(node) { - if (!node.fixed) { - return 'pin'; - } - }, - pin(node) { - if (node.fixed) { - return 'unpin'; + EditController.prototype.create_edit_form = function(toggleEdit) { + var formNode; + formNode = document.createElement('form'); + formNode.classList.add("cntrl-set", "edit-form"); + formNode.innerHTML = ''; + formNode.innerHTML += ''; + formNode.innerHTML += ''; + toggleEdit.appendChild(formNode); + return this.set_predicate_selector(); + }; + + EditController.prototype.set_predicate_selector = function() { + var availablePredicates, predicate, _i, _len, _ref; + availablePredicates = []; + if (this.huviz.predicate_set) { + _ref = this.huviz.predicate_set; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + predicate = _ref[_i]; + availablePredicates.push(predicate.lid); } + availablePredicates.push("literal"); + } else { + availablePredicates = ["A", "literal"]; } + return $("#predicate").autocomplete({ + source: availablePredicates, + open: this.update_predicate_picked, + close: this.update_predicate_picked, + change: this.update_predicate_picked, + position: { + my: "left bottom", + at: "left top" + } + }); }; - this.prototype.verbs_requiring_regarding = - ['show','suppress','emphasize','deemphasize']; - this.prototype.verbs_override = { // when overriding ones are selected, others are unselected - choose: ['discard', 'unchoose', 'shelve', 'hide', 'wander', 'walk'], - wander: ['choose', 'unchoose', 'discard', 'shelve', 'hide', 'walk'], - walk: ['choose', 'unchoose', 'discard', 'shelve', 'hide', 'wander'], - shelve: ['unchoose', 'choose', 'hide', 'discard', 'retrieve', 'wander', 'walk'], - discard: ['choose', 'retrieve', 'hide', 'unchoose', 'unselect', 'select', 'wander', 'walk'], - hide: ['discard', 'undiscard', 'label', 'choose' ,'unchoose', 'select', 'unselect', 'wander', 'walk'], - hunt: ['discard', 'undiscard', 'choose', 'unchoose', 'wander', 'walk', 'hide', 'unhide', 'shelve', 'pin', 'unpin'] - }; - this.prototype.verb_descriptions = { - choose: `Put nodes in the graph and pull other, connected nodes in too, \ -so long as they haven't been discarded.`, - wander: `Put nodes in the graph and pull connected nodes in followed by \ -shelving of the nodes which had been pulled into the graph previously.`, - walk: `Put nodes in the graph but keep the previous central nodes activated. \ -Shelve previous sub-nodes.`, - shelve: `Remove nodes from the graph and put them on the shelf \ -(the circle of nodes around the graph) from which they \ -might return if called back into the graph by a neighbor \ -being chosen.`, - hide: `Remove nodes from the graph and don't display them anywhere, \ -though they might be called back into the graph when some \ -other node calls it back in to show an edge.`, - label: "Show the node's labels.", - unlabel: "Stop showing the node's labels.", - discard: `Put nodes in the discard bin (the small red circle which appears \ -when you start dragging a node) from which they do not get \ -called back into the graph unless they are first retrieved.`, - undiscard: `Retrieve nodes from the discard bin (the small red circle \ -which appears when you start dragging a node)) \ -and put them back on the shelf.`, - print: "Print associated snippets.", - redact: "Hide the associated snippets.", - show: `Show edges: 'Show (nodes) regarding (edges).' \ -Add to the existing state of the graph edges from nodes of \ -the classes indicated edges of the types indicated.`, - suppress: `Stop showing: 'Suppress (nodes) regarding (edges).' \ -Remove from the existing sate of the graph edges of the types \ -indicated from nodes of the types classes indicated.`, - specify: `Immediately specify the entire state of the graph with \ -the constantly updating set of edges indicated from nodes \ -of the classes indicated.`, - load: "Load knowledge from the given uri.", - pin: "Make a node immobile", - unpin: "Make a node mobile again", - hunt: "Animate binary search for the node" + + EditController.prototype.update_predicate_picked = function(event, ui) { + var new_pred_value; + new_pred_value = this.predicate_input.value; + console.log("" + new_pred_value + " is new predicate"); + return this.validate_proposed_edge(); }; - this.prototype.verb_cursors = { - choose: "←", - unchoose: "⇠", - wander: "🚶", - walk: "🚶", - shelve: "↺", - label: "☭", - unlabel: "☢", - discard: "☣", - undiscard: "☯", - hide: "☠", - select: "☘", - unselect: "☺", - pin: "p", - unpin: "u", - hunt: "X" + + EditController.prototype.hide_form = function() { + this.con.setAttribute("edit", "no"); + return this.con.classList.remove("edit-mode"); }; - - this.prototype.working_timeout = 500; - this.prototype.nextcommand_prompts_visible = true; - this.prototype.nextcommand_str_visible = false; - this.prototype.engaged_verbs = []; - this.prototype.verb_control = {}; - } - constructor(huviz, container, hierarchy) { - this.on_downloadscript_json_clicked = this.on_downloadscript_json_clicked.bind(this); - this.on_downloadscript_txt_clicked = this.on_downloadscript_txt_clicked.bind(this); - this.on_downloadscript_hybrid_clicked = this.on_downloadscript_hybrid_clicked.bind(this); - this.on_downloadscript_type = this.on_downloadscript_type.bind(this); - this.on_stashscript_clicked = this.on_stashscript_clicked.bind(this); - this.on_rewind_click = this.on_rewind_click.bind(this); - this.on_backward_click = this.on_backward_click.bind(this); - this.on_forward_click = this.on_forward_click.bind(this); - this.on_fastforward_click = this.on_fastforward_click.bind(this); - this.on_dataset_loaded = this.on_dataset_loaded.bind(this); - this.select_the_initial_set = this.select_the_initial_set.bind(this); - this.NEW_select_the_initial_set = this.NEW_select_the_initial_set.bind(this); - this.OLD_select_the_initial_set = this.OLD_select_the_initial_set.bind(this); - this.handle_newpredicate = this.handle_newpredicate.bind(this); - this.recolor_edges_and_predicates = this.recolor_edges_and_predicates.bind(this); - this.add_predicate = this.add_predicate.bind(this); - this.handle_on_predicate_clicked = this.handle_on_predicate_clicked.bind(this); - this.on_predicate_clicked = this.on_predicate_clicked.bind(this); - this.recolor_edges = this.recolor_edges.bind(this); - this.add_taxon = this.add_taxon.bind(this); - this.onChangeEnglish = this.onChangeEnglish.bind(this); - this.handle_on_taxon_clicked = this.handle_on_taxon_clicked.bind(this); - this.on_taxon_clicked = this.on_taxon_clicked.bind(this); - this.stop_working = this.stop_working.bind(this); - this.handle_clear_like = this.handle_clear_like.bind(this); - this.handle_like_input = this.handle_like_input.bind(this); - this.disengage_all_verbs = this.disengage_all_verbs.bind(this); - this.push_future_onto_history = this.push_future_onto_history.bind(this); - this.update_command = this.update_command.bind(this); - this.perform_current_command = this.perform_current_command.bind(this); - this.handle_on_verb_clicked = this.handle_on_verb_clicked.bind(this); - this.handle_on_set_picked = this.handle_on_set_picked.bind(this); - this.disengage_all_sets = this.disengage_all_sets.bind(this); - this.clear_all_sets = this.clear_all_sets.bind(this); - this.on_set_count_update = this.on_set_count_update.bind(this); - this.huviz = huviz; - this.container = container; - this.hierarchy = hierarchy; - if (!this.huviz.all_set.length) { - $(this.container).hide(); - } - d3.select(this.container).html(""); - if (this.huviz.args.display_hints) { - this.hints = d3.select(this.container).append("div").attr("class","hints"); - $(".hints").append($(".hint_set").contents()); - } - this.style_context_selector = this.huviz.get_picker_style_context_selector(); - this.make_command_history(); - this.prepare_tabs_sparqlQueries(); - this.control_label("Current Command"); - this.nextcommandbox = this.comdiv.append('div'); - this.make_verb_sets(); - this.control_label("Verbs"); - this.verbdiv = this.comdiv.append('div').attr('class','verbs'); - this.depthdiv = this.comdiv.append('div'); - this.add_clear_both(this.comdiv); - //@node_pickers = @comdiv.append('div') - this.node_pickers = this.comdiv.append('div').attr("id","node_pickers"); - this.set_picker_box_parent = this.build_set_picker("Sets",this.node_pickers); - this.taxon_picker_box_parent = this.build_taxon_picker("Class Selector",this.node_pickers); - this.add_clear_both(this.comdiv); - this.likediv = this.taxon_picker_box_parent.append('div'); - this.build_predicate_picker("Edges of the Selected Nodes"); - this.init_editor_data(); - this.build_form(); - this.update_command(); - this.install_listeners(); - } - control_label(txt, what, title) { - what = what || this.comdiv; - const outer = what.append('div'); - const label = outer.append('div'); - label.classed("control_label",true).text(txt); - if (title) { - label.attr('title',title); - } - return outer; - } - new_GraphCommand(args) { - return new gcl.GraphCommand(this.huviz, args); - } - reset_graph() { - /* - * unhide all - * retrieve all - * shelve all - * sanity check set counts - */ - //@huviz.run_command(@new_GraphCommand( - // verbs: ['unhide'] - // sets: [@huviz.all_set] - // skip_history: true)) - this.huviz.walkBackAll(); - this.huviz.walk_path_set = []; - this.huviz.run_command(this.new_GraphCommand({ - verbs: ['undiscard','unchoose','unselect', 'unpin', 'shelve','unlabel'], - sets: [this.huviz.all_set.id], - skip_history: true})); - this.disengage_all_verbs(); - this.reset_command_history(); - return this.engaged_taxons = []; - } - prepare_tabs_sparqlQueries() { - // populate @huviz.tabs_sparqlQueries_JQElem with needed furniture - } - push_sparqlQuery_onto_log(qry, meta) { - if (meta == null) { meta = {}; } - if (meta.timestamp == null) { meta.timestamp = Date.now(); } - const id = meta.id || this.huviz.hash(qry + meta.timestamp); - const queriesJQElem = this.huviz.tabs_sparqlQueries_JQElem; - const qryJQElem = $('
'); - qryJQElem.attr('id', id); - queriesJQElem.append(qryJQElem); - const preJQElem = qryJQElem.find('pre'); - const preElem = preJQElem[0]; - preJQElem.text(qry); // rely on text() doing HTML encoding (to protect <, >, etc ) - queriesJQElem.scrollTop(10000); - const queryManager = new QueryManager(qry); - return Object.assign(queryManager, {qryJQElem, preJQElem, preElem}); - } - make_command_history() { - this.comdiv = d3.select(this.container).append("div"); // --- Add a container - const history = d3.select(this.huviz.oldToUniqueTabSel['tabs-history']); - this.cmdtitle = history. - append('div'). - attr('class','control_label'). - html('Command History'). - attr('style', 'display:inline'); - this.scriptPlayerControls = history.append('div').attr('class','scriptPlayerControls'); - // attr('style','position: relative; float:right') - - this.scriptRewindButton = this.scriptPlayerControls.append('button'). - attr('title','rewind to start'). - attr('disabled', 'disabled').on('click', this.on_rewind_click); - this.scriptRewindButton.append('i'). - attr("class", "fa fa-fast-backward"); - - this.scriptBackButton = this.scriptPlayerControls.append('button'). - attr('title','go back one step'). - attr('disabled', 'disabled').on('click', this.on_backward_click); - this.scriptBackButton.append('i').attr("class", "fa fa-play fa-flip-horizontal"); - - this.scriptPlayButton = this.scriptPlayerControls.append('button'). - attr('title','play script step by step'). - attr('disabled', 'disabled').on('click', this.on_forward_click); - this.scriptPlayButton.append('i').attr("class", "fa fa-play"); - - this.scriptForwardButton = this.scriptPlayerControls.append('button'). - attr('title','play script continuously'). - attr('disabled', 'disabled').on('click', this.on_fastforward_click); - this.scriptForwardButton.append('i').attr("class", "fa fa-fast-forward"); - - this.scriptDownloadButton = this.scriptPlayerControls.append('button'). - attr('title','save script to file'). - attr('style', 'margin-left:1em'). // ;display:none - attr('disabled', 'disabled').on('click', this.on_downloadscript_hybrid_clicked); - this.scriptDownloadButton.append('i').attr("class", "fa fa-download"); - //.append('span').text('.txt') - - this.scriptDownloadJsonButton = this.scriptPlayerControls.append('button'). - attr('title','save script as .json'). - attr('style', 'display:none').on('click', this.on_downloadscript_json_clicked); - this.scriptDownloadJsonButton.append('i').attr("class", "fa fa-download"). - append('span').text('.json'); - - this.scriptStashButton = this.scriptPlayerControls.append('button'). - attr('title','save script to menu'). - attr('disabled', 'disabled'). - attr('style', 'margin-left:.1em').on('click', this.on_stashscript_clicked); - this.scriptStashButton.append('i').attr("class", "fa fa-bars"); - //.append('span').text('save to menu') - - this.cmdlist = history. - append('div'). - attr('class','commandlist'); - this.oldcommands = this.cmdlist. - append('div'). - attr('class','commandhistory'). - style('max-height', `${this.huviz.height-80}px`); - this.commandhistoryElem = this.huviz.topElem.querySelector('.commandhistory'); - this.commandhistory_JQElem = $(this.commandhistoryElem); - this.future_cmdArgs = []; - this.command_list = []; - return this.command_idx0 = 0; - } + EditController.prototype.show_form = function() { + this.con.setAttribute("edit", "yes"); + return this.con.classList.add("edit-mode"); + }; - reset_command_history() { - return Array.from(this.command_list).map((record) => - record.elem.attr('class','command')); - } - get_downloadscript_name(ext) { - return this.lastScriptName || (`HuVizScript.${ext}`); - } - get_script_prefix() { - return [ - "#!/bin/env huviz", - "# This HuVis script file was generated by the page:", - `# ${this.huviz.get_reload_uri()}`, - `# Generated at ${(new Date()).toISOString()}`, - "", - "" - ].join("\n"); - } - get_script_body() { - return this.get_script_prefix() + this.oldcommands.text(); - } - get_script_body_as_json() { - const cmdList = []; - if (this.huviz.dataset_loader.value) { - cmdList.push({ - verbs: ['load'], - data_uri: this.huviz.dataset_loader.value, - ontologies: [this.huviz.ontology_loader.value], - skip_history: true - }); - } - for (let elem_and_cmd of Array.from(this.command_list)) { - const { cmd } = elem_and_cmd; - cmdList.push(cmd.args_or_str); - } - const replacer = function(key, value) { - // replacer() removes non-literals from GraphCommand.args_or_script for serialization - const retlist = []; - if (key === 'subjects') { - for (let node_or_id of Array.from(value)) { - var obj; - if (!node_or_id.id) { - console.debug("expecting node_or_id to have attribute .id", node_or_id); - } - if (node_or_id.id && node_or_id.lid) { - // ideally send both the id (ie url) and the lid which is the pretty id - obj = { - id: node_or_id.id, - lid: node_or_id.lid - }; - } - retlist.push(obj || node_or_id); - } - return retlist; + EditController.prototype.toggle_edit_form = function() { + var toggleEditMode; + toggleEditMode = this.con.getAttribute("edit"); + if (toggleEditMode === 'no') { + this.show_verbs(); + this.show_form(); + } + if (toggleEditMode === 'yes') { + this.hide_verbs(); + return this.hide_form(); } - if (key === 'sets') { - for (let set_or_id of Array.from(value)) { - const setId = set_or_id.id || set_or_id; - retlist.push(setId); + }; + + EditController.prototype.validate_edit_form = function(evt) { + var elem, form, i, inputFields, saveButton, _i, _ref; + form = this.controls; + inputFields = form.getElementsByTagName('input'); + saveButton = form.getElementsByTagName('button')[0]; + for (i = _i = 0, _ref = inputFields.length - 1; 0 <= _ref ? _i <= _ref : _i >= _ref; i = 0 <= _ref ? ++_i : --_i) { + elem = form.elements[i]; + if (elem.value === '') { + saveButton.disabled = 'disabled'; + break; + } else { + saveButton.disabled = false; } - return retlist; } - return value; + return this.adjust_object_datatype(); }; - return JSON.stringify(cmdList, replacer, 4); - } - get_script_body_as_hybrid() { - // The "hybrid" script style consists of three parts - // 1) the text version of the script - // 2) the json_marker, a separator between the two parts - // 3) the json version of the script - return this.get_script_body() + - "\n\n" + this.huviz.json_script_marker + - "\n\n" + this.get_script_body_as_json(); - } - make_txt_script_href() { - const theBod = encodeURIComponent(this.get_script_body()); - const theHref = `data:text/plain;charset=utf-8,${theBod}`; - return theHref; - } - make_json_script_href() { - const theJSON = encodeURIComponent(this.get_script_body_as_json()); - const theHref = `data:text/json;charset=utf-8,${theJSON}`; - return theHref; - } - make_hybrid_script_href() { - const theBod = encodeURIComponent(this.get_script_body_as_hybrid()); - const theHref = `data:text/plain;charset=utf-8,${theBod}`; - return theHref; - } - on_downloadscript_json_clicked() { - this.on_downloadscript_type('json'); - } - on_downloadscript_txt_clicked() { - this.on_downloadscript_type('txt'); - } - on_downloadscript_hybrid_clicked() { - this.on_downloadscript_type('hybrid', 'txt'); - } - on_downloadscript_type(scriptFileType, ext) { - let theHref; - const transientLink = this.scriptPlayerControls.append('a'); - transientLink.text('script'); - const thisName = prompt("What would you like to call your saved script?", - this.get_downloadscript_name(ext || scriptFileType)); - if (!thisName) { - return; - } - this.lastScriptName = thisName; - transientLink.attr('style','display:none'); - transientLink.attr('download', this.lastScriptName); - if (scriptFileType === 'json') { - theHref = this.make_json_script_href(); - } else if (scriptFileType === 'txt') { - theHref = this.make_txt_script_href(); - } else if (scriptFileType === 'hybrid') { - theHref = this.make_hybrid_script_href(); - } - transientLink.attr('href',theHref); - transientLink.node().click(); - const node = transientLink.node(); - node.parentNode.removeChild(node); - } - on_stashscript_clicked() { - const scriptFileType = 'hybrid'; - const ext = 'txt'; - const thisName = prompt("What would you like to call this script in your menu?", - this.get_downloadscript_name(ext || scriptFileType)); - if (!thisName) { - return; - } - this.lastScriptName = thisName; - const script_rec = { - uri: thisName, - opt_group: 'Your Own', - data: this.get_script_body_as_hybrid() + + EditController.prototype.predicate_is_DatatypeProperty = function() { + var current_value; + if (this.predicate_input) { + window.THINGY = this.predicate_input; + current_value = this.predicate_input.value; + return current_value === 'literal'; + } + return false; }; - this.huviz.script_loader.add_local_file(script_rec); - } - on_rewind_click() { - this.reset_graph(); - this.command_idx0 = 0; - return this.update_script_buttons(); - } - on_backward_click() { - const forward_to_idx = this.command_idx0 - 1; - this.on_rewind_click(); - return this.on_fastforward_click(forward_to_idx); - } - on_forward_click() { - this.play_old_command_by_idx(this.command_idx0); - this.command_idx0++; - return this.update_script_buttons(); - } - on_fastforward_click(forward_to_idx) { - if (forward_to_idx == null) { forward_to_idx = this.command_list.length; } - return (() => { - const result = []; - while (this.command_idx0 < forward_to_idx) { - result.push(this.on_forward_click()); + + EditController.prototype.adjust_object_datatype = function() { + var placeholder_label; + if (this.predicate_is_DatatypeProperty()) { + this.object_datatype_is_literal = true; + placeholder_label = "a literal value"; + } else { + this.object_datatype_is_literal = false; + placeholder_label = "object"; } - return result; - })(); - } - play_old_command_by_idx(idx) { - const record = this.command_list[idx]; - record.elem.attr('class', 'command played'); - return this.play_old_command(record.cmd); - } - play_old_command(cmd) { - cmd.skip_history = true; - cmd.skip_history_remove = true; - return this.huviz.run_command(cmd); - } - install_listeners() { - window.addEventListener('changePredicate', this.predicate_picker.onChangeState); - window.addEventListener('changeTaxon', this.taxon_picker.onChangeState); - return window.addEventListener('changeEnglish', this.onChangeEnglish); - } - on_dataset_loaded(evt) { - if ((evt.done == null)) { - $(this.container).show(); - this.show_succession_of_hints(); - this.huviz.perform_tasks_after_dataset_loaded(); - this.huviz.hide_state_msg(); - // FIXME is there a standards-based way to prevent this happening three times? - return evt.done = true; - } - } - show_succession_of_hints() { - // Show the reminders, give them close buttons which reveal them in series - $(".hints.hint_set").show(); - for (let reminder of Array.from($(".hints > .a_hint"))) { - $(reminder).attr('style','position:relative'); - $(reminder).append(''). - on("click", (evt,ui) => { - $(evt.target).parent().hide(); // hide reminder whose close was clicked - if ($(evt.target).parent().next()) { // is there a next another - $(evt.target).parent().next().show(); // then show it - } - return false; - }); - } // so not all close buttons are pressed at once - $(".hints > .a_hint").hide(); - return $(".hints > .a_hint").first().show(); - } - select_the_initial_set() { - this.OLD_select_the_initial_set(); - } - NEW_select_the_initial_set() { - // this does NOT function as a workaround for the problem like OLD_select_the_initial_set - this.huviz.run_command(this.new_GraphCommand({ - verbs: ['select'], - every_class: true, - classes: ['Thing'], - skip_history: true})); - this.huviz.run_command(this.new_GraphCommand({ - verbs: ['unselect'], - every_class: true, - classes: ['Thing'], - skip_history: true})); - this.huviz.shelved_set.resort(); // TODO remove when https://github.com/cwrc/HuViz/issues/109 - } - OLD_select_the_initial_set() { - // TODO initialize the taxon coloring without cycling all - const rm_cmd = () => { // more hideous hackery: remove toggleTaxonThing from script - return this.delete_script_command_by_idx(0); - }; - const toggleEveryThing = () => { - this.huviz.toggle_taxon("Thing", false); //, () -> alert('called')) - return setTimeout(rm_cmd, 1000); - }; - toggleEveryThing.call(); - // everyThingIsSelected = () => - // @huviz.nodes.length is @huviz.selected_set.length - // @check_until_then(everyThingIsSelected, toggleEveryThing) - setTimeout(toggleEveryThing, 1200); - setTimeout(this.push_future_onto_history, 1800); - //@huviz.do({verbs: ['unselect'], sets: [], skip_history: true}) - this.huviz.shelved_set.resort(); // TODO remove when https://github.com/cwrc/HuViz/issues/109 - } - check_until_then(checkCallback, thenCallback) { - let intervalId; - const nag = () => { - if (checkCallback.call()) { - clearInterval(intervalId); - //alert('check_until_then() is done') - return thenCallback.call(); + return this.object_input.setAttribute("placeholder", placeholder_label); + }; + + EditController.prototype.save_edit_form = function() { + var assrtSave, elem, form, i, inputFields, quad, saveButton, tuple, _i, _ref; + form = this.controls; + inputFields = form.getElementsByTagName('input'); + tuple = []; + for (i = _i = 0, _ref = inputFields.length - 1; 0 <= _ref ? _i <= _ref : _i >= _ref; i = 0 <= _ref ? ++_i : --_i) { + elem = form.elements[i]; + console.log(elem.name + ": " + elem.value); + tuple.push(elem.value); + } + assrtSave = new indexdDBstore.IndexedDBStorageController(this.huviz); + console.log(assrtSave); + quad = { + s: tuple[0], + p: tuple[1], + o: tuple[2] + }; + this.latest_quad = quad; + this.huviz.set_proposed_edge(null); + saveButton = form.getElementsByTagName('button')[0]; + for (i in inputFields) { + form.elements[i].value = ''; } + return saveButton.disabled = true; }; - return intervalId = setInterval(nag, 30); - } - init_editor_data() { - // operations common to the constructor and reset_editor - this.shown_edges_by_predicate = {}; - this.unshown_edges_by_predicate = {}; - return this.engaged_taxons = []; // new SortedSet() - } - reset_editor() { - this.clear_like(); - this.disengage_all_verbs(); - this.disengage_all_sets(); - this.clear_all_sets(); - this.init_editor_data(); - return this.update_command(); - } - disengage_command() { - this.clear_like(); - this.disengage_all_verbs(); - this.disengage_all_sets(); - return this.update_command(); - } - disengage_all() { - this.clear_like(); - this.disengage_all_sets(); - this.disengage_all_verbs(); - return this.update_command(); - } - add_clear_both(target) { - // keep taxonomydiv from being to the right of the verbdiv - return target.append('div').attr('style','clear:both'); - } - ignore_predicate(pred_id) { - return this.predicates_ignored.push(pred_id); - } - handle_newpredicate(e) { - const { pred_uri } = e.detail; - const { parent_lid } = e.detail; - const { pred_lid } = e.detail; - let { pred_name } = e.detail; - if (!Array.from(this.predicates_ignored).includes(pred_uri)) { // FIXME merge with predicates_to_ignore - if (!Array.from(this.predicates_ignored).includes(pred_lid)) { // FIXME merge with predicates_to_ignore - if (pred_name == null) { pred_name = pred_lid.match(/([\w\d\_\-]+)$/g)[0]; } - this.add_predicate(pred_lid, parent_lid, pred_name); - return this.recolor_edges_and_predicates_eventually(e); + + EditController.prototype.clear_edit_form = function() { + var form, i, inputFields, saveButton; + form = this.controls; + inputFields = form.getElementsByTagName('input'); + saveButton = form.getElementsByTagName('button')[0]; + for (i in inputFields) { + form.elements[i].value = ''; + } + if (this.proposed_quad) { + console.log("@proposed_quad:", this.proposed_quad); + this.remove_proposed_quad(); + } + this.set_subject_node(); + this.set_object_node(); + return saveButton.disabled = true; + }; + + EditController.prototype.set_subject_node = function(node) { + var new_value; + if (this.subject_node === node) { + return; } - } - } - recolor_edges_and_predicates_eventually() { - if (this.recolor_edges_and_predicates_eventually_id != null) { - // console.log "defer edges_and_predicates",@recolor_edges_and_predicates_eventually_id - clearTimeout(this.recolor_edges_and_predicates_eventually_id); - } - return this.recolor_edges_and_predicates_eventually_id = setTimeout(this.recolor_edges_and_predicates, 300); - } - recolor_edges_and_predicates(evt) { - this.predicate_picker.recolor_now(); - return this.recolor_edges(); // FIXME should only run after the predicate set has settled for some time - } - resort_pickers() { - if (this.taxon_picker != null) { - // propagate the labels according to the currently preferred language - this.taxon_picker.resort_recursively(); - this.taxon_picker.recolor_now(); - this.huviz.recolor_nodes(); - } - if (this.predicate_picker != null) { - console.log("resorting of predicate_picker on hold until it does not delete 'anything'"); - } - //@predicate_picker?.resort_recursively() - //@set_picker?.resort_recursively() - } - build_predicate_picker(label) { - let extra_classes, needs_expander, squash_case, use_name_as_label; - this.predicates_id = this.huviz.unique_id('predicates_'); - const title = - "Medium color: all edges shown -- click to show none\n" + - "Faint color: no edges are shown -- click to show all\n" + - "Stripey color: some edges shown -- click to show all\n" + - "Hidden: no edges among the selected nodes"; - const where = ((label != null) && this.control_label(label,this.comdiv,title)) || this.comdiv; - this.predicatebox = where.append('div') - .classed('container', true) - .attr('id', this.predicates_id); - //@predicatebox.attr('class','scrolling') - this.predicates_ignored = []; - this.predicate_picker = new ColoredTreePicker( - this.predicatebox, 'anything', - (extra_classes=[]), - (needs_expander=true), - (use_name_as_label=true), - (squash_case=true), - this.style_context_selector); - this.predicate_hierarchy = {'anything':['anything']}; - // FIXME Why is show_tree being called four times per node? - this.predicate_picker.click_listener = this.handle_on_predicate_clicked; - this.predicate_picker.show_tree(this.predicate_hierarchy, this.predicatebox); - this.predicates_JQElem = $(this.predicates_id); - this.predicates_JQElem.addClass("predicates ui-resizable").append("
"); - return this.predicates_JQElem.resizable({handles: 's'}); - } - add_predicate(pred_lid, parent_lid, pred_name) { - //if pred_lid in @predicates_to_ignore - // return - this.predicate_picker.add(pred_lid, parent_lid, pred_name, this.handle_on_predicate_clicked); - return this.make_predicate_proposable(pred_lid); - } - make_predicate_proposable(pred_lid) { - const predicate_ctl = this.predicate_picker.id_to_elem[pred_lid]; - predicate_ctl.on('mouseenter', () => { - const every = !!this.predicate_picker.id_is_collapsed[pred_lid]; - const nextStateArgs = this.predicate_picker.get_next_state_args(pred_lid); - if (nextStateArgs.new_state === 'showing') { - this.proposed_verb = 'draw'; - } else { - this.proposed_verb = 'undraw'; + this.subject_node = node; + new_value = node && node.id || ""; + console.log("set_subject_node() id:'" + new_value + "'"); + this.subject_input.setAttribute("value", new_value); + this.validate_edit_form(); + return this.validate_proposed_edge(); + }; + + EditController.prototype.set_object_node = function(node) { + var new_value; + if (this.object_node === node) { + return; } - this.regarding = [pred_lid]; - this.regarding_every = !!this.predicate_picker.id_is_collapsed[pred_lid]; - const ready = this.prepare_command(this.build_command()); - }); - return predicate_ctl.on('mouseleave', () => { - this.proposed_verb = null; - this.regarding = null; - this.prepare_command(this.build_command()); - //@prepare_command(@new_GraphCommand( {})) - }); - } - handle_on_predicate_clicked(pred_id, new_state, elem, args) { - this.start_working(); - return setTimeout(() => { // run asynchronously so @start_working() can get a head start - return this.on_predicate_clicked(pred_id, new_state, elem, args); - }); - } - on_predicate_clicked(pred_id, new_state, elem, args) { - let verb; - const skip_history = !args || !args.original_click; - if (new_state === 'showing') { - verb = 'draw'; - } else { - verb = 'undraw'; - } - const cmd = this.new_GraphCommand({ - verbs: [verb], - regarding: [pred_id], - regarding_every: !!this.predicate_picker.id_is_collapsed[pred_id], - sets: [this.huviz.selected_set.id], - skip_history}); - this.prepare_command(cmd); - return this.huviz.run_command(this.command); - } - recolor_edges(evt) { - let count = 0; - return Array.from(this.huviz.all_set).map((node) => - (() => { - const result = []; - for (let edge of Array.from(node.links_from)) { - count++; - const pred_n_js_id = edge.predicate.id; - result.push(edge.color = this.predicate_picker.get_color_forId_byName(pred_n_js_id, 'showing')); - } - return result; - })()); - } - build_taxon_picker(label, where) { - let extra_classes, needs_expander, squash_case, use_name_as_label; - const id = 'classes'; - const title = - "Medium color: all nodes are selected -- click to select none\n" + - "Faint color: no nodes are selected -- click to select all\n" + - "Stripey color: some nodes are selected -- click to select all\n"; - where = ((label != null) && this.control_label(label, where, title)) || this.comdiv; - this.taxon_box = where.append('div') - .classed('container', true) - .attr('id', id); - this.taxon_box.attr('style','vertical-align:top'); - // http://en.wikipedia.org/wiki/Taxon - this.taxon_picker = new ColoredTreePicker( - this.taxon_box, 'Thing', - // documenting meaning of positional params with single use variables - (extra_classes=[]), - (needs_expander=true), - (use_name_as_label=true), - (squash_case=true), - this.style_context_selector); - this.taxon_picker.click_listener = this.handle_on_taxon_clicked; - this.taxon_picker.hover_listener = this.on_taxon_hovered; - this.taxon_picker.show_tree(this.hierarchy, this.taxon_box); - where.classed("taxon_picker_box_parent", true); - return where; - } - add_taxon(taxon_id, parent_lid, class_name, taxon) { - this.taxon_picker.add(taxon_id, parent_lid, class_name, this.handle_on_taxon_clicked); - this.make_taxon_proposable(taxon_id); - this.taxon_picker.recolor_now(); - return this.huviz.recolor_nodes(); - } - make_taxon_proposable(taxon_id) { - const taxon_ctl = this.taxon_picker.id_to_elem[taxon_id]; - taxon_ctl.on('mouseenter', evt => { - //evt.stopPropagation() - // REVIEW consider @taxon_picker.get_next_state_args(taxon_id) like make_predicate_proposable() - this.proposed_taxon = taxon_id; - this.proposed_every = !!this.taxon_picker.id_is_collapsed[taxon_id]; - if (!this.engaged_verbs.length) { - // only presume that select/unselect is what is happening when no other verbs are engaged - if (this.engaged_taxons.includes(taxon_id)) { - this.proposed_verb = 'unselect'; - } else { - this.proposed_verb = 'select'; + this.object_node = node; + new_value = node && node.id || ""; + console.log("set_object_node() id:'" + new_value + "'"); + this.object_input.setAttribute("value", new_value); + this.validate_edit_form(); + return this.validate_proposed_edge(); + }; + + EditController.prototype.validate_proposed_edge = function() { + var RDF_literal, RDF_object, obj_type, object_id, predicate_val, q, subject_id; + console.log('validate_proposed_edge()'); + RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; + RDF_literal = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; + subject_id = this.subject_input.value; + object_id = this.object_input.value; + predicate_val = this.predicate_input.value; + if (subject_id && object_id) { + obj_type = predicate_val === 'literal' ? RDF_literal : RDF_object; + q = { + s: subject_id, + p: predicate_val || "anything", + o: { + type: obj_type, + value: object_id + }, + g: "http://" + Date.now() + }; + if ((this.proposed_quad != null) && this.quads_match(q, this.proposed_quad)) { + console.log("... skipping: matches old"); + return; } + console.log("... accepting: "); + return this.set_proposed_quad(q); } - //console.log(@proposed_verb, @proposed_taxon) - const ready = this.prepare_command(this.build_command()); - }); - taxon_ctl.on('mouseleave', evt => { - this.proposed_taxon = null; - this.proposed_verb = null; - const ready = this.prepare_command(this.build_command()); - }); - } - onChangeEnglish(evt) { - this.object_phrase = evt.detail.english; - //console.log("%c#{@object_phrase}",'color:orange;font-size:2em') - this.prepare_command(this.build_command()); - return this.update_command(); - } - handle_on_taxon_clicked(id, new_state, elem, args) { - this.start_working(); - return setTimeout(() => { // run asynchronously so @start_working() can get a head start - return this.on_taxon_clicked(id, new_state, elem, args); - }); - } - set_taxa_click_storm_callback(callback) { - if (this.taxa_click_storm_callback != null) { - throw new Error("taxa_click_storm_callback already defined"); - } else { - return this.taxa_click_storm_callback = callback; - } - } - taxa_being_clicked_increment() { - if ((this.taxa_being_clicked == null)) { - this.taxa_being_clicked = 0; - } - this.taxa_being_clicked++; - } - taxa_being_clicked_decrement() { - if ((this.taxa_being_clicked == null)) { - throw new Error("taxa_being_clicked_decrement() has apparently been called before taxa_being_clicked_increment()"); - } - //@taxa_being_clicked ?= 1 - //console.log("taxa_being_clicked_decrement() before:", @taxa_being_clicked) - this.taxa_being_clicked--; - //console.log("taxa_being_clicked_decrement() after:", @taxa_being_clicked) - if (this.taxa_being_clicked === 0) { - //console.log("taxa click storm complete after length #{@taxa_click_storm_length}") - //debugger if @taxa_click_storm_callback? - if (this.taxa_click_storm_callback != null) { - this.taxa_click_storm_callback.call(document); - return this.taxa_click_storm_callback = null; - } - } - } - //@taxa_click_storm_length = 0 - //else - // blurt(@taxa_being_clicked, null, true) - // @taxa_click_storm_length ?= 0 - // @taxa_click_storm_length++ - // - make_run_transient_and_cleanup_callback(because) { - return err => { - if (err) { - console.log(err); - throw err; - } - this.huviz.clean_up_all_dirt(); - this.run_any_immediate_command({}); - this.perform_any_cleanup(because); }; - } - on_taxon_clicked(taxonId, new_state, elem, args) { - let cmd, old_state; - if (args == null) { args = {}; } - // This method is called in various contexts: - // 1) aVerb ______ . Engage a taxon, run command, disengage taxon - // 2) _____ ______ . Engage a taxon - // 3) _____ aTaxon . Disengage a taxon - // 4) _____ a and b . Engage or disenage a taxon - - // These variables are interesting regardless of which scenario holds - const taxon = this.huviz.taxonomy[taxonId]; - const hasVerbs = !!this.engaged_verbs.length; - const skip_history = !args.original_click; - const every_class = !!args.collapsed; // force boolean value and default false - // If there is already a verb engaged then this click should be running - // EngagedVerb taxonWith_id . - // In particular, the point being made here is that it is just the - // taxon given by taxonId which will be involved, not the selected_set - // or any other nodes. - // - // Let us have some examples as a sanity check: - // Select taxonId . # cool - // Label taxonId . # no problemo - // * * # OK, OK looks straight forward - if (hasVerbs) { - cmd = this.new_GraphCommand({ - verbs: this.engaged_verbs, - classes: [taxonId], - every_class, - skip_history}); - this.huviz.run_command(cmd); - return; - } - // If there is no verb engaged then this click should either engage or - // disengage the taxon identified by id as dictated by new_state. - // - // The following implements the tristate behaviour: - // Mixed —> On - // On —> Off - // Off —> On - if (taxon != null) { - old_state = taxon.get_state(); - } else { - throw `Uhh, there should be a root Taxon 'Thing' by this point: ${taxonId}`; - } - if (new_state === 'showing') { - if (['mixed', 'unshowing', 'empty'].includes(old_state)) { - if (!(Array.from(this.engaged_taxons).includes(taxonId))) { - this.engaged_taxons.push(taxonId); - } - // SELECT all members of the currently chosen classes - cmd = this.new_GraphCommand({ - verbs: ['select'], - classes: [taxonId], - every_class, - skip_history}); - //classes: (class_name for class_name in @engaged_taxons) - } else { - console.error(`no action needed because ${taxonId}.${old_state} == ${new_state}`); + EditController.prototype.quads_match = function(a, b) { + return (a.s === b.s) && (a.p === b.p) && (a.o.value === b.o.value); + }; + + EditController.prototype.set_proposed_quad = function(new_q) { + console.log("set_proposed_quad()"); + if (this.proposed_quad) { + this.remove_proposed_quad(); } - } else if (new_state === 'unshowing') { - this.unselect_node_class(taxonId); - cmd = this.new_GraphCommand({ - verbs: ['unselect'], - classes: [taxonId], - every_class, - skip_history}); - } else if (old_state === "hidden") { - console.error(`${taxonId}.old_state should NOT equal 'hidden' here`); - } - this.taxon_picker.style_with_kid_color_summary_if_needed(taxonId); - if (cmd != null) { - this.huviz.run_command(cmd, this.make_run_transient_and_cleanup_callback(because)); - var because = {}; // clear the because - } - this.update_command(); - } - unselect_node_class(node_class) { - // removes node_class from @engaged_taxons - return this.engaged_taxons = this.engaged_taxons.filter(eye_dee => eye_dee !== node_class); - } - // # Elements may be in one of these states: - // mixed - some instances of the node class are selected, but not all - // unshowing - a light color indicating nothing of that type is selected - // showing - a medium color indicating all things of that type are selected - // abstract - the element represents an abstract superclass, - // presumably containing concrete node classes - // - // hidden - TBD: not sure when hidden is appropriate - // emphasized - TBD: mark the class of the focused_node - make_verb_sets() { - this.verb_sets = [{ // mutually exclusive within each set - choose: this.huviz.human_term.choose, - unchoose: this.huviz.human_term.unchoose, - wander: this.huviz.human_term.wander, - walk: this.huviz.human_term.walk - } - , { - select: this.huviz.human_term.select, - unselect: this.huviz.human_term.unselect - } - , { - label: this.huviz.human_term.label, - unlabel: this.huviz.human_term.unlabel - } - , { - shelve: this.huviz.human_term.shelve, - hide: this.huviz.human_term.hide - } - , { - discard: this.huviz.human_term.discard, - undiscard: this.huviz.human_term.undiscard - } - , { - pin: this.huviz.human_term.pin, - unpin: this.huviz.human_term.unpin + this.add_proposed_quad(new_q); + this.huviz.tick(); + return console.log("Tick in editui.coffee set_proposed_quad"); + }; + + EditController.prototype.add_proposed_quad = function(q) { + var edge; + console.log("add_proposed_quad() " + q.s + " " + q.p + " " + q.o.value); + edge = this.huviz.add_quad(q); + if (!edge) { + console.log("error"); } - ]; - if (this.huviz.show_hunt_verb) { - return this.verb_sets.push({hunt: this.huviz.human_term.hunt}); - } - } - should_be_immediate_mode() { - return !this.is_verb_phrase_empty() && - this.is_command_object_empty() && - !this.liking_all_mode; - } - is_command_object_empty() { - return (this.huviz.selected_set.length === 0) && (this.chosen_set == null); - } - is_verb_phrase_empty() { - return this.engaged_verbs.length === 0; - } - auto_change_verb_if_warranted(node) { - if (this.huviz.edit_mode) { - return; - } - if (this.immediate_execution_mode) { - // If there is only one verb, then do auto_change - if (this.engaged_verbs.length === 1) { - const verb = this.engaged_verbs[0]; - const test = this.auto_change_verb_tests[verb]; - if (test) { - const next_verb = test(node, this.engaged_verbs[0]); - if (next_verb) { - this.engage_verb(next_verb, verb === this.transient_verb_engaged); - } - } + this.huviz.set_proposed_edge(edge); + this.huviz.show_link(edge); + return this.proposed_quad = q; + }; + + EditController.prototype.remove_proposed_quad = function() { + var edge_id, old_edge; + old_edge = this.huviz.proposed_edge; + if (old_edge) { + edge_id = old_edge.id; + this.huviz.set_proposed_edge(null); + this.huviz.delete_edge(old_edge); } - return this.huviz.set_cursor_for_verbs(this.engaged_verbs); - } else { // no verbs are engaged - return this.huviz.set_cursor_for_verbs([]); - } - } - build_form() { - this.build_verb_form(); - this.build_depth(); - this.build_like(); - this.nextcommand = this.nextcommandbox.append('div'). - attr('class','nextcommand command'); - - // Where the full command string to appear as plain text, eg: - // "____ every Thing." - // "shelve every Person." - this.nextcommandstr = this.nextcommand.append('code'); - $(this.nextcommandstr[0][0]).addClass('nextcommand_str'); - - if (this.nextcommand_prompts_visible && this.nextcommand_str_visible) { - this.nextcommand.append('hr'); - } + return this.proposed_quad = null; + }; - // Where the broken out versions of the command string, with prompts, goes. - this.nextcommand_prompts = this.nextcommand.append('code'); - this.nextcommand_prompts.attr('class', 'nextcommand_prompt'); - this.nextcommand_verb_phrase = this.nextcommand_prompts.append('span'); - this.nextcommand_verb_phrase.attr('class','verb_phrase'); - this.nextcommand_noun_phrase = this.nextcommand_prompts.append('span'); - this.nextcommand_noun_phrase.attr('class','noun_phrase'); - this.nextcommand_suffix_phrase = this.nextcommand_prompts.append('span'); - this.nextcommand_suffix_phrase.attr('class','suffix_phrase'); - - if (this.nextcommand_prompts_visible) { - $(this.nextcommand_prompts[0][0]).show(); - } else { - $(this.nextcommand_prompts[0][0]).hide(); - } + (typeof exports !== "undefined" && exports !== null ? exports : EditController).EditController = EditController; - if (this.nextcommand_str_visible) { - $(this.nextcommandstr[0][0]).show(); - } else { - $(this.nextcommandstr[0][0]).hide(); - } + return EditController; - this.nextcommand_working = this.nextcommand.append('div').attr('class','cmd-spinner'); - this.nextcommand_working.style('float:right; color:red; display:none;'); - return this.build_submit(); // msec - } - start_working() { - log_click(); - if (this.already_working) { - clearTimeout(this.already_working); - //console.log "already working", @already_working - } else { - //console.log "start_working()" - this.show_working_on(); - } - return this.already_working = setTimeout(this.stop_working, this.working_timeout); - } - stop_working() { - this.show_working_off(); - return this.already_working = undefined; - } - show_working_on(cmd){ - //console.log "show_working_on()" - if ((cmd != null) && !cmd.skip_history) { - this.push_command_onto_history(cmd); - } - this.nextcommand_working.attr('class','fa fa-spinner fa-spin'); // PREFERRED fa-2x - return this.nextcommand.attr('class','nextcommand command cmd-working'); - } - show_working_off() { - //console.log "show_working_off()" - this.nextcommand_working.attr('class',''); - return this.nextcommand.attr('class','nextcommand command'); - } - //@nextcommand.attr('style','background-color:yellow') # PREFERRED - - build_depth() { - this.depthdiv.text('Activate/Wander Depth:').classed("control_label activate_depth", true); - this.depthdiv.style('display','none');//('display','inline-block') - this.depthdiv.style('white-space','nowrap'); - this.depth_input = this.depthdiv.append('input'); - this.depth_input.attr('class', 'depth_input'); - this.depth_input.attr('placeholder','1'); - this.depth_input.attr('type','number'); - this.depth_input.attr('min','1'); - this.depth_input.attr('max','9'); - return this.depth_input.attr('value','1'); - } + })(FiniteStateMachine); - build_like() { - this.likediv.text('matching:').classed("control_label", true); - this.likediv.style('display','inline-block'); - this.likediv.style('white-space','nowrap'); - this.like_input = this.likediv.append('input'); - this.like_input.attr('class', 'like_input'); - this.like_input.attr('placeholder','node Name'); - this.liking_all_mode = false; // rename to @liking_mode - this.like_input.on('input', this.handle_like_input); - this.clear_like_button = this.likediv.append('button').text('⌫'); - this.clear_like_button.attr('type','button').classed('clear_like', true); - this.clear_like_button.attr('disabled','disabled'); - this.clear_like_button.attr('title','clear the "matching" field'); - return this.clear_like_button.on('click', this.handle_clear_like); - } +}).call(this); +}, "fsm": function(exports, require, module) {(function() { + var FiniteStateMachine; - handle_clear_like(evt) { - this.like_input.property('value',''); - return this.handle_like_input(); - } + FiniteStateMachine = (function() { + function FiniteStateMachine() {} - handle_like_input(evt) { - let TODO; - const like_value = this.get_like_string(); - const like_has_a_value = !!like_value; - if (like_has_a_value) { - this.clear_like_button.attr('disabled', null); - if (this.liking_all_mode) { // - TODO = "update the selection based on the like value"; - //@update_command(evt) # update the impact of the value in the like input - } else { - this.liking_all_mode = true; - this.chosen_set_before_liking_all = this.chosen_set_id; - this.set_immediate_execution_mode(this.is_verb_phrase_empty()); - this.huviz.click_set("all"); // ie choose the 'All' set - } - } else { // like does not have a value - this.clear_like_button.attr('disabled','disabled'); - if (this.liking_all_mode) { // but it DID - TODO = "restore the state before liking_all_mode " + - "eg select a different set or disable all set selection"; - //alert(TODO+" was: #{@chosen_set_before_liking_all}") - if (this.chosen_set_before_liking_all) { - this.huviz.click_set(this.chosen_set_before_liking_all); - this.chosen_set_before_liking_all = undefined; // forget all about it - } else { - this.huviz.click_set('all'); // this should toggle OFF the selection of 'All' + FiniteStateMachine.prototype.call_method_by_name = function(meth_name) { + var meth; + if ((meth = this[meth_name])) { + meth.call(this); + if (this.trace) { + this.trace.push(meth_name); } - this.liking_all_mode = false; - this.set_immediate_execution_mode(true); - //@update_command(evt) # does this deal with that moment when it becomes blanked? - } else { // nothing has happened, so - TODO = "do nothing ????"; + return true; } - } - return this.update_command(evt); - } + return false; + }; - build_submit() { - this.doit_butt = this.nextcommand.append('span').append("input"). - attr("style","float:right;"). - attr("type","submit"). - attr('value','GO!'). - attr('class','doit_button'); - this.doit_butt.on('click', () => { - if (this.update_command()) { - return this.huviz.run_command(this.command); - } - }); - //@huviz.update_all_counts() # TODO Try to remove this, should be auto - return this.set_immediate_execution_mode(true); - } - enable_doit_button() { - return this.doit_butt.attr('disabled',null); - } - disable_doit_button() { - return this.doit_butt.attr('disabled','disabled'); - } - hide_doit_button() { - return $(this.doit_butt[0][0]).hide(); - } - show_doit_button() { - return $(this.doit_butt[0][0]).show(); - } - set_immediate_execution_mode(which) { - if (which) { - this.hide_doit_button(); - } else { - this.show_doit_button(); - } - return this.immediate_execution_mode = which; - } - update_immediate_execution_mode_as_warranted() { - return this.set_immediate_execution_mode(this.should_be_immediate_execution_mode()); - } + FiniteStateMachine.prototype.set_state = function(state) { + var called; + called = this.call_method_by_name('enter__' + state); + this.state = state; + return called; + }; - disengage_all_verbs() { - return Array.from(this.engaged_verbs).map((vid) => - this.disengage_verb(vid)); - } - unselect_all_node_classes() { - return (() => { - const result = []; - for (let nid of Array.from(this.engaged_taxons)) { - this.unselect_node_class(nid); - result.push(this.taxon_picker.set_direct_state(nid, 'unshowing')); + FiniteStateMachine.prototype.exit_state = function() { + return this.call_method_by_name('exit__' + this.state); + }; + + FiniteStateMachine.prototype.get_state = function() { + return this.state; + }; + + FiniteStateMachine.prototype.is_state = function(candidate) { + return this.state === candidate; + }; + + FiniteStateMachine.prototype.make_noop_msg = function(trans_id, old_state, new_state) { + return this.constructor.name + " had neither " + ("on__" + trans_id + " exit__" + old_state + " or enter__" + new_state); + }; + + FiniteStateMachine.prototype.throw_log_or_ignore_msg = function(msg) { + var throw_log_or_ignore; + throw_log_or_ignore = this.throw_log_or_ignore || 'ignore'; + if (throw_log_or_ignore === 'throw') { + throw new Error(msg); + } else if (throw_log_or_ignore === 'log') { + console.warn(msg); } - return result; - })(); - } - clear_like() { - return this.huviz.like_string(); - } - get_like_string() { - return this.like_input[0][0].value; - } - push_command(cmd) { - throw new Error('DEPRECATED'); - return this.push_command_onto_history(cmd); - } - push_cmdArgs_onto_future(cmdArgs) { - return this.future_cmdArgs.push(cmdArgs); - } - push_future_onto_history() { - if (this.future_cmdArgs.length) { - this.huviz.goto_tab(3); - for (let cmdArgs of Array.from(this.future_cmdArgs)) { - this.push_command_onto_history(this.new_GraphCommand(cmdArgs)); + }; + + FiniteStateMachine.prototype.transit = function(trans_id) { + var called, initial_state, msg, target_id, transition; + if (this.transitions == null) { + this.transitions = {}; } - this.reset_command_history(); - this.command_idx0 = 0; - return this.update_script_buttons(); - } - } - push_command_onto_history(cmd) { - // Maybe the command_pointer is in the middle of the command_list and here - // we are trying to run a new command -- so we need to dispose of the remaining - // commands in the command_list because the user is choosing to take a new path. - this.clear_unreplayed_commands_if_needed(); - cmd.id = getRandomId('cmd'); - const elem = this.oldcommands.append('div'). - attr('class','played command'). - attr('id',cmd.id); - this.commandhistory_JQElem.scrollTop(this.commandhistory_JQElem.scrollHeight); - const elem_and_cmd = { - elem, - cmd - }; - this.command_list.push(elem_and_cmd); - this.command_idx0 = this.command_list.length; - const idx_of_this_command = this.command_idx0; - // we are appending to the end of the script, playing is no longer valid, so... - this.disable_play_buttons(); - elem.text(cmd.str+"\n"); // add CR for downloaded scripts - const delete_button = elem.append('a'); - delete_button.attr('class','delete-command'); - delete_button.on('click',() => this.delete_script_command_by_id(cmd.id)); - return this.update_script_buttons(); - } - clear_unreplayed_commands_if_needed() { - while (this.command_idx0 < this.command_list.length) { - this.delete_script_command_by_idx(this.command_list.length - 1); - } - } - delete_script_command_by_id(cmd_id) { - for (let idx = 0; idx < this.command_list.length; idx++) { - const elem_and_cmd = this.command_list[idx]; - if (elem_and_cmd.cmd.id === cmd_id) { - this.delete_script_command_by_idx(idx); - break; - } - } - } - delete_script_command_by_idx(idx) { - const elem_and_cmd = this.command_list.splice(idx, 1)[0]; - //alert("about to delete: " + elem_and_cmd.cmd.str) - const elem = elem_and_cmd.elem[0]; - if (!elem || !elem[0]) { - return; - } - const orphan = elem[0]; - const pops = orphan.parentNode; - pops.removeChild(orphan); - if (idx < this.command_idx0) { - this.command_idx0--; - } - if (this.command_idx0 < 0) { - this.command_idx0 = 0; - } - return this.update_script_buttons(); - } - update_script_buttons() { - if (this.command_list.length > 1) { - this.enable_save_buttons(); - } else { - this.disable_save_buttons(); - } - if (this.command_idx0 >= this.command_list.length) { - this.disable_play_buttons(); - } else { - this.enable_play_buttons(); - } - if (this.command_idx0 > 0) { - this.enable_back_buttons(); - } - if (this.command_idx0 <= 0) { - return this.disable_back_buttons(); - } - } - disable_play_buttons() { - this.scriptPlayButton.attr('disabled', 'disabled'); - return this.scriptForwardButton.attr('disabled', 'disabled'); - } - enable_play_buttons() { - this.scriptForwardButton.attr('disabled', null); - return this.scriptPlayButton.attr('disabled', null); - } - disable_back_buttons() { - this.scriptBackButton.attr('disabled', 'disabled'); - return this.scriptRewindButton.attr('disabled', 'disabled'); - } - enable_back_buttons() { - this.scriptBackButton.attr('disabled', null); - return this.scriptRewindButton.attr('disabled', null); - } - disable_save_buttons() { - this.scriptDownloadButton.attr('disabled', 'disabled'); - return this.scriptStashButton.attr('disabled', 'disabled'); - } - enable_save_buttons() { - this.scriptDownloadButton.attr('disabled', null); - return this.scriptStashButton.attr('disabled', null); - } - build_command() { - const args = - {verbs: []}; - args.object_phrase = this.object_phrase; - if (this.engaged_verbs.length > 0) { - for (let v of Array.from(this.engaged_verbs)) { - if (v !== this.transient_verb_engaged) { - args.verbs.push(v); - } - } - } - if ((this.regarding != null) && this.regarding.length) { - args.regarding = this.regarding.slice(); // ie copy - args.regarding_every = this.regarding_every; - } - if (this.proposed_verb) { - args.verbs.push(this.proposed_verb); - } - if (this.chosen_set_id) { - args.sets = [this.chosen_set]; - } else if (this.proposed_set) { - args.sets = [this.proposed_set]; - } else { - if (this.proposed_taxon) { - args.every_class = this.proposed_every; - args.classes = [this.proposed_taxon]; - } else { // proposed_taxon dominates engaged_taxons and the selected_set equally - if (this.engaged_taxons.length > 0) { - args.classes = (Array.from(this.engaged_taxons)); + if ((transition = this.transitions[trans_id])) { + initial_state = this.state; + called = this.call_method_by_name('on__' + trans_id); + called = this.exit_state() || called; + if ((target_id = transition.target)) { + called = this.set_state(target_id) || called; } - if (this.huviz.selected_set.length > 0) { - args.sets = ['selected']; + if (!called) { + msg = this.make_noop_msg(trans_id, initial_state, target_id); + this.throw_log_or_ignore_msg(msg); } - } - } - const like_str = (this.like_input[0][0].value || "").trim(); - if (like_str) { - args.like = like_str; - } - return this.command = this.new_GraphCommand(args); - } - is_proposed() { - return this.proposed_verb || this.proposed_set || this.proposed_taxon; - } - update_command(because) { - //console.log("update_command()", because) - because = because || {}; - this.huviz.show_state_msg("update_command"); - this.run_any_immediate_command(because); - return this.huviz.hide_state_msg(); - } - run_any_immediate_command(because) { - //console.log("run_any_immediate_command()", because) - const ready = this.prepare_command(this.build_command()); - if (ready && this.huviz.doit_asap && this.immediate_execution_mode && !this.is_proposed()) { - this.perform_current_command(because); - } - } - perform_current_command(because) { - this.show_working_on(this.command); - if (this.huviz.slow_it_down) { - const start = Date.now(); - while (Date.now() < (start + (this.huviz.slow_it_down * 1000))) { - console.log(Math.round((Date.now() - start) / 1000)); - } - } - //alert("About to execute:\n "+@command.str) - this.command.execute(); - this.huviz.update_all_counts(); - this.perform_any_cleanup(because); - return this.show_working_off(); - } - perform_any_cleanup(because) { - //console.log("perform_any_cleanup()",because) - if ((because != null) && because.cleanup) { - because.cleanup(); - this.update_command(); - } - } - prepare_command(cmd) { - this.command = cmd; - if (this.nextcommand_prompts_visible || true) { // NEEDED BY huviz_test.js - this.nextcommand_verb_phrase.text(this.command.verb_phrase); - if (this.command.verb_phrase_ready) { - $(this.nextcommand_verb_phrase[0][0]). - addClass('nextcommand_prompt_ready'). - removeClass('nextcommand_prompt_unready'); - } else { - $(this.nextcommand_verb_phrase[0][0]). - removeClass('nextcommand_prompt_ready'). - addClass('nextcommand_prompt_unready'); - } - this.nextcommand_noun_phrase.text(this.command.noun_phrase); - if (this.command.noun_phrase_ready) { - $(this.nextcommand_noun_phrase[0][0]). - addClass('nextcommand_prompt_ready'). - removeClass('nextcommand_prompt_unready'); } else { - $(this.nextcommand_noun_phrase[0][0]). - removeClass('nextcommand_prompt_ready'). - addClass('nextcommand_prompt_unready'); + this.throw_log_or_ignore_msg("" + this.constructor.name + " has no transition with id " + trans_id); } - this.nextcommand_suffix_phrase.text(this.command.suffix_phrase); - } - if (this.nextcommand_str_visible || true) { // NEEDED BY huviz_test.js - this.nextcommandstr.text(this.command.str); - } - if (this.command.ready) { - this.enable_doit_button(); + }; + + return FiniteStateMachine; + + })(); + + (typeof exports !== "undefined" && exports !== null ? exports : this).FiniteStateMachine = FiniteStateMachine; + +}).call(this); +}, "gclui": function(exports, require, module) { +/* + * verbs: choose,label,discard,shelve,unlabel + * classes: writers,others,people,orgs # places,titles + * like: + * ids: + * + * choose,label/unlabel,discard,shelve,expand + * + */ + +(function() { + var ColoredTreePicker, CommandController, QueryManager, TreePicker, gcl, getRandomId, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, + __indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; }; + + window.toggle_suspend_updates = function(val) { + console.log("toggle_suspend_updates(#val)"); + if ((window.suspend_updates == null) || !window.suspend_updates) { + window.suspend_updates = true; } else { - this.disable_doit_button(); + window.suspend_updates = false; } - return this.command.ready; - } - ready_to_perform() { - const permit_multi_select = true; - return (this.transient_verb_engaged === 'unselect') || - (!this.object_phrase && (this.engaged_verbs.length > 0)) || - (permit_multi_select && - ((this.engaged_verbs.length === 1) && (this.engaged_verbs[0] === 'select'))); - } - build_verb_form() { - this.verb_pretty_name = {}; - return Array.from(this.verb_sets).map((vset) => - this.add_verb_set(vset)); - } - add_verb_set(vset) { - const alternatives = this.verbdiv.append('div').attr('class','alternates'); - for (let id in vset) { - const label = vset[id]; - this.verb_pretty_name[id] = label; - this.build_verb_picker(id,label,alternatives); - } - this.verb_pretty_name['load'] = this.huviz.human_term.load; - this.verb_pretty_name['hunt'] = this.huviz.human_term.hunt; - this.verb_pretty_name['draw'] = this.huviz.human_term.draw; - this.verb_pretty_name['undraw'] = this.huviz.human_term.undraw; - return alternatives; - } - get_verbs_overridden_by(verb_id) { - const override = this.verbs_override[verb_id] || []; - for (let vset of Array.from(this.verb_sets)) { - if (vset[verb_id]) { - for (let vid in vset) { - const label = vset[vid]; - if (!(Array.from(override).includes(vid)) && (verb_id !== vid)) { - override.push(vid); - } - } - } + if (val != null) { + window.suspend_updates = val; } - return override; - } - - /* - The "Do it" button is not needed if the following hold... + return window.suspend_updates; + }; - If there is an object_phrase then the instant a verb is picked the command - should run. + getRandomId = function(prefix) { + var max; + max = 10000000000; + prefix = prefix || 'id'; + return prefix + Math.floor(Math.random() * Math.floor(max)); + }; - If there are verbs picked then the instant there is an object_phrase the - command should run and the object_phrase cleared. (what about selected_set?) + gcl = require('graphcommandlanguage'); - Note that this covers immediate execution of transient verbs select/unselect + ColoredTreePicker = require('coloredtreepicker').ColoredTreePicker; - */ - are_non_transient_verbs() { - // return whether there are any non-transient verbs engaged - const len_transient = ((this.transient_verb_engaged != null) && 1) || 0; - return this.engaged_verbs.length > len_transient; - } + QueryManager = require('querymanager').QueryManager; - engage_transient_verb_if_needed(verb_id) { - if ((this.engaged_verbs.length === 0) && !this.are_non_transient_verbs()) { - return this.engage_verb(verb_id, true); - } - } + TreePicker = require('treepicker').TreePicker; - disengage_transient_verb_if_needed() { - if (this.transient_verb_engaged) { - this.disengage_verb(this.transient_verb_engaged); - this.huviz.set_cursor_for_verbs(this.engaged_verbs); - return this.update_command(); + CommandController = (function() { + function CommandController(huviz, container, hierarchy) { + this.huviz = huviz; + this.container = container; + this.hierarchy = hierarchy; + this.on_set_count_update = __bind(this.on_set_count_update, this); + this.clear_all_sets = __bind(this.clear_all_sets, this); + this.disengage_all_sets = __bind(this.disengage_all_sets, this); + this.handle_on_set_picked = __bind(this.handle_on_set_picked, this); + this.handle_on_verb_clicked = __bind(this.handle_on_verb_clicked, this); + this.perform_current_command = __bind(this.perform_current_command, this); + this.update_command = __bind(this.update_command, this); + this.push_future_onto_history = __bind(this.push_future_onto_history, this); + this.disengage_all_verbs = __bind(this.disengage_all_verbs, this); + this.handle_like_input = __bind(this.handle_like_input, this); + this.handle_clear_like = __bind(this.handle_clear_like, this); + this.stop_working = __bind(this.stop_working, this); + this.on_taxon_clicked = __bind(this.on_taxon_clicked, this); + this.handle_on_taxon_clicked = __bind(this.handle_on_taxon_clicked, this); + this.onChangeEnglish = __bind(this.onChangeEnglish, this); + this.add_taxon = __bind(this.add_taxon, this); + this.recolor_edges = __bind(this.recolor_edges, this); + this.on_predicate_clicked = __bind(this.on_predicate_clicked, this); + this.handle_on_predicate_clicked = __bind(this.handle_on_predicate_clicked, this); + this.add_predicate = __bind(this.add_predicate, this); + this.recolor_edges_and_predicates = __bind(this.recolor_edges_and_predicates, this); + this.handle_newpredicate = __bind(this.handle_newpredicate, this); + this.OLD_select_the_initial_set = __bind(this.OLD_select_the_initial_set, this); + this.NEW_select_the_initial_set = __bind(this.NEW_select_the_initial_set, this); + this.select_the_initial_set = __bind(this.select_the_initial_set, this); + this.on_dataset_loaded = __bind(this.on_dataset_loaded, this); + this.on_fastforward_click = __bind(this.on_fastforward_click, this); + this.on_forward_click = __bind(this.on_forward_click, this); + this.on_backward_click = __bind(this.on_backward_click, this); + this.on_rewind_click = __bind(this.on_rewind_click, this); + this.on_stashscript_clicked = __bind(this.on_stashscript_clicked, this); + this.on_downloadscript_type = __bind(this.on_downloadscript_type, this); + this.on_downloadscript_hybrid_clicked = __bind(this.on_downloadscript_hybrid_clicked, this); + this.on_downloadscript_txt_clicked = __bind(this.on_downloadscript_txt_clicked, this); + this.on_downloadscript_json_clicked = __bind(this.on_downloadscript_json_clicked, this); + if (!this.huviz.all_set.length) { + $(this.container).hide(); + } + d3.select(this.container).html(""); + if (this.huviz.args.display_hints) { + this.hints = d3.select(this.container).append("div").attr("class", "hints"); + $(".hints").append($(".hint_set").contents()); + } + this.style_context_selector = this.huviz.get_picker_style_context_selector(); + this.make_command_history(); + this.prepare_tabs_sparqlQueries(); + this.control_label("Current Command"); + this.nextcommandbox = this.comdiv.append('div'); + this.make_verb_sets(); + this.control_label("Verbs"); + this.verbdiv = this.comdiv.append('div').attr('class', 'verbs'); + this.depthdiv = this.comdiv.append('div'); + this.add_clear_both(this.comdiv); + this.node_pickers = this.comdiv.append('div').attr("id", "node_pickers"); + this.set_picker_box_parent = this.build_set_picker("Sets", this.node_pickers); + this.taxon_picker_box_parent = this.build_taxon_picker("Class Selector", this.node_pickers); + this.add_clear_both(this.comdiv); + this.likediv = this.taxon_picker_box_parent.append('div'); + this.build_predicate_picker("Edges of the Selected Nodes"); + this.init_editor_data(); + this.build_form(); + this.update_command(); + this.install_listeners(); } - } - engage_verb(verb_id, transient) { - if (transient) { - this.transient_verb_engaged = verb_id; - this.verb_control[verb_id].classed('transient', true); - } - const overrides = this.get_verbs_overridden_by(verb_id); - this.verb_control[verb_id].classed('engaged',true); - for (let vid of Array.from(this.engaged_verbs)) { - if (Array.from(overrides).includes(vid)) { - this.disengage_verb(vid); + CommandController.prototype.control_label = function(txt, what, title) { + var label, outer; + what = what || this.comdiv; + outer = what.append('div'); + label = outer.append('div'); + label.classed("control_label", true).text(txt); + if (title) { + label.attr('title', title); } - } - if (!(Array.from(this.engaged_verbs).includes(verb_id))) { - return this.engaged_verbs.push(verb_id); - } - } - disengage_verb(verb_id, transient) { - this.engaged_verbs = this.engaged_verbs.filter(verb => verb !== verb_id); // remove verb_id - this.verb_control[verb_id].classed('engaged',false); - if (verb_id === this.transient_verb_engaged) { - this.transient_verb_engaged = false; - return this.verb_control[verb_id].classed('transient', false); - } - } - build_verb_picker(id,label,alternatives) { - const vbctl = alternatives.append('div').attr("class","verb"); - if (this.verb_descriptions[id]) { - vbctl.attr("title", this.verb_descriptions[id]); - } - vbctl.attr("id", `verb-${id}`); - this.verb_control[id] = vbctl; - vbctl.text(label); - const that = this; - vbctl.on('click', () => { - return this.handle_on_verb_clicked(id, vbctl); - }); - vbctl.on('mouseenter', function() { // tell user what will happen if this verb is clicked - const elem = d3.select(this); - const click_would_engage = !elem.classed('engaged'); - let because = {}; - if (click_would_engage) { - that.proposed_verb = id; // not proposed_verbs because there can be at most one - because = - {proposed_verb: id}; - //cleanup: that.disengage_all_verbs - } else { // clicking would disengage the verb - that.proposed_verb = null; // TODO figure out whether and how to show user - } - // After the click there will be engaged verbs if click_would_engage - // or there are more than one engaged_verbs. - //click_would_leave_a_verb_phrase = click_would_engage or that.engaged_verbs.length > 1 - return that.update_command(because); - }); - return vbctl.on('mouseleave', function() { - const elem = d3.select(this); - const leaving_verb_id = elem.classed('engaged'); - const because = - {verb_leaving: leaving_verb_id}; - that.proposed_verb = null; - return that.update_command(because); - }); - } + return outer; + }; - handle_on_verb_clicked(id, elem) { - this.start_working(); - return setTimeout(() => { // run asynchronously so @start_working() can get a head start - return this.on_verb_clicked(id, elem); - }); - } + CommandController.prototype.new_GraphCommand = function(args) { + return new gcl.GraphCommand(this.huviz, args); + }; - on_verb_clicked(id, elem) { - let because; - const newstate = !elem.classed('engaged'); - elem.classed('engaged',newstate); - if (newstate) { - this.engage_verb(id); - if (id === "walk") { - this.taxon_picker.shield(); - this.set_picker.shield(); - } - this.proposed_verb = null; // there should be no proposed_verb if we are clicking engaging one - because = { - verb_added: id, - cleanup: this.disengage_all_verbs - }; - } else { - if (id === "walk") { - this.taxon_picker.unshield(); - this.set_picker.unshield(); - } - this.disengage_verb(id); - } - if ((this.engaged_verbs == null) || (this.engaged_verbs.length === 0)) { - this.huviz.set_cursor_for_verbs([]); - } - return this.update_command(because); - } + CommandController.prototype.reset_graph = function() { - run_script(script) { - // We recognize a couple of different visible "space-illustrating characters" as spaces. - // https://en.wikipedia.org/wiki/Whitespace_character - // U+237D ⍽ SHOULDERED OPEN BOX - // U+2420 ␠ SYMBOL FOR SPACE - // The purpose of recognizing these as spaces is to make the scripts using them - // more readable in a URL, especially in a FormURLa. - script = script.replace(/[\u237D\u2420]/g," "); - this.huviz.gclc.run(script); - return this.huviz.update_all_counts(); - } - build_set_picker(label, where) { - // FIXME populate @the_sets from @huviz.selectable_sets - where = ((label != null) && this.control_label(label, where)) || this.comdiv; - this.the_sets = { // TODO build this automatically from huviz.selectable_sets - 'all_set': [this.huviz.all_set.label, { - selected_set: [this.huviz.selected_set.label], - chosen_set: [this.huviz.chosen_set.label], - graphed_set: [this.huviz.graphed_set.label], - shelved_set: [this.huviz.shelved_set.label], - hidden_set: [this.huviz.hidden_set.label], - discarded_set: [this.huviz.discarded_set.label], - labelled_set: [this.huviz.labelled_set.label], - pinned_set: [this.huviz.pinned_set.label], - nameless_set: [this.huviz.nameless_set.label], - walked_set: [this.huviz.walked_set.label], - suppressed_set: [this.huviz.suppressed_set.label] - } - ] - }; - this.set_picker_box = where.append('div') - .classed('container',true) - .attr('id', 'sets'); - this.set_picker = new TreePicker(this.set_picker_box, 'all', ['treepicker-vertical']); - this.set_picker.click_listener = this.handle_on_set_picked; - this.set_picker.show_tree(this.the_sets, this.set_picker_box); - this.populate_all_set_docs(); - this.make_sets_proposable(); - where.classed("set_picker_box_parent",true); - return where; - } - populate_all_set_docs() { - return (() => { - const result = []; - for (let id in this.huviz.selectable_sets) { - const a_set = this.huviz.selectable_sets[id]; - if (a_set.docs != null) { - result.push(this.set_picker.set_title(id, a_set.docs)); - } else { - result.push(undefined); - } - } - return result; - })(); - } - make_sets_proposable() { - const make_listeners = (id, a_set) => { // fat arrow carries this to @ - const set_ctl = this.set_picker.id_to_elem[id]; - set_ctl.on('mouseenter', () => { - this.proposed_set = a_set; - return this.update_command(); - }); - return set_ctl.on('mouseleave', () => { - this.proposed_set = null; - return this.update_command(); - }); + /* + * unhide all + * retrieve all + * shelve all + * sanity check set counts + */ + this.huviz.walkBackAll(); + this.huviz.walk_path_set = []; + this.huviz.run_command(this.new_GraphCommand({ + verbs: ['undiscard', 'unchoose', 'unselect', 'unpin', 'shelve', 'unlabel'], + sets: [this.huviz.all_set.id], + skip_history: true + })); + this.disengage_all_verbs(); + this.reset_command_history(); + return this.engaged_taxons = []; }; - return (() => { - const result = []; - for (let id in this.huviz.selectable_sets) { - const a_set = this.huviz.selectable_sets[id]; - result.push(make_listeners(id, a_set)); - } - return result; - })(); - } - handle_on_set_picked(set_id, new_state) { - this.start_working(); - return setTimeout(() => { // run asynchronously so @start_working() can get a head start - return this.on_set_picked(set_id, new_state); - }); - } - on_set_picked(set_id, new_state) { - let cmd; - this.clear_set_picker(); // TODO consider in relation to liking_all_mode - this.set_picker.set_direct_state(set_id, new_state); - let because = {}; - const hasVerbs = !!this.engaged_verbs.length; - if (new_state === 'showing') { - this.taxon_picker.shield(); - this.chosen_set = this.huviz[set_id]; - this.chosen_set_id = set_id; - because = { - set_added: set_id, - cleanup: this.disengage_all_sets // the method to call to clear - }; - if (hasVerbs) { - cmd = new gcl.GraphCommand(this.huviz, { - verbs: this.engaged_verbs, // ['select'] - sets: [this.chosen_set.id] - }); - } - } else if (new_state === 'unshowing') { - this.taxon_picker.unshield(); - const XXXcmd = new gcl.GraphCommand(this.huviz, { - verbs: ['unselect'], - sets: [this.chosen_set.id] - }); - this.disengage_all_sets(); - } - if (cmd != null) { - this.huviz.run_command(cmd, this.make_run_transient_and_cleanup_callback(because)); - because = {}; - } - return this.update_command(); - } - disengage_all_sets() { - // TODO harmonize disengage_all_sets() and clear_all_sets() or document difference - if (this.chosen_set_id) { - this.on_set_picked(this.chosen_set_id, "unshowing"); - delete this.chosen_set_id; - return delete this.chosen_set; - } - } - clear_all_sets() { - const skip_sets = ['shelved_set']; - for (let set_key in this.the_sets.all_set[1]) { - const set_label = this.the_sets.all_set[1][set_key]; - if (Array.from(skip_sets).includes(set_key)) { - continue; - } - const the_set = this.huviz[set_key]; - const { cleanup_verb } = the_set; - const cmd = new gcl.GraphCommand(this.huviz, { - verbs: [cleanup_verb], - sets: [the_set.id] + CommandController.prototype.prepare_tabs_sparqlQueries = function() {}; + + CommandController.prototype.push_sparqlQuery_onto_log = function(qry, meta) { + var id, preElem, preJQElem, qryJQElem, queriesJQElem, queryManager; + if (meta == null) { + meta = {}; + } + if (meta.timestamp == null) { + meta.timestamp = Date.now(); + } + id = meta.id || this.huviz.hash(qry + meta.timestamp); + queriesJQElem = this.huviz.tabs_sparqlQueries_JQElem; + qryJQElem = $('
'); + qryJQElem.attr('id', id); + queriesJQElem.append(qryJQElem); + preJQElem = qryJQElem.find('pre'); + preElem = preJQElem[0]; + preJQElem.text(qry); + queriesJQElem.scrollTop(10000); + queryManager = new QueryManager(qry); + return Object.assign(queryManager, { + qryJQElem: qryJQElem, + preJQElem: preJQElem, + preElem: preElem }); - this.huviz.run_command(cmd); - } - } - on_set_count_update(set_id, count) { - return this.set_picker.set_payload(set_id, count); - } - on_taxon_count_update(taxon_id, count) { - return this.taxon_picker.set_payload(taxon_id, count); - } - on_predicate_count_update(pred_lid, count) { - return this.predicate_picker.set_payload(pred_lid, count); - } - clear_set_picker() { - if (this.chosen_set_id != null) { - this.set_picker.set_direct_state(this.chosen_set_id, 'unshowing'); - return delete this.chosen_set_id; - } - } -} -CommandController.initClass(); - -(typeof exports !== 'undefined' && exports !== null ? exports : this).CommandController = CommandController; -}, "graphcommandlanguage": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS101: Remove unnecessary use of Array.from - * DS102: Remove unnecessary code created because of implicit returns - * DS205: Consider reworking code to avoid use of IIFEs - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -const { angliciser } = require('angliciser'); -//gvcl = require('gvcl') #.GVCL -class GCLTest { - constructor(runner, spec) { - this.runner = runner; - this.spec = spec; - console.log("GCLTest",this); - } + }; - perform() { - if (this.spec.script) { - //console.log "==================",@spec.script - this.runner.gclc.run(this.spec.script); - } - // should the expections be checked in a callback? - for (let exp of Array.from((this.spec.expectations != null ? this.spec.expectations : [] ))) { - var got; - console.log("exp",exp); - try { - got = eval(exp[0]); - } catch (e) { - throw new Error(`while eval('${exp[0]}') caught: ${e}`); - } - const expected = exp[1]; - if (this.runner.verbose) { - console.log(`got=${got} expected:${expected}`); - } - if (got !== expected) { - var msg = msg != null ? msg : `'${this.spec.desc}' ${exp[0]} = ${got} not ${expected}`; - return msg; - } - } - } -} + CommandController.prototype.make_command_history = function() { + var history; + this.comdiv = d3.select(this.container).append("div"); + history = d3.select(this.huviz.oldToUniqueTabSel['tabs-history']); + this.cmdtitle = history.append('div').attr('class', 'control_label').html('Command History').attr('style', 'display:inline'); + this.scriptPlayerControls = history.append('div').attr('class', 'scriptPlayerControls'); + this.scriptRewindButton = this.scriptPlayerControls.append('button').attr('title', 'rewind to start').attr('disabled', 'disabled').on('click', this.on_rewind_click); + this.scriptRewindButton.append('i').attr("class", "fa fa-fast-backward"); + this.scriptBackButton = this.scriptPlayerControls.append('button').attr('title', 'go back one step').attr('disabled', 'disabled').on('click', this.on_backward_click); + this.scriptBackButton.append('i').attr("class", "fa fa-play fa-flip-horizontal"); + this.scriptPlayButton = this.scriptPlayerControls.append('button').attr('title', 'play script step by step').attr('disabled', 'disabled').on('click', this.on_forward_click); + this.scriptPlayButton.append('i').attr("class", "fa fa-play"); + this.scriptForwardButton = this.scriptPlayerControls.append('button').attr('title', 'play script continuously').attr('disabled', 'disabled').on('click', this.on_fastforward_click); + this.scriptForwardButton.append('i').attr("class", "fa fa-fast-forward"); + this.scriptDownloadButton = this.scriptPlayerControls.append('button').attr('title', 'save script to file').attr('style', 'margin-left:1em').attr('disabled', 'disabled').on('click', this.on_downloadscript_hybrid_clicked); + this.scriptDownloadButton.append('i').attr("class", "fa fa-download"); + this.scriptDownloadJsonButton = this.scriptPlayerControls.append('button').attr('title', 'save script as .json').attr('style', 'display:none').on('click', this.on_downloadscript_json_clicked); + this.scriptDownloadJsonButton.append('i').attr("class", "fa fa-download").append('span').text('.json'); + this.scriptStashButton = this.scriptPlayerControls.append('button').attr('title', 'save script to menu').attr('disabled', 'disabled').attr('style', 'margin-left:.1em').on('click', this.on_stashscript_clicked); + this.scriptStashButton.append('i').attr("class", "fa fa-bars"); + this.cmdlist = history.append('div').attr('class', 'commandlist'); + this.oldcommands = this.cmdlist.append('div').attr('class', 'commandhistory').style('max-height', "" + (this.huviz.height - 80) + "px"); + this.commandhistoryElem = this.huviz.topElem.querySelector('.commandhistory'); + this.commandhistory_JQElem = $(this.commandhistoryElem); + this.future_cmdArgs = []; + this.command_list = []; + return this.command_idx0 = 0; + }; -class GCLTestSuite { - /* - * callback = function(){ - * this.expect(this.graph_ctrl.nodes.length,7); - * this.expect(this.graph_ctrl.shelved_set.length,0); - * } - * ts = new GCLTestSuite(gclc, [ - * {script:"choose 'abdyma'", - * expectations: [ - * ["this.graph_ctrl.nodes.length",7], - * ["this.graph_ctrl.shelved_set.length",0], - * ] - * } - * ]) - */ - constructor(huviz, suite) { - this.huviz = huviz; - this.suite = suite; - console.log("GCLTestSuite() arguments",arguments); - this.break_quickly = true; - } - emit(txt,id) { - return $("#testsuite-results").append("div").attr("id",id).text(txt); - } - run() { - let pass_count = 0; - const errors = []; - const fails = []; - let num = 0; - this.emit("RUNNING","running"); - for (let spec of Array.from(this.suite)) { - num++; - let passed = false; - console.log("spec:",spec); - const test = new GCLTest(this,spec); - try { - const retval = test.perform(); - if (this.verbose) { - console.log(retval); - } - if (retval != null) { - fails.push([num,retval]); - } else { - passed = true; - pass_count++; - } - } catch (e) { - errors.push([num,e]); - } - //throw e - if (!passed && this.break_quickly) { - break; + CommandController.prototype.reset_command_history = function() { + var record, _i, _len, _ref, _results; + _ref = this.command_list; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + record = _ref[_i]; + _results.push(record.elem.attr('class', 'command')); } - } - console.log(`passed:${pass_count}`+ - " failed:"+fails.length, - ` errors:${errors.length}`); - for (let fail of Array.from(fails)) { - console.log(`test#${fail[0]}`,fail[1]); - } - return Array.from(errors).map((err) => - console.log(`err#${err[0]}`,err[1])); - } -} + return _results; + }; -class GraphCommand { - static initClass() { - this.prototype.missing = '____'; - } - // "choose,label 'abdyma'" - // "label Thing" - // "choose matching 'Maria'" - // "choose organizations matching 'church'" - // "choose Thing matching 'mary'" - // "discard organizations matching 'mary'" - // "choose writers matching 'Margaret' regarding family" - // /(\w+)(,\s*\w+) '(\w+)'/ - - // Expect args: verbs, subjects, classes, constraints, regarding - // verbs: a list of verb names eg: ['choose','label'] REQUIRED - // subjects: a list of subj_ids eg: ['_:AE','http://a.com/abdyma'] - // classes: a list of classes: ['writers','orgs'] - // sets: a list of the huviz sets to act on eg: [@huviz.graphed_set] - // constraints: matching TODO(smurp) document GraphCommand constraints - // regarding: a list of pred_ids eg: ['orl:child','orl:denom'] - // really [ orl:connectionToOrganization, - // http://vocab.sindice.com/xfn#child ] - // Every command must have at least one verb and any kind of subject, so - // at least one of: subjects, classes or sets - // Optional parameters are: - // constraints and regarding - constructor(huviz, args_or_str) { - let args; - this.huviz = huviz; - if (args_or_str instanceof GraphCommand) { - throw new Error("nested GraphCommand no longer permitted"); - } - this.prefixes = {}; - this.args_or_str = args_or_str; - if (typeof args_or_str === 'string') { - args = this.parse(args_or_str); - } else { - args = args_or_str; - } - if (args.skip_history == null) { args.skip_history = false; } - if (args.every_class == null) { args.every_class = false; } - for (let argn in args) { - const argv = args[argn]; - this[argn] = argv; - } - if ((this.str == null)) { - this.update_str(); - } - } - get_node(node_spec) { - // REVIEW this method needs attention - let abbr, id, node, prefix, term; - if (node_spec.id) { - node = this.huviz.nodes.get({'id':node_spec.id}); - } - if (node) { - return node; - } + CommandController.prototype.get_downloadscript_name = function(ext) { + return this.lastScriptName || ('HuVizScript.' + ext); + }; - const tried = [node_spec]; - const id_parts = node_spec.split(':'); // REVIEW curie? uri? - if (id_parts.length > 1) { - abbr = id_parts[0]; - id = id_parts[1]; - prefix = this.prefixes[abbr]; - if (prefix) { - term = prefix+id; - node = this.huviz.nodes.get({'id':term}); - tried.push(term); - } - } - if (!node) { - for (abbr in this.prefixes) { - prefix = this.prefixes[abbr]; - if (!node) { - term = prefix+id; - tried.push(term); - node = this.huviz.nodes.get({'id':term}); - } - } - } - if (!node) { - const msg = `node with id = ${term} not found among ${this.huviz.nodes.length} nodes: ${tried}`; - console.warn(msg); - throw new Error(msg); - } - return node; - } - get_nodes() { - let node; - const result_set = SortedSet().sort_on("id"); - let like_regex = null; - if (this.like) { - like_regex = new RegExp(this.like,"ig"); // ignore, greedy - } - if (this.subjects) { - for (let node_spec of Array.from(this.subjects)) { - node = this.get_node(node_spec); - if (node) { - if ((like_regex == null) || node.name.match(like_regex)) { - result_set.add(node); - } - } else { - if ((this.classes == null)) { - this.classes = []; - } - this.classes.push(node_spec.id); // very hacky - } + CommandController.prototype.get_script_prefix = function() { + return ["#!/bin/env huviz", "# This HuVis script file was generated by the page:", "# " + this.huviz.get_reload_uri(), "# Generated at " + (new Date()).toISOString(), "", ""].join("\n"); + }; + + CommandController.prototype.get_script_body = function() { + return this.get_script_prefix() + this.oldcommands.text(); + }; + + CommandController.prototype.get_script_body_as_json = function() { + var cmd, cmdList, elem_and_cmd, replacer, _i, _len, _ref; + cmdList = []; + if (this.huviz.dataset_loader.value) { + cmdList.push({ + verbs: ['load'], + data_uri: this.huviz.dataset_loader.value, + ontologies: [this.huviz.ontology_loader.value], + skip_history: true + }); } - } - //nodes.push(node) - if (this.classes) { - for (let class_name of Array.from(this.classes)) { - const the_set = this.huviz.taxonomy[class_name] != null ? this.huviz.taxonomy[class_name].get_instances() : undefined; - if (the_set != null) { - var n; - if (like_regex) { - for (n of Array.from(the_set)) { - if (n.name.match(like_regex)) { - result_set.add(n); - } + _ref = this.command_list; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + elem_and_cmd = _ref[_i]; + cmd = elem_and_cmd.cmd; + cmdList.push(cmd.args_or_str); + } + replacer = function(key, value) { + var node_or_id, obj, retlist, setId, set_or_id, _j, _k, _len1, _len2; + retlist = []; + if (key === 'subjects') { + for (_j = 0, _len1 = value.length; _j < _len1; _j++) { + node_or_id = value[_j]; + if (!node_or_id.id) { + console.debug("expecting node_or_id to have attribute .id", node_or_id); } - } else { // a redundant loop, kept shallow for speed when no like - for (n of Array.from(the_set)) { - result_set.add(n); + if (node_or_id.id && node_or_id.lid) { + obj = { + id: node_or_id.id, + lid: node_or_id.lid + }; } + retlist.push(obj || node_or_id); } + return retlist; } - } - } - if (this.sets) { - for (let set of Array.from(this.sets)) { // set might be a SortedSet instance or a_set_id string - var a_set; - if (typeof set === 'string') { - const a_set_id = set; - a_set = this.huviz.get_set_by_id(a_set_id); - } else { - a_set = set; - } - for (node of Array.from(a_set)) { - if ((like_regex == null) || node.name.match(like_regex)) { - result_set.add(node); + if (key === 'sets') { + for (_k = 0, _len2 = value.length; _k < _len2; _k++) { + set_or_id = value[_k]; + setId = set_or_id.id || set_or_id; + retlist.push(setId); } + return retlist; } + return value; + }; + return JSON.stringify(cmdList, replacer, 4); + }; + + CommandController.prototype.get_script_body_as_hybrid = function() { + return this.get_script_body() + "\n\n" + this.huviz.json_script_marker + "\n\n" + this.get_script_body_as_json(); + }; + + CommandController.prototype.make_txt_script_href = function() { + var theBod, theHref; + theBod = encodeURIComponent(this.get_script_body()); + theHref = "data:text/plain;charset=utf-8," + theBod; + return theHref; + }; + + CommandController.prototype.make_json_script_href = function() { + var theHref, theJSON; + theJSON = encodeURIComponent(this.get_script_body_as_json()); + theHref = "data:text/json;charset=utf-8," + theJSON; + return theHref; + }; + + CommandController.prototype.make_hybrid_script_href = function() { + var theBod, theHref; + theBod = encodeURIComponent(this.get_script_body_as_hybrid()); + theHref = "data:text/plain;charset=utf-8," + theBod; + return theHref; + }; + + CommandController.prototype.on_downloadscript_json_clicked = function() { + this.on_downloadscript_type('json'); + }; + + CommandController.prototype.on_downloadscript_txt_clicked = function() { + this.on_downloadscript_type('txt'); + }; + + CommandController.prototype.on_downloadscript_hybrid_clicked = function() { + this.on_downloadscript_type('hybrid', 'txt'); + }; + + CommandController.prototype.on_downloadscript_type = function(scriptFileType, ext) { + var node, theHref, thisName, transientLink; + transientLink = this.scriptPlayerControls.append('a'); + transientLink.text('script'); + thisName = prompt("What would you like to call your saved script?", this.get_downloadscript_name(ext || scriptFileType)); + if (!thisName) { + return; } - } - return result_set; - } - get_methods() { - const methods = []; - for (let verb of Array.from(this.verbs)) { - const method = this.huviz[verb]; - if (method) { - method.build_callback = this.huviz[`${verb}__build_callback`]; - method.callback = this.huviz[`${verb}__atLast`]; - method.atFirst = this.huviz[`${verb}__atFirst`]; - methods.push(method); - } else { - const msg = `method '${verb}' not found`; - console.error(msg); + this.lastScriptName = thisName; + transientLink.attr('style', 'display:none'); + transientLink.attr('download', this.lastScriptName); + if (scriptFileType === 'json') { + theHref = this.make_json_script_href(); + } else if (scriptFileType === 'txt') { + theHref = this.make_txt_script_href(); + } else if (scriptFileType === 'hybrid') { + theHref = this.make_hybrid_script_href(); + } + transientLink.attr('href', theHref); + transientLink.node().click(); + node = transientLink.node(); + node.parentNode.removeChild(node); + }; + + CommandController.prototype.on_stashscript_clicked = function() { + var ext, scriptFileType, script_rec, thisName; + scriptFileType = 'hybrid'; + ext = 'txt'; + thisName = prompt("What would you like to call this script in your menu?", this.get_downloadscript_name(ext || scriptFileType)); + if (!thisName) { + return; } - } - return methods; - } - get_predicate_methods() { - const methods = []; - for (let verb of Array.from(this.verbs)) { - const method = this.huviz[verb + "_edge_regarding"]; - if (method) { - methods.push(method); - } else { - const msg = `method '${verb}' not found`; - console.error(msg); - } - } - return methods; - } - regarding_required() { - return (this.regarding != null) && (this.regarding.length > 0); - } - execute() { - let iter, meth; - this.huviz.show_state_msg(this.as_msg()); - this.huviz.force.stop(); - const regarding_required = this.regarding_required(); - const nodes = this.get_nodes(); - console.log(`%c${this.str}`, "color:blue;font-size:1.5em;", `on ${nodes.length} nodes`); - const errorHandler = function(err_arg) { - //alert("WOOT! command has executed") - if (err_arg != null) { - console.error("err =", err_arg); - if ((err_arg == null)) { - throw "err_arg is null"; - } - throw err_arg; - } - }; - //else - // console.log("DONE .execute()") - if (regarding_required) { - for (meth of Array.from(this.get_predicate_methods())) { - iter = node => { - for (let pred of Array.from(this.regarding)) { - const retval = meth.call(this.huviz, node, pred); - } - return this.huviz.tick(); - }; - if (nodes != null) { - async.each(nodes, iter, errorHandler); - } - } - } else if (this.verbs[0] === 'load') { - this.huviz.load_with(this.data_uri, this.with_ontologies); - console.log("load data_uri has returned"); - } else if (this.verbs[0] === 'query') { - this.huviz.query_from_seeking_limit(this.sparqlQuery); - } else { - for (meth of Array.from(this.get_methods())) { // find the methods on huviz which implement each verb - var callback; - if (meth.callback) { - ({ callback } = meth); - } else if (meth.build_callback) { - callback = meth.build_callback(this, nodes); - } else { - callback = errorHandler; - } - const { atFirst } = meth; - if (atFirst != null) { - atFirst(); // is called once before iterating through the nodes - } - iter = node => { - let retval; - return retval = meth.call(this.huviz, node); // call the verb - }; - //@huviz.tick() # TODO(smurp) move this out, or call every Nth node - // REVIEW Must we check for nodes? Perhaps atLast dominates. - if (nodes != null) { - var USE_ASYNC; - if (USE_ASYNC = false) { - async.each(nodes, iter, callback); - } else { - for (let node of Array.from(nodes)) { - iter(node); - } - this.huviz.gclui.set; - callback(); // atLast is called once, after the verb has been called on each node - } - } - } - } - this.huviz.clean_up_all_dirt_once(); - this.huviz.hide_state_msg(); - this.huviz.force.start(); - this.huviz.tick("Tick in graphcommandlanguage"); - } - get_pretty_verbs() { - const l = []; - for (let verb_id of Array.from(this.verbs)) { - l.push(this.huviz.gclui.verb_pretty_name[verb_id]); - } - return l; - } - update_str() { - let regarding_phrase; - let subj; - const { missing } = this; - let cmd_str = ""; - let ready = true; - let regarding_required = false; - this.verb_phrase = ''; - this.noun_phrase = ''; - this.noun_phrase_ready = false; - //@object_phrase = null - if (this.verbs && this.verbs.length) { - cmd_str = angliciser(this.get_pretty_verbs()); - this.verb_phrase_ready = true; - this.verb_phrase = cmd_str; - } else { - ready = false; - cmd_str = missing; - this.verb_phrase_ready = false; - this.verb_phrase = this.huviz.human_term.blank_verb; - } - this.verb_phrase += ' '; - cmd_str += " "; - let obj_phrase = ""; - if (cmd_str === 'load ') { - this.str += this.data_uri + " ."; - return; - } - //debugger if not @object_phrase? - if (this.object_phrase == null) { this.object_phrase = null; } // this gives @object_phrase a value even if it is null - if (this.sets != null) { - const setLabels = []; - for (let set of Array.from(this.sets)) { // either a list of SortedSets or their ids - var aSet; - if (typeof set === 'string') { - aSet = this.huviz.get_set_by_id(set); - } else { - aSet = set; - } - const setLabel = aSet.get_label(); - setLabels.push(setLabel); - } - let more = angliciser(setLabels); - more = `the ${more} set` + (((this.sets.length > 1) && 's') || ''); - this.object_phrase = more; - //if @object_phrase? - this.noun_phrase_ready = true; - obj_phrase = this.object_phrase; - this.noun_phrase = obj_phrase; - } else { - if (this.object_phrase) { - console.log("update_str() object_phrase: ", this.object_phrase); - obj_phrase = this.object_phrase; - } else if (this.classes) { - const maybe_every = (this.every_class && "every ") || ""; - obj_phrase += maybe_every + angliciser(this.classes); - if (this.except_subjects) { - obj_phrase += ' except ' + angliciser(((() => { - const result = []; - for (subj of Array.from(this.subjects)) { result.push(subj.lid); - } - return result; - })())); - } - } else if (this.subjects) { - obj_phrase = angliciser(((() => { - const result1 = []; - for (subj of Array.from(this.subjects)) { result1.push(subj.lid || subj); - } - return result1; - })())); - } - } - //@noun_phrase = obj_phrase - if (obj_phrase === "") { - obj_phrase = missing; - ready = false; - this.noun_phrase_ready = false; - this.noun_phrase = this.huviz.human_term.blank_noun; - } else if (obj_phrase.length > 0) { - this.noun_phrase_ready = true; - this.noun_phrase = obj_phrase; - } - cmd_str += obj_phrase; - const like_str = (this.like || "").trim(); - if (this.verbs) { - for (let verb of Array.from(this.verbs)) { - if (['draw', 'undraw'].indexOf(verb) > -1) { - regarding_required = true; - } - } - } - if (regarding_required) { - regarding_phrase = missing; - if (this.regarding_required()) { //? and @regarding.length > 0 - regarding_phrase = angliciser(this.regarding); - if (this.regarding_every) { - regarding_phrase = `every ${regarding_phrase}`; - } - } else { - ready = false; - } - } - this.suffix_phrase = ''; - if (like_str) { - this.suffix_phrase += ` matching '${like_str}'`; - } - if (regarding_phrase) { - this.suffix_phrase += ` regarding ${regarding_phrase} .`; - } else if (this.polar_coords) { - this.suffix_phrase += ` at ${this.polar_coords.degrees.toFixed(0)} degrees`; - this.suffix_phrase += ` and range ${this.polar_coords.range.toFixed(2)} .`; - } else { - this.suffix_phrase += ' .'; - } - cmd_str += this.suffix_phrase; - //cmd_str += " ." - this.ready = ready; - return this.str = cmd_str; - } - toString() { - return this.str; - } - parse_query_command(parts) { - const keymap = { // from key in command url to key on querySpec passed to HuViz - query: 'serverUrl', - from: 'graphUrl', - limit: 'limit', - seeking: 'subjectUrl' + this.lastScriptName = thisName; + script_rec = { + uri: thisName, + opt_group: 'Your Own', + data: this.get_script_body_as_hybrid() }; - const spec = {}; - while (parts.length) { - // find argName/argVal pairs - const argName = keymap[parts.shift()]; - const argVal = unescape(parts.shift()); - if (argName != null) { - spec[argName] = argVal; - } else { - throw new Error("parse_query_command() failed at",parts.join(' ')); - } - } - return spec; - } - parse(cmd_str) { - const parts = cmd_str.split(" "); - const verb = parts[0]; - const cmd = {}; - cmd.verbs = [verb]; - if (verb === 'load') { - cmd.data_uri = parts[1]; - if (parts.length > 3) { - // "load /data/bob.ttl with onto1.ttl onto2.ttl" - cmd.with_ontologies = parts.slice(3); // cdr - } - } else if (verb === 'query') { - this.sparqlQuery = this.parse_query_command(parts); - } else { - const subj = parts[1].replace(/\'/g,""); - cmd.subjects = [{'id': subj}]; - } - return cmd; - } - toString() { - return this.str; - } - as_msg() { - return this.str; - } -} -GraphCommand.initClass(); + this.huviz.script_loader.add_local_file(script_rec); + }; -class GraphCommandLanguageCtrl { - constructor(huviz) { - this.execute = this.execute.bind(this); - this.huviz = huviz; - this.prefixes = {}; - } - run(script, callback) { - this.huviz.before_running_command(this); - //console.debug("script: ",script) - if ((script == null)) { - console.error("script must be defined"); - return; - } - if (script instanceof GraphCommand) { - this.commands = [script]; - } else if (typeof script === 'string') { - this.commands = script.split(';'); - //@gvcl_script = new GVCL(script) - } else if (script.constructor === [].constructor) { - this.commands = script; - } else { // an object we presume - this.commands = [script]; - } - const retval = this.execute(callback); - //console.log "commands:" - //console.log @commands - this.huviz.after_running_command(this); - return retval; - } - run_one(cmd_spec) { - let cmd; - if (cmd_spec instanceof GraphCommand) { - cmd = cmd_spec; - } else { - cmd = new GraphCommand(this.huviz, cmd_spec); - } - cmd.prefixes = this.prefixes; - return cmd.execute(); - } - execute(callback) { - if ((this.commands.length > 0) && (typeof this.commands[0] === 'string') && this.commands[0].match(/^load /)) { - //console.log("initial execute", @commands) - this.run_one(this.commands.shift()); - //setTimeout @execute, 2000 - var run_once = () => { - document.removeEventListener('dataset-loaded',run_once); - return this.execute(); - }; - document.addEventListener('dataset-loaded',run_once); - return; - } - for (let cmd_spec of Array.from(this.commands)) { - if (cmd_spec) { // ie not blank - this.run_one(cmd_spec); + CommandController.prototype.on_rewind_click = function() { + this.reset_graph(); + this.command_idx0 = 0; + return this.update_script_buttons(); + }; + + CommandController.prototype.on_backward_click = function() { + var forward_to_idx; + forward_to_idx = this.command_idx0 - 1; + this.on_rewind_click(); + return this.on_fastforward_click(forward_to_idx); + }; + + CommandController.prototype.on_forward_click = function() { + this.play_old_command_by_idx(this.command_idx0); + this.command_idx0++; + return this.update_script_buttons(); + }; + + CommandController.prototype.on_fastforward_click = function(forward_to_idx) { + var _results; + if (forward_to_idx == null) { + forward_to_idx = this.command_list.length; } - } - if (callback != null) { - callback(); - } - } -} + _results = []; + while (this.command_idx0 < forward_to_idx) { + _results.push(this.on_forward_click()); + } + return _results; + }; -(typeof exports !== 'undefined' && exports !== null ? exports : this).GraphCommandLanguageCtrl = GraphCommandLanguageCtrl; -(typeof exports !== 'undefined' && exports !== null ? exports : this).GraphCommand = GraphCommand; -(typeof exports !== 'undefined' && exports !== null ? exports : this).GCLTest = GCLTest; -(typeof exports !== 'undefined' && exports !== null ? exports : this).GCLTestSuite = GCLTestSuite; -}, "greenerturtle": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS102: Remove unnecessary code created because of implicit returns - * DS205: Consider reworking code to avoid use of IIFEs - * DS206: Consider reworking classes to avoid initClass - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ -//GreenTurtle = GreenTurtle or require("green_turtle").GreenTurtle -var GreenerTurtle = (function() { - let verbosity = undefined; - let obj_has_type = undefined; - let RDF_object = undefined; - let build_indices = undefined; - let get_incoming_predicates = undefined; - let count_subjects = undefined; - GreenerTurtle = class GreenerTurtle { - static initClass() { - verbosity = false; - obj_has_type = (obj, typ) => obj.type === typ; - - RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; - build_indices = graph => - //console.log("SUBJ",graph.subjects); - (() => { - const result = []; - for (let subj_id in graph.subjects) { - var subj = graph.subjects[subj_id]; - - //console.log(' s =',subj,subj.predicates); - result.push((() => { - const result1 = []; - for (var p in subj.predicates) { - var predicate = subj.predicates[p]; - - //console.log(' p =',predicate.objects.length,p); - var oi = 0; - result1.push((() => { - const result2 = []; - while (oi < predicate.objects.length) { - const obj = predicate.objects[oi]; - - //console.log(obj); - if (obj && obj_has_type(obj, RDF_object)) { - if (typeof graph.oid_2_id_p[obj.value] === "undefined") { graph.oid_2_id_p[obj.value] = []; } - if ((obj.value === "_:E") && verbosity) { console.log(obj.value, "----> [", subj.id, p, "]"); } - graph.oid_2_id_p[obj.value].push([ - subj.id, - p - ]); - } - result2.push(oi++); - } - return result2; - })()); - } - return result1; - })()); - } - return result; - })() - ; - - get_incoming_predicates = function(subj) { - const resp = this.oid_2_id_p[subj.id] || []; - - //console.log("get_incoming_predicates(",subj.id,") ===>",resp); - return resp; - }; - - count_subjects = function(graph) { - graph.num_subj = 0; - return (() => { - const result = []; - for (let s in graph.subjects) { - result.push(graph.num_subj++); - } - return result; - })(); - }; - } + CommandController.prototype.play_old_command_by_idx = function(idx) { + var record; + record = this.command_list[idx]; + record.elem.attr('class', 'command played'); + return this.play_old_command(record.cmd); + }; - parse(data, type) { - const G = GreenTurtle.implementation.parse(data, type); - if (!G.oid_2_id_p) { G.oid_2_id_p = {}; } - build_indices(G); - count_subjects(G); - G.get_incoming_predicates = get_incoming_predicates; - return G; - } - }; - GreenerTurtle.initClass(); - return GreenerTurtle; -})(); + CommandController.prototype.play_old_command = function(cmd) { + cmd.skip_history = true; + cmd.skip_history_remove = true; + return this.huviz.run_command(cmd); + }; -exports.GreenerTurtle = GreenerTurtle;}, "huviz": function(exports, require, module) {/* - * decaffeinate suggestions: - * DS001: Remove Babel/TypeScript constructor workaround - * DS101: Remove unnecessary use of Array.from - * DS102: Remove unnecessary code created because of implicit returns - * DS104: Avoid inline assignments - * DS202: Simplify dynamic range loops - * DS205: Consider reworking code to avoid use of IIFEs - * DS206: Consider reworking classes to avoid initClass - * DS207: Consider shorter variations of null checks - * DS208: Avoid top-level this - * Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md - */ + CommandController.prototype.install_listeners = function() { + window.addEventListener('changePredicate', this.predicate_picker.onChangeState); + window.addEventListener('changeTaxon', this.taxon_picker.onChangeState); + return window.addEventListener('changeEnglish', this.onChangeEnglish); + }; -//See for inspiration: -// Collapsible Force Layout -// http://bl.ocks.org/mbostock/1093130 -// Force-based label placement -// http://bl.ocks.org/MoritzStefaner/1377729 -// Graph with labeled edges: -// http://bl.ocks.org/jhb/5955887 -// Multi-Focus Layout: -// http://bl.ocks.org/mbostock/1021953 -// Edge Labels -// http://bl.ocks.org/jhb/5955887 -// -// Shelf -- around the graph, the ring of nodes which serves as reorderable menu -// Discard Bin -- a jail to contain nodes one does not want to be bothered by -// -// Commands on nodes -// choose/shelve -- graph or remove from graph -// choose - add to graph and show all edges -// unchoose - hide all edges except those to 'chosen' nodes -// this will shelve (or hide if previously hidden) -// those nodes which end up no longer being connected -// to anything -// discard/retrieve -- throw away or recover -// label/unlabel -- shows labels or hides them -// substantiate/redact -- shows source text or hides it -// expand/contract -- show all links or collapse them -// -// TODO(smurp) implement emphasize and deemphasize 'verbs' (we need a new word) -// emphasize: (node,predicate,color) => -// deemphasize: (node,predicate,color) => -// pin/unpin -// -// TODO(smurp) break out verbs as instances of class Verb, support loading of verbs -// -// TODO: perhaps there is a distinction to be made between verbs -// and 'actuators' where verbs are the things that people issue -// while actuators (actions?) are the one-or-more things per-verb that -// constitute the implementation of the verb. The motivations are: -// a) that actuators may be shared between verbs -// b) multiple actuators might be needed per verb -// c) there might be applications for actuators other than verbs -// d) there might be update operations against gclui apart from actuators -// -// Immediate Priorities: -// 120) BUG: hidden nodes are hidden but are also detectable via TextCursor -// 118) TASK: add setting for "'chosen' border thickness (px)" -// 116) BUG: stop truncating verbs lists longer than 2 in TextCursor: use grid -// 115) TASK: add ColorTreepicker [+] and [-] boxes for 'show' and 'unshow' -// 114) TASK: make text_cursor show detailed stuff when in Commands and Settings -// 113) TASK: why is CP "Poetry" in abdyma.nq not shelved? -// 107) TASK: minimize hits on TextCursor by only calling it when verbs change -// not whenever @focused_node changes -// 104) TASK: remove no-longer-needed text_cursor calls -// 40) TASK: support search better, show matches continuously -// 79) TASK: support dragging of edges to shelf or discard bin -// 97) TASK: integrate blanket for code coverage http://goo.gl/tH4Ghk -// 93) BUG: toggling a predicate should toggle indirect-mixed on its supers -// 92) BUG: non-empty predicates should not have payload '0/0' after kid click -// 94) TASK: show_msg() during command.run to inform user and prevent clicks -// 95) TASK: get /orlonto.html working smoothly again -// 90) BUG: english is no longer minimal -// 91) BUG: mocha async being misused re done(), so the passes count is wrong -// 86) BUG: try_to_set_node_type: only permit subtypes to override supertypes -// 87) BUG: solve node.type vs node.taxon sync problem (see orlonto) -// 46) TASK: impute node type based on predicates via ontology DONE??? -// 53) PERF: should_show_label should not have search_regex in inner loop -// 65) BUG: hidden nodes are not fully ignored on the shelf so shelved nodes -// are not always the focused node -// 68) TASK: optimize update_english -// 69) TASK: figure out ideal root for predicate hierarchy -- owl:Property? -// 70) TASK: make owl:Thing implicit root class -// ie: have Taxons be subClassOf owl:Thing unless replaced -// 72) TASK: consolidate type and taxon links from node? -// 74) TASK: recover from loading crashes with Cancel button on show_state_msg -// 76) TASK: consider renaming graphed_set to connected_set and verbs -// choose/unchoose to graph/ungraph -// 84) TASK: add an unchosen_set containing the graphed but not chosen nodes -// -// Eventual Tasks: -// 85) TASK: move SVG, Canvas and WebGL renderers to own pluggable Renderer subclasses -// 75) TASK: implement real script parser -// 4) TASK: Suppress all but the 6-letter id of writers in the cmd cli -// 14) TASK: it takes time for clicks on the predicate picker to finish; -// showing a busy cursor or a special state for the selected div -// would help the user have faith. -// (Investigate possible inefficiencies, too.) -// AKA: fix bad-layout-until-drag-and-drop bug -// 18) TASK: drop a node on another node to draw their mutual edges only -// 19) TASK: progressive documentation (context sensitive tips and intros) -// 25) TASK: debug wait cursor when slow operations are happening, maybe -// prevent starting operations when slow stuff is underway -// AKA: show waiting cursor during verb execution -// 30) TASK: Stop passing (node, change, old_node_status, new_node_status) to -// Taxon.update_state() because it never seems to be needed -// 35) TASK: get rid of jquery -// 37) TASK: fix Bronte names, ie unicode -// 41) TASK: link to new backend -// 51) TASK: make predicate picker height adjustable -// 55) TASK: clicking an edge for a snippet already shown should add that -// triple line to the snippet box and bring the box forward -// (ideally using css animation to flash the triple and scroll to it) -// 56) TASK: improve layout of the snippet box so the subj is on the first line -// and subsequent lines show (indented) predicate-object pairs for -// each triple which cites the snippet -// 57) TASK: hover over node on shelf shows edges to graphed and shelved nodes -// 61) TASK: make a settings controller for edge label (em) (or mag?) -// 66) BUG: #load+/data/ballrm.nq fails to populate the predicate picker -// 67) TASK: add verbs pin/unpin (using polar coords to record placement) -// -let default_node_radius_policy, is_one_of, node_radius_policies; -const { - angliciser -} = require('angliciser'); -const { - uniquer -} = require("uniquer"); // FIXME rename to make_dom_safe_id -const gcl = require('graphcommandlanguage'); -//asyncLoop = require('asynchronizer').asyncLoop -const { - CommandController -} = require('gclui'); -const { - EditController -} = require('editui'); -//FiniteStateMachine = require('fsm').FiniteStateMachine -const { - IndexedDBService -} = require('indexeddbservice'); -const { - IndexedDBStorageController -} = require('indexeddbstoragecontroller'); -const { - Edge -} = require('edge'); -const { - GraphCommandLanguageCtrl -} = require('graphcommandlanguage'); -const { - GreenerTurtle -} = require('greenerturtle'); -const { - Node -} = require('node'); -const { - Predicate -} = require('predicate'); -const { - Taxon -} = require('taxon'); -const { - TextCursor -} = require('textcursor'); - -MultiString.set_langpath('en:fr'); // TODO make this a setting - -// It is as if these imports were happening but they are being stitched in instead -// OnceRunner = require('oncerunner').OnceRunner -// TODO document the other examples of requires that are being "stitched in" - -const colorlog = function(msg, color, size) { - if (color == null) { color = "red"; } - if (size == null) { size = "1.2em"; } - return console.log(`%c${msg}`, `color:${color};font-size:${size};`); -}; + CommandController.prototype.on_dataset_loaded = function(evt) { + if (evt.done == null) { + $(this.container).show(); + this.show_succession_of_hints(); + this.huviz.perform_tasks_after_dataset_loaded(); + this.huviz.hide_state_msg(); + return evt.done = true; + } + }; -const unpad_md = function(txt, pad) { - // Purpose: - // Remove padding at the beginings of all lines in txt IFF all lines have padding - // Motivation: - // Markdown is very whitespace sensitive but it makes for ugly code - // to not have left padding in large strings. - pad = " "; - const out_lines = []; - const in_lines = txt.split("\n"); - for (let line of Array.from(in_lines)) { - if (!(line.startsWith(pad) || (line.length === 0))) { - return txt; - } - out_lines.push(line.replace(/^ /,'')); - } - const out = out_lines.join("\n"); - return out; -}; + CommandController.prototype.show_succession_of_hints = function() { + var reminder, _i, _len, _ref; + $(".hints.hint_set").show(); + _ref = $(".hints > .a_hint"); + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + reminder = _ref[_i]; + $(reminder).attr('style', 'position:relative'); + $(reminder).append('').on("click", (function(_this) { + return function(evt, ui) { + $(evt.target).parent().hide(); + if ($(evt.target).parent().next()) { + $(evt.target).parent().next().show(); + } + return false; + }; + })(this)); + } + $(".hints > .a_hint").hide(); + return $(".hints > .a_hint").first().show(); + }; -const strip_surrounding_quotes = s => s.replace(/\"$/,'').replace(/^\"/,''); + CommandController.prototype.select_the_initial_set = function() { + this.OLD_select_the_initial_set(); + }; -const wpad = undefined; -const hpad = 10; -const tau = Math.PI * 2; -const distance = function(p1, p2) { - p2 = p2 || [0,0]; - const x = (p1.x || p1[0]) - (p2.x || p2[0]); - const y = (p1.y || p1[1]) - (p2.y || p2[1]); - return Math.sqrt((x * x) + (y * y)); -}; -const dist_lt = function(mouse, d, thresh) { - const x = mouse[0] - d.x; - const y = mouse[1] - d.y; - return Math.sqrt((x * x) + (y * y)) < thresh; -}; -let hash = function(str) { - // https://github.com/darkskyapp/string-hash/blob/master/index.js - let hsh = 5381; - let i = str.length; - while (i) { - hsh = (hsh * 33) ^ str.charCodeAt(--i); - } - return hsh >>> 0; -}; -const convert = function(src, srctable, desttable) { - // convert.js - // http://rot47.net - // Dr Zhihua Lai - const srclen = srctable.length; - const destlen = desttable.length; - // first convert to base 10 - let val = 0; - const numlen = src.length; - let i = 0; - while (i < numlen) { - val = (val * srclen) + srctable.indexOf(src.charAt(i)); - i++; - } - if (val < 0) { return 0; } - // then covert to any base - let r = val % destlen; - let res = desttable.charAt(r); - let q = Math.floor(val / destlen); - while (q) { - r = q % destlen; - q = Math.floor(q / destlen); - res = desttable.charAt(r) + res; - } - return res; -}; -const BASE57 = "23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"; -const BASE10 = "0123456789"; -const int_to_base = intgr => convert(""+intgr, BASE10, BASE57); -const synthIdFor = str => // return a short random hash suitable for use as DOM/JS id -'h' + int_to_base(hash(str)).substr(0,6); -window.synthIdFor = synthIdFor; -const unescape_unicode = u => // pre-escape any existing quotes so when JSON.parse does not get confused -JSON.parse('"' + u.replace('"', '\\"') + '"'); - -var linearize = function(msgRecipient, streamoid) { - if (streamoid.idx === 0) { - return msgRecipient.postMessage({event: 'finish'}); - } else { - let i = streamoid.idx + 1; - let l = 0; - while (streamoid.data[i](!'\n')) { - l++; - i++; - } - const line = streamoid.data.substr(streamoid.idx, l+1).trim(); - msgRecipient.postMessage({event:'line', line}); - streamoid.idx = i; - const recurse = () => linearize(msgRecipient, streamoid); - return setTimeout(recurse, 0); - } -}; + CommandController.prototype.NEW_select_the_initial_set = function() { + this.huviz.run_command(this.new_GraphCommand({ + verbs: ['select'], + every_class: true, + classes: ['Thing'], + skip_history: true + })); + this.huviz.run_command(this.new_GraphCommand({ + verbs: ['unselect'], + every_class: true, + classes: ['Thing'], + skip_history: true + })); + this.huviz.shelved_set.resort(); + }; -const ident = data => data; + CommandController.prototype.OLD_select_the_initial_set = function() { + var rm_cmd, toggleEveryThing; + rm_cmd = (function(_this) { + return function() { + return _this.delete_script_command_by_idx(0); + }; + })(this); + toggleEveryThing = (function(_this) { + return function() { + _this.huviz.toggle_taxon("Thing", false); + return setTimeout(rm_cmd, 1000); + }; + })(this); + toggleEveryThing.call(); + setTimeout(toggleEveryThing, 1200); + setTimeout(this.push_future_onto_history, 1800); + this.huviz.shelved_set.resort(); + }; -const unique_id = function(prefix) { - if (prefix == null) { prefix = 'uid_'; } - return prefix + Math.random().toString(36).substr(2,10); -}; + CommandController.prototype.check_until_then = function(checkCallback, thenCallback) { + var intervalId, nag; + nag = (function(_this) { + return function() { + if (checkCallback.call()) { + clearInterval(intervalId); + return thenCallback.call(); + } + }; + })(this); + return intervalId = setInterval(nag, 30); + }; -const sel_to_id = selector => // remove the leading hash to make a selector into an id -selector.replace(/^\#/, ''); - -window.log_click = () => console.log("%cCLICK", "color:red;font-size:1.8em"); - -// http://dublincore.org/documents/dcmi-terms/ -const DC_subject = "http://purl.org/dc/terms/subject"; -const DCE_title = "http://purl.org/dc/elements/1.1/title"; -const FOAF_Group = "http://xmlns.com/foaf/0.1/Group"; -const FOAF_Person = "http://xmlns.com/foaf/0.1/Person"; -const FOAF_name = "http://xmlns.com/foaf/0.1/name"; -const OA_ = "http://www.w3.org/ns/oa#"; // the prefix of the Open Annotation Ontology -// OA_terms_regex was built with the help of: -// grep '^oa:' data/oa.ttl | grep " a " | sort | sed 's/\ a\ .*//' | uniq | sed 's/^oa://' | tr '\n' '|' -const OA_terms_regex = /^(Annotation|Choice|CssSelector|CssStyle|DataPositionSelector|Direction|FragmentSelector|HttpRequestState|Motivation|PreferContainedDescriptions|PreferContainedIRIs|RangeSelector|ResourceSelection|Selector|SpecificResource|State|Style|SvgSelector|TextPositionSelector|TextQuoteSelector|TextualBody|TimeState|XPathSelector|annotationService|assessing|bodyValue|bookmarking|cachedSource|canonical|classifying|commenting|describing|editing|end|exact|hasBody|hasEndSelector|hasPurpose|hasScope|hasSelector|hasSource|hasStartSelector|hasState|hasTarget|highlighting|identifying|linking|ltrDirection|moderating|motivatedBy|prefix|processingLanguage|questioning|refinedBy|renderedVia|replying|rtlDirection|sourceDate|sourceDateEnd|sourceDateStart|start|styleClass|styledBy|suffix|tagging|textDirection|via)$/; -const OSMT_name = "https://wiki.openstreetmap.org/wiki/Key:name"; -const OSMT_reg_name = "https://wiki.openstreetmap.org/wiki/Key:reg_name"; -const OWL_Class = "http://www.w3.org/2002/07/owl#Class"; -const OWL_Thing = "http://www.w3.org/2002/07/owl#Thing"; -const OWL_ObjectProperty = "http://www.w3.org/2002/07/owl#ObjectProperty"; -const RDF_literal = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; -const RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; -const RDF_type = "http://www.w3.org/1999/02/22-rdf-syntax-ns#type"; -const RDF_Class = "http://www.w3.org/2000/01/rdf-schema#Class"; // TODO rename RDFS_ -const RDF_subClassOf = "http://www.w3.org/2000/01/rdf-schema#subClassOf"; // TODO rename RDFS_ -const RDF_a = 'a'; -const RDFS_label = "http://www.w3.org/2000/01/rdf-schema#label"; -const SCHEMA_name = "http://schema.org/name"; -const SKOS_prefLabel = "http://www.w3.org/2004/02/skos/core#prefLabel"; -const XL_literalForm = "http://www.w3.org/2008/05/skos-xl#literalForm"; -const TYPE_SYNS = [RDF_type, RDF_a, 'rdfs:type', 'rdf:type']; -const THUMB_PREDS = [ - 'http://dbpedia.org/ontology/thumbnail', - 'http://xmlns.com/foaf/0.1/thumbnail']; -const NAME_SYNS = [ - FOAF_name, RDFS_label, 'rdfs:label', 'name', SKOS_prefLabel, XL_literalForm, - SCHEMA_name, DCE_title, OSMT_reg_name, OSMT_name ]; -const XML_TAG_REGEX = /(<([^>]+)>)/ig; - -const typeSigRE = { - // https://regex101.com/r/lKClAg/1 - 'xsd': new RegExp("^http:\/\/www\.w3\.org\/2001\/XMLSchema\#(.*)$"), - // https://regex101.com/r/ccfdLS/3/ - 'rdf': new RegExp("^http:\/\/www\.w3\.org\/1999\/02\/22-rdf-syntax-ns#(.*)$") -}; -const getPrefixedTypeSignature = function(typeUri) { - for (let prefix in typeSigRE) { - const sig = typeSigRE[prefix]; - const match = typeUri.match(sig); - if (match) { - return `${prefix}__${match[1]}`; - } - } -}; -const getTypeSignature = function(typeUri) { - const typeSig = getPrefixedTypeSignature(typeUri); - return typeSig; -}; - //return (typeSig or '').split('__')[1] -const PRIMORDIAL_ONTOLOGY = { - subClassOf: { - Literal: 'Thing', - // https://www.w3.org/1999/02/22-rdf-syntax-ns - // REVIEW(smurp) ignoring all but the rdfs:Datatype instances - // REVIEW(smurp) should Literal be called Datatype instead? - "rdf__PlainLiteral": 'Literal', - "rdf__HTML": 'Literal', - "rdf__langString": 'Literal', - "rdf__type": 'Literal', - "rdf__XMLLiteral": 'Literal', - // https://www.w3.org/TR/xmlschema11-2/type-hierarchy-201104.png - // https://www.w3.org/2011/rdf-wg/wiki/XSD_Datatypes - // REVIEW(smurp) ideally all the xsd types would fall under anyType > anySimpleType > anyAtomicType - // REVIEW(smurp) what about Built-in list types like: ENTITIES, IDREFS, NMTOKENS ???? - "xsd__anyURI": 'Literal', - "xsd__base64Binary": 'Literal', - "xsd__boolean": 'Literal', - "xsd__date": 'Literal', - "xsd__dateTimeStamp": 'date', - "xsd__decimal": 'Literal', - "xsd__integer": "xsd__decimal", - "xsd__long": "xsd__integer", - "xsd__int": "xsd__long", - "xsd__short": "xsd__int", - "xsd__byte": "xsd__short", - "xsd__nonNegativeInteger": "xsd__integer", - "xsd__positiveInteger": "xsd__nonNegativeInteger", - "xsd__unsignedLong": "xsd__nonNegativeInteger", - "xsd__unsignedInt": "xsd__unsignedLong", - "xsd__unsignedShort": "xsd__unsignedInt", - "xsd__unsignedByte": "xsd__unsignedShort", - "xsd__nonPositiveInteger": "xsd__integer", - "xsd__negativeInteger": "xsd__nonPositiveInteger", - "xsd__double": 'Literal', - "xsd__duration": 'Literal', - "xsd__float": 'Literal', - "xsd__gDay": 'Literal', - "xsd__gMonth": 'Literal', - "xsd__gMonthDay": 'Literal', - "xsd__gYear": 'Literal', - "xsd__gYearMonth": 'Literal', - "xsd__hexBinary": 'Literal', - "xsd__NOTATION": 'Literal', - "xsd__QName": 'Literal', - "xsd__string": 'Literal', - "xsd__normalizedString": "xsd_string", - "xsd__token": "xsd__normalizedString", - "xsd__language": "xsd__token", - "xsd__Name": "xsd__token", - "xsd__NCName": "xsd__Name", - "xsd__time": 'Literal' - }, - subPropertyOf: {}, - domain: {}, - range: {}, - label: {} // MultiStrings as values -}; + CommandController.prototype.init_editor_data = function() { + this.shown_edges_by_predicate = {}; + this.unshown_edges_by_predicate = {}; + return this.engaged_taxons = []; + }; -const MANY_SPACES_REGEX = /\s{2,}/g; -const UNDEFINED = undefined; -const start_with_http = new RegExp("http", "ig"); -const ids_to_show = start_with_http; - -const PEEKING_COLOR = "darkgray"; - -const themeStyles = { - "light": { - "themeName": "theme_white", - "pageBg": "white", - "labelColor": "black", - "shelfColor": "lightgreen", - "discardColor": "salmon", - "nodeHighlightOutline": "black" - }, - "dark": { - "themeName": "theme_black", - "pageBg": "black", - "labelColor": "#ddd", - "shelfColor": "#163e00", - "discardColor": "#4b0000", - "nodeHighlightOutline": "white" - } -}; + CommandController.prototype.reset_editor = function() { + this.clear_like(); + this.disengage_all_verbs(); + this.disengage_all_sets(); + this.clear_all_sets(); + this.init_editor_data(); + return this.update_command(); + }; + CommandController.prototype.disengage_command = function() { + this.clear_like(); + this.disengage_all_verbs(); + this.disengage_all_sets(); + return this.update_command(); + }; -const id_escape = function(an_id) { - let retval = an_id.replace(/\:/g,'_'); - retval = retval.replace(/\//g,'_'); - retval = retval.replace(new RegExp(' ','g'),'_'); - retval = retval.replace(new RegExp('\\?','g'),'_'); - retval = retval.replace(new RegExp('\=','g'),'_'); - retval = retval.replace(new RegExp('\\.','g'),'_'); - retval = retval.replace(new RegExp('\\#','g'),'_'); - return retval; -}; + CommandController.prototype.disengage_all = function() { + this.clear_like(); + this.disengage_all_sets(); + this.disengage_all_verbs(); + return this.update_command(); + }; -if (true) { - node_radius_policies = { - "node radius by links"(d) { - d.radius = Math.max(this.node_radius, Math.log(d.links_shown.length)); - return d.radius; - if (d.showing_links === "none") { - d.radius = this.node_radius; - } else { - if (d.showing_links === "all") { - d.radius = Math.max(this.node_radius, - 2 + Math.log(d.links_shown.length)); + CommandController.prototype.add_clear_both = function(target) { + return target.append('div').attr('style', 'clear:both'); + }; + + CommandController.prototype.ignore_predicate = function(pred_id) { + return this.predicates_ignored.push(pred_id); + }; + + CommandController.prototype.handle_newpredicate = function(e) { + var parent_lid, pred_lid, pred_name, pred_uri; + pred_uri = e.detail.pred_uri; + parent_lid = e.detail.parent_lid; + pred_lid = e.detail.pred_lid; + pred_name = e.detail.pred_name; + if (__indexOf.call(this.predicates_ignored, pred_uri) < 0) { + if (__indexOf.call(this.predicates_ignored, pred_lid) < 0) { + if (pred_name == null) { + pred_name = pred_lid.match(/([\w\d\_\-]+)$/g)[0]; + } + this.add_predicate(pred_lid, parent_lid, pred_name); + return this.recolor_edges_and_predicates_eventually(e); } } - return d.radius; - }, - "equal dots"(d) { - return this.node_radius; - } - }; - default_node_radius_policy = "equal dots"; - default_node_radius_policy = "node radius by links"; + }; + + CommandController.prototype.recolor_edges_and_predicates_eventually = function() { + if (this.recolor_edges_and_predicates_eventually_id != null) { + clearTimeout(this.recolor_edges_and_predicates_eventually_id); + } + return this.recolor_edges_and_predicates_eventually_id = setTimeout(this.recolor_edges_and_predicates, 300); + }; - const has_type = (subject, typ) => has_predicate_value(subject, RDF_type, typ); + CommandController.prototype.recolor_edges_and_predicates = function(evt) { + this.predicate_picker.recolor_now(); + return this.recolor_edges(); + }; - var has_predicate_value = function(subject, predicate, value) { - const pre = subject.predicates[predicate]; - if (pre) { - const objs = pre.objects; - let oi = 0; - while (oi <= objs.length) { - const obj = objs[oi]; - if (obj.value === value) { return true; } - oi++; + CommandController.prototype.resort_pickers = function() { + if (this.taxon_picker != null) { + this.taxon_picker.resort_recursively(); + this.taxon_picker.recolor_now(); + this.huviz.recolor_nodes(); } - } - return false; - }; + if (this.predicate_picker != null) { + console.log("resorting of predicate_picker on hold until it does not delete 'anything'"); + } + }; - const is_a_main_node = d => (BLANK_HACK && (d.s.id[7] !== "/")) || (!BLANK_HACK && (d.s.id[0] !== "_")); + CommandController.prototype.build_predicate_picker = function(label) { + var extra_classes, needs_expander, squash_case, title, use_name_as_label, where; + this.predicates_id = this.huviz.unique_id('predicates_'); + title = "Medium color: all edges shown -- click to show none\n" + "Faint color: no edges are shown -- click to show all\n" + "Stripey color: some edges shown -- click to show all\n" + "Hidden: no edges among the selected nodes"; + where = (label != null) && this.control_label(label, this.comdiv, title) || this.comdiv; + this.predicatebox = where.append('div').classed('container', true).attr('id', this.predicates_id); + this.predicates_ignored = []; + this.predicate_picker = new ColoredTreePicker(this.predicatebox, 'anything', (extra_classes = []), (needs_expander = true), (use_name_as_label = true), (squash_case = true), this.style_context_selector); + this.predicate_hierarchy = { + 'anything': ['anything'] + }; + this.predicate_picker.click_listener = this.handle_on_predicate_clicked; + this.predicate_picker.show_tree(this.predicate_hierarchy, this.predicatebox); + this.predicates_JQElem = $(this.predicates_id); + this.predicates_JQElem.addClass("predicates ui-resizable").append("
"); + return this.predicates_JQElem.resizable({ + handles: 's' + }); + }; - const is_node_to_always_show = is_a_main_node; + CommandController.prototype.add_predicate = function(pred_lid, parent_lid, pred_name) { + this.predicate_picker.add(pred_lid, parent_lid, pred_name, this.handle_on_predicate_clicked); + return this.make_predicate_proposable(pred_lid); + }; - is_one_of = (itm, array) => array.indexOf(itm) > -1; -} + CommandController.prototype.make_predicate_proposable = function(pred_lid) { + var predicate_ctl; + predicate_ctl = this.predicate_picker.id_to_elem[pred_lid]; + predicate_ctl.on('mouseenter', (function(_this) { + return function() { + var every, nextStateArgs, ready; + every = !!_this.predicate_picker.id_is_collapsed[pred_lid]; + nextStateArgs = _this.predicate_picker.get_next_state_args(pred_lid); + if (nextStateArgs.new_state === 'showing') { + _this.proposed_verb = 'draw'; + } else { + _this.proposed_verb = 'undraw'; + } + _this.regarding = [pred_lid]; + _this.regarding_every = !!_this.predicate_picker.id_is_collapsed[pred_lid]; + ready = _this.prepare_command(_this.build_command()); + }; + })(this)); + return predicate_ctl.on('mouseleave', (function(_this) { + return function() { + _this.proposed_verb = null; + _this.regarding = null; + _this.prepare_command(_this.build_command()); + }; + })(this)); + }; -if (!is_one_of(2,[3,2,4])) { - alert("is_one_of() fails"); -} + CommandController.prototype.handle_on_predicate_clicked = function(pred_id, new_state, elem, args) { + this.start_working(); + return setTimeout((function(_this) { + return function() { + return _this.on_predicate_clicked(pred_id, new_state, elem, args); + }; + })(this)); + }; -window.blurt = function(str, type, noButton) { - throw new Error('global blurt() is defunct, use @blurt() on HuViz'); -}; + CommandController.prototype.on_predicate_clicked = function(pred_id, new_state, elem, args) { + var cmd, skip_history, verb; + skip_history = !args || !args.original_click; + if (new_state === 'showing') { + verb = 'draw'; + } else { + verb = 'undraw'; + } + cmd = this.new_GraphCommand({ + verbs: [verb], + regarding: [pred_id], + regarding_every: !!this.predicate_picker.id_is_collapsed[pred_id], + sets: [this.huviz.selected_set.id], + skip_history: skip_history + }); + this.prepare_command(cmd); + return this.huviz.run_command(this.command); + }; -const escapeHtml = unsafe => unsafe - .replace(/&/g, "&") - .replace(//g, ">") - .replace(/"/g, """) - .replace(/'/g, "'"); - -const noop = function() {}; // Yup, does nothing. On purpose! - -class SettingsWidget { - constructor(huviz, inputElem, state) { - this.huviz = huviz; - this.inputElem = inputElem; - this.id = unique_id('widget_'); - this.inputJQElem = $(this.inputElem); - } + CommandController.prototype.recolor_edges = function(evt) { + var count, edge, node, pred_n_js_id, _i, _len, _ref, _results; + count = 0; + _ref = this.huviz.all_set; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node = _ref[_i]; + _results.push((function() { + var _j, _len1, _ref1, _results1; + _ref1 = node.links_from; + _results1 = []; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + edge = _ref1[_j]; + count++; + pred_n_js_id = edge.predicate.id; + _results1.push(edge.color = this.predicate_picker.get_color_forId_byName(pred_n_js_id, 'showing')); + } + return _results1; + }).call(this)); + } + return _results; + }; - wrap(html) { - return $(this.inputElem).wrap(html); - } -} + CommandController.prototype.build_taxon_picker = function(label, where) { + var extra_classes, id, needs_expander, squash_case, title, use_name_as_label; + id = 'classes'; + title = "Medium color: all nodes are selected -- click to select none\n" + "Faint color: no nodes are selected -- click to select all\n" + "Stripey color: some nodes are selected -- click to select all\n"; + where = (label != null) && this.control_label(label, where, title) || this.comdiv; + this.taxon_box = where.append('div').classed('container', true).attr('id', id); + this.taxon_box.attr('style', 'vertical-align:top'); + this.taxon_picker = new ColoredTreePicker(this.taxon_box, 'Thing', (extra_classes = []), (needs_expander = true), (use_name_as_label = true), (squash_case = true), this.style_context_selector); + this.taxon_picker.click_listener = this.handle_on_taxon_clicked; + this.taxon_picker.hover_listener = this.on_taxon_hovered; + this.taxon_picker.show_tree(this.hierarchy, this.taxon_box); + where.classed("taxon_picker_box_parent", true); + return where; + }; -class UsernameWidget extends SettingsWidget { - static initClass() { - // https://fontawesome.com/v4.7.0/examples/#animated explains animations fa-spin (continuous) and fa-pulse (8-step) - this.prototype.state_to_state_icon = { - bad: 'fa-times', // the username has been tried and failed last use - good: 'fa-check', // the username has been tried and succeeded last use - untried: 'fa-question', // a username has been provided but not yet tried - trying: 'fa-spinner fa-pulse', // performing a lookup with a username which might be bad or good - empty: 'fa-ellipsis-h', // no username present - looking: 'fa-map-marker-alt fa-spin' // performing a lookup with a known good username - }; - this.prototype.state_to_color = { - bad: 'red', - good: 'green', - untried: 'orange', - trying: 'orange', - empty: 'grey', - looking: 'green' + CommandController.prototype.add_taxon = function(taxon_id, parent_lid, class_name, taxon) { + this.taxon_picker.add(taxon_id, parent_lid, class_name, this.handle_on_taxon_clicked); + this.make_taxon_proposable(taxon_id); + this.taxon_picker.recolor_now(); + return this.huviz.recolor_nodes(); }; - } - constructor() { - super(...arguments); - this.wrap(`
`); // style="border:2px solid; padding:2px - //@inputElem.setAttribute('style','border:none') - this.widgetJQElem = $('#'+this.id); - this.widgetJQElem.prepend(""); - this.stateIconJQElem = this.widgetJQElem.find('.stateIcon'); - this.userIconJQElem = this.widgetJQElem.find('.userIcon'); - this.set_state('empty'); - } + CommandController.prototype.make_taxon_proposable = function(taxon_id) { + var taxon_ctl; + taxon_ctl = this.taxon_picker.id_to_elem[taxon_id]; + taxon_ctl.on('mouseenter', (function(_this) { + return function(evt) { + var ready; + _this.proposed_taxon = taxon_id; + _this.proposed_every = !!_this.taxon_picker.id_is_collapsed[taxon_id]; + if (!_this.engaged_verbs.length) { + if (_this.engaged_taxons.includes(taxon_id)) { + _this.proposed_verb = 'unselect'; + } else { + _this.proposed_verb = 'select'; + } + } + ready = _this.prepare_command(_this.build_command()); + }; + })(this)); + taxon_ctl.on('mouseleave', (function(_this) { + return function(evt) { + var ready; + _this.proposed_taxon = null; + _this.proposed_verb = null; + ready = _this.prepare_command(_this.build_command()); + }; + })(this)); + }; - set_state(state) { - if (false && this.state && (this.state === state)) { - console.log("not bothering to change the state to",state,"cause it already is"); - return; - } - this.state = state; - console.log(state, this.inputJQElem.val()); - const stateIcon = this.state_to_state_icon[state]; - this.stateIconJQElem.attr('class', "stateIcon fa " + stateIcon); - const color = this.state_to_color[state]; - this.widgetJQElem.css('border-color',color); - this.widgetJQElem.css('color',color); - } -} -UsernameWidget.initClass(); + CommandController.prototype.onChangeEnglish = function(evt) { + this.object_phrase = evt.detail.english; + this.prepare_command(this.build_command()); + return this.update_command(); + }; -class GeoUserNameWidget extends UsernameWidget { - constructor() { - super(...arguments); - this.stateIconJQElem.on('click', this.huviz.show_geonames_instructions); - this.userIconJQElem.on('click', this.huviz.show_geonames_instructions); - } -} + CommandController.prototype.handle_on_taxon_clicked = function(id, new_state, elem, args) { + this.start_working(); + return setTimeout((function(_this) { + return function() { + return _this.on_taxon_clicked(id, new_state, elem, args); + }; + })(this)); + }; -const orlando_human_term = { - all: 'All', - chosen: 'Activated', - unchosen: 'Deactivated', - selected: 'Selected', - shelved: 'Shelved', - discarded: 'Discarded', - hidden: 'Hidden', - graphed: 'Graphed', - fixed: 'Pinned', - labelled: 'Labelled', - choose: 'Activate', - unchoose: 'Deactivate', - wander: 'Wander', - walk: 'Walk', - walked: "Walked", - select: 'Select', - unselect: 'Unselect', - label: 'Label', - unlabel: 'Unlabel', - shelve: 'Shelve', - hide: 'Hide', - discard: 'Discard', - undiscard: 'Retrieve', - pin: 'Pin', - unpin: 'Unpin', - unpinned: 'Unpinned', - nameless: 'Nameless', - blank_verb: 'VERB', - blank_noun: 'SET/SELECTION', - hunt: 'Hunt', - load: 'Load', - draw: 'Draw', - undraw: 'Undraw', - connect: 'Connect', - spawn: 'Spawn', - specialize: 'Specialize', - annotate: 'Annotate', - seeking_object: 'Object node', - suppress: 'Suppress', - suppressed: 'Suppresssed' -}; + CommandController.prototype.set_taxa_click_storm_callback = function(callback) { + if (this.taxa_click_storm_callback != null) { + throw new Error("taxa_click_storm_callback already defined"); + } else { + return this.taxa_click_storm_callback = callback; + } + }; -var Huviz = (function() { - let renderStyles = undefined; - let nodeOrderAngle = undefined; - let node_display_type = undefined; - Huviz = class Huviz { - static initClass() { - this.prototype.hash = hash; - this.prototype.class_list = []; // FIXME remove - this.prototype.HHH = {}; - this.prototype.edges_by_id = {}; - this.prototype.edge_count = 0; - this.prototype.snippet_db = {}; - this.prototype.class_index = {}; - this.prototype.hierarchy = {}; - this.prototype.default_color = "brown"; - this.prototype.DEFAULT_CONTEXT = 'http://universal.org/'; - this.prototype.turtle_parser = 'GreenerTurtle'; - //turtle_parser: 'N3' - - this.prototype.use_canvas = true; - this.prototype.use_svg = false; - this.prototype.use_webgl = false; - //use_webgl: true if location.hash.match(/webgl/) - //use_canvas: false if location.hash.match(/nocanvas/) - - this.prototype.nodes = undefined; - this.prototype.links_set = undefined; - this.prototype.node = undefined; - this.prototype.link = undefined; - - this.prototype.lariat = undefined; - this.prototype.verbose = true; - this.prototype.verbosity = 0; - this.prototype.TEMP = 5; - this.prototype.COARSE = 10; - this.prototype.MODERATE = 20; - this.prototype.DEBUG = 40; - this.prototype.DUMP = false; - this.prototype.node_radius_policy = undefined; - this.prototype.draw_circle_around_focused = true; - this.prototype.draw_lariat_labels_rotated = true; - this.prototype.run_force_after_mouseup_msec = 2000; - this.prototype.nodes_pinnable = true; - - this.prototype.BLANK_HACK = false; - this.prototype.width = undefined; - this.prototype.height = 0; - this.prototype.cx = 0; - this.prototype.cy = 0; - - this.prototype.snippet_body_em = .7; - this.prototype.line_length_min = 4; - - // TODO figure out how to replace with the default_graph_control - this.prototype.link_distance = 29; - this.prototype.fisheye_zoom = 4.0; - this.prototype.peeking_line_thicker = 4; - this.prototype.show_snippets_constantly = false; - this.prototype.charge = -193; - this.prototype.gravity = 0.025; - this.prototype.snippet_count_on_edge_labels = true; - this.prototype.label_show_range = null; // @link_distance * 1.1 - this.prototype.focus_threshold = 100; - this.prototype.discard_radius = 200; - this.prototype.fisheye_radius = 300; //null # label_show_range * 5 - this.prototype.focus_radius = null; // label_show_range - this.prototype.drag_dist_threshold = 5; - this.prototype.snippet_size = 300; - this.prototype.dragging = false; - this.prototype.last_status = undefined; - this.prototype.edge_x_offset = 5; - this.prototype.shadow_offset = 1; - this.prototype.shadow_color = 'DarkGray'; - - this.prototype.my_graph = { - predicates: {}, - subjects: {}, - objects: {} - }; - - // required by green turtle, should be retired - this.prototype.G = {}; - this.prototype.local_file_data = ""; - - this.prototype.search_regex = new RegExp("^$", "ig"); - this.prototype.node_radius = 3.2; - - this.prototype.mousedown_point = false; - this.prototype.discard_center = [0,0]; - this.prototype.lariat_center = [0,0]; - this.prototype.last_mouse_pos = [ 0, 0]; - - renderStyles = themeStyles.light; - this.prototype.display_shelf_clockwise = true; - nodeOrderAngle = 0.5; - node_display_type = ''; - - this.prototype.pfm_data = { - tick: { - total_count: 0, - prev_total_count: 0, - timed_count: [], - label: "Ticks/sec." - }, - add_quad: { - total_count: 0, - prev_total_count: 0, - timed_count: [], - label: "Add Quad/sec" - }, - hatch: { - total_count: 0, - prev_total_count: 0, - timed_count: [], - label: "Hatch/sec" - }, - taxonomy: { - total_count: 0, - label: "Number of Classes:" - }, - sparql: { - total_count: 0, - prev_total_count: 0, - timed_count: [], - label: "Sparql Queries/sec" - } - }; - - this.prototype.p_total_sprql_requests = 0; - - this.prototype.default_dialog_args = { - width:200, - height:200, - left:100, - top:100, - head_bg_color:'#157fcc', - classes: "contextMenu temp", - title: '' - }; - - this.prototype.DEPRECATED_showing_links_to_cursor_map = { - all: 'not-allowed', - some: 'all-scroll', - none: 'pointer' - }; - - this.proposed_edge = null; - - this.prototype.shown_messages = []; - - this.prototype.msg_history = ""; - - this.prototype.my_graph = { - subjects: {}, - predicates: {}, - objects: {} - }; - - // msec betweeen repetition of a msg display - this.prototype.discover_geoname_name_msgs_threshold_ms = 5 * 1000; - - // TODO eliminate all use of this version in favor of the markdown version - this.prototype.discover_geoname_name_instructions = `\ -Be sure to - 1) create a - new account - 2) validate your email - 3) on - manage account - press - click here to enable - 4) re-enter your GeoNames Username in HuViz settings to trigger lookup`; - - this.prototype.discover_geoname_name_instructions_md = `\ -## How to get GeoNames lookup working - -[GeoNames](http://www.geonames.org) is a very popular service experiencing much load. -To protect their servers they require a username to be able to perform lookup. -The hourly limit is 1000 and the daily limit is 30000 per username. - -You may use the \`huviz\` username if you are going to perform just a couple of lookups. -If you are going to do lots of GeoNames lookups you should set up your own account. -Here is how: - -1. create a new account if you don't have one -2. validate your email (if you haven't already) -3. on the manage account page - press Click here to enable - if your account is not already _enabled to use the free web services_ -4. enter your *GeoNames Username* in HuViz \`Settings\` tab then press the TAB or ENTER key to trigger lookup -5. if you need to perform more lookups, just adjust the *GeoNames Limit*, then leave that field with TAB, ENTER or a click - -(Soon, HuViz will let you save your personal *GeoNames Username* and your *GeoNames Limit* to make this more convenient.) - \ -`; - - /* - "fcode" : "RGN", - "adminCodes1" : { - "ISO3166_2" : "ENG" - }, - "adminName1" : "England", - "countryName" : "United Kingdom", - "fcl" : "L", - "countryId" : "2635167", - "adminCode1" : "ENG", - "name" : "Yorkshire", - "lat" : "53.95528", - "population" : 0, - "geonameId" : 8581589, - "fclName" : "parks,area, ...", - "countryCode" : "GB", - "fcodeName" : "region", - "toponymName" : "Yorkshire", - "lng" : "-1.16318" - */ - this.prototype.discover_geoname_key_to_predicate_mapping = { - name: RDFS_label, - //toponymName: RDFS_label - //lat: 'http://dbpedia.org/property/latitude' - //lng: 'http://dbpedia.org/property/longitude' - //fcodeName: RDF_literal - population: 'http://dbpedia.org/property/population' - }; - - // ## Linked Data Fragments (LDF) - // - // Linked Data Fragments is a technique for performing efficient federated searches. - // - // http://linkeddatafragments.org/ - // - // This implementation makes use of - // - // https://github.com/smurp/comunica-ldf-client - // - // which is a fork of: - // https://github.com/comunica/jQuery-Widget.js - // - // with the only real difference being a dist version of ldf-client-worker.min.js - - this.prototype.domain2ldfServer = { - // values feed LDF client context.sources.value # see run_managed_query_ldf - 'dbpedia.org': "http://fragments.dbpedia.org/2016-04/en", - 'viaf.org': "http://data.linkeddatafragments.org/viaf", - 'getty.edu': "http://data.linkeddatafragments.org/lov", - '*': "http://data.linkeddatafragments.org/lov" - }; - //'wikidata.org': - // source: "https://query.wikidata.org/bigdata/ldf" - // TODO handle "wikidata.org" - - this.prototype.default_name_query_args = { - predicates: [RDFS_label, FOAF_name, SCHEMA_name], - limit: 20 - }; - - this.prototype.last_quad = {}; - - // ### `add_quad` is the standard entrypoint for all data sources - // - // It is fires the events: - // newsubject - - this.prototype.object_value_types = {}; - this.prototype.unique_pids = {}; - - this.prototype.scroll_spacer = " "; - - this.prototype.report_every = 100; - - this.prototype.snippet_positions_filled = {}; - - this.prototype.domain2sparqlEndpoint = { - 'cwrc.ca': 'http://sparql.cwrc.ca/sparql', - 'getty.edu': 'http://vocab.getty.edu/sparql.tsv', - 'openstreetmap.org': 'https://sophox.org/sparql' - }; - - // TODO make other than 'anything' optional - this.prototype.predicates_to_ignore = ["anything", "first", "rest", "members"]; - - this.prototype.default_tab_specs = [{ - id: 'commands', - cssClass:'huvis_controls scrolling_tab unselectable', - title: "Power tools for controlling the graph", - text: "Commands" + CommandController.prototype.taxa_being_clicked_increment = function() { + if (this.taxa_being_clicked == null) { + this.taxa_being_clicked = 0; } - , { - id: 'settings', - cssClass: 'settings scrolling_tab', - title: "Fine tune sizes, lengths and thicknesses", - text: "Settings" + this.taxa_being_clicked++; + }; + + CommandController.prototype.taxa_being_clicked_decrement = function() { + if (this.taxa_being_clicked == null) { + throw new Error("taxa_being_clicked_decrement() has apparently been called before taxa_being_clicked_increment()"); } - , { - id: 'history', - cssClass:'tabs-history', - title: "The command history", - text: "History" + this.taxa_being_clicked--; + if (this.taxa_being_clicked === 0) { + if (this.taxa_click_storm_callback != null) { + this.taxa_click_storm_callback.call(document); + return this.taxa_click_storm_callback = null; + } } - , { - id: 'credits', - cssClass: 'tabs-credit scrolling_tab', - title: "Academic, funding and technical credit", - text: "Credit", - bodyUrl: "/huviz/docs/credits.md" + }; + + CommandController.prototype.make_run_transient_and_cleanup_callback = function(because) { + return (function(_this) { + return function(err) { + if (err) { + console.log(err); + throw err; + } + _this.huviz.clean_up_all_dirt(); + _this.run_any_immediate_command({}); + _this.perform_any_cleanup(because); + }; + })(this); + }; + + CommandController.prototype.on_taxon_clicked = function(taxonId, new_state, elem, args) { + var because, cmd, every_class, hasVerbs, old_state, skip_history, taxon; + if (args == null) { + args = {}; } - , { - id: 'tutorial', - cssClass: "tabs-tutor scrolling_tab", - title: "A tutorial", - text: "Tutorial", - bodyUrl: "/huviz/docs/tutorial.md" + taxon = this.huviz.taxonomy[taxonId]; + hasVerbs = !!this.engaged_verbs.length; + skip_history = !args.original_click; + every_class = !!args.collapsed; + if (hasVerbs) { + cmd = this.new_GraphCommand({ + verbs: this.engaged_verbs, + classes: [taxonId], + every_class: every_class, + skip_history: skip_history + }); + this.huviz.run_command(cmd); + return; } - , { - id: 'sparqlQueries', - cssClass: "tabs-sparqlQueries scrolling_tab", - title: "SPARQL Queries", - text: "Q" + if (taxon != null) { + old_state = taxon.get_state(); + } else { + throw "Uhh, there should be a root Taxon 'Thing' by this point: " + taxonId; } - ]; - - // The div on the left should be placed in the div on the right - // The div on the left should appear in needed_divs. - // The div on right should be identified by a tab id like 'huvis_controls' - // or by a div id like 'viscanvas' - // Divs which do not have a 'special_parent' get plunked in the @topElem - this.prototype.div_has_special_parent = - {gclui: 'huvis_controls'}; - - this.prototype.needed_divs = [ - 'gclui', - 'performance_dashboard', - 'state_msg_box', - 'status', - 'viscanvas', - 'vissvg' - ]; - - this.prototype.needed_JQElems = [ - 'gclui', - 'performance_dashboard', - 'viscanvas', - 'huviz_controls' - ]; //.style('color','red') - - this.prototype.human_term = { - all: 'ALL', - chosen: 'CHOSEN', - unchosen: 'UNCHOSEN', - selected: 'SELECTED', - shelved: 'SHELVED', - discarded: 'DISCARDED', - hidden: 'HIDDEN', - graphed: 'GRAPHED', - fixed: 'PINNED', - labelled: 'LABELLED', - choose: 'CHOOSE', - unchoose: 'UNCHOOSE', - select: 'SELECT', - unselect: 'UNSELECT', - label: 'LABEL', - unlabel: 'UNLABEL', - shelve: 'SHELVE', - hide: 'HIDE', - discard: 'DISCARD', - undiscard: 'RETRIEVE', - pin: 'PIN', - unpin: 'UNPIN', - unpinned: 'UNPINNED', - nameless: 'NAMELESS', - blank_verb: 'VERB', - blank_noun: 'SET/SELECTION', - hunt: 'HUNT', - walk: 'WALK', - walked: 'WALKED', - wander: 'WANDER', - draw: 'DRAW', - undraw: 'UNDRAW', - connect: 'CONNECT', - spawn: 'SPAWN', - specialize: 'SPECIALIZE', - annotate: 'ANNOTATE', - suppress: "SUPPRESS" - }; - - // TODO add controls - // selected_border_thickness - // show_cosmetic_tabs - this.prototype.default_settings = [{ - reset_settings_to_default: { - text: "Reset Settings", - label: { - title: "Reset all settings to their defaults" - }, - input: { - type: "button", - label: "Reset" - } - } - } - , { - use_accordion_for_settings: { - text: "show Settings in accordion", - label: { - title: "Show the Settings Groups as an 'Accordion'" - }, - input: { - //checked: "checked" - type: "checkbox" - } - } - } - //style: "display:none" - , { - show_cosmetic_tabs: { - text: "Show Cosmetic Tabs", - label: { - title: "Expose the merely informational tabs such as 'Intro' and 'Credits'" - }, - input: { - type: "checkbox", - checked: "checked" - } - } - } - , { - focused_mag: { - group: "Labels", - text: "focused label mag", - input: { - value: 1.4, - min: 1, - max: 3, - step: .1, - type: 'range' - }, - label: { - title: "the amount bigger than a normal label the currently focused one is" - } - } - } - , { - selected_mag: { - group: "Labels", - text: "selected node mag", - input: { - value: 1.5, - min: 0.5, - max: 4, - step: .1, - type: 'range' - }, - label: { - title: "the amount bigger than a normal node the currently selected ones are" - } + if (new_state === 'showing') { + if (old_state === 'mixed' || old_state === 'unshowing' || old_state === 'empty') { + if (!(__indexOf.call(this.engaged_taxons, taxonId) >= 0)) { + this.engaged_taxons.push(taxonId); } + cmd = this.new_GraphCommand({ + verbs: ['select'], + classes: [taxonId], + every_class: every_class, + skip_history: skip_history + }); + } else { + console.error("no action needed because " + taxonId + "." + old_state + " == " + new_state); } - , { - label_em: { - group: "Labels", - text: "label size (em)", - label: { - title: "the size of the font" - }, - input: { - value: .9, - min: .1, - max: 4, - step: .05, - type: 'range' - } - } + } else if (new_state === 'unshowing') { + this.unselect_node_class(taxonId); + cmd = this.new_GraphCommand({ + verbs: ['unselect'], + classes: [taxonId], + every_class: every_class, + skip_history: skip_history + }); + } else if (old_state === "hidden") { + console.error("" + taxonId + ".old_state should NOT equal 'hidden' here"); + } + this.taxon_picker.style_with_kid_color_summary_if_needed(taxonId); + if (cmd != null) { + this.huviz.run_command(cmd, this.make_run_transient_and_cleanup_callback(because)); + because = {}; + } + this.update_command(); + }; + + CommandController.prototype.unselect_node_class = function(node_class) { + return this.engaged_taxons = this.engaged_taxons.filter(function(eye_dee) { + return eye_dee !== node_class; + }); + }; + + CommandController.prototype.make_verb_sets = function() { + this.verb_sets = [ + { + choose: this.huviz.human_term.choose, + unchoose: this.huviz.human_term.unchoose, + wander: this.huviz.human_term.wander, + walk: this.huviz.human_term.walk + }, { + select: this.huviz.human_term.select, + unselect: this.huviz.human_term.unselect + }, { + label: this.huviz.human_term.label, + unlabel: this.huviz.human_term.unlabel + }, { + shelve: this.huviz.human_term.shelve, + hide: this.huviz.human_term.hide + }, { + discard: this.huviz.human_term.discard, + undiscard: this.huviz.human_term.undiscard + }, { + pin: this.huviz.human_term.pin, + unpin: this.huviz.human_term.unpin } - , { - //snippet_body_em: - // text: "snippet body (em)" - // label: - // title: "the size of the snippet text" - // input: - // value: .7 - // min: .2 - // max: 4 - // step: .1 - // type: "range" - //, - charge: { - group: "Layout", - text: "charge (-)", - label: { - title: "the repulsive charge betweeen nodes" - }, - input: { - value: -210, - min: -600, - max: -1, - step: 1, - type: "range" - } - } + ]; + if (this.huviz.show_hunt_verb) { + return this.verb_sets.push({ + hunt: this.huviz.human_term.hunt + }); + } + }; + + CommandController.prototype.auto_change_verb_tests = { + select: function(node) { + if (node.selected != null) { + return 'unselect'; } - , { - gravity: { - group: "Layout", - text: "gravity", - label: { - title: "the attractive force keeping nodes centered" - }, - input: { - value: 0.50, - min: 0, - max: 1, - step: 0.025, - type: "range" - } - } + }, + unselect: function(node) { + if (node.selected == null) { + return 'select'; } - , { - shelf_radius: { - group: "Sizing", - text: "shelf radius", - label: { - title: "how big the shelf is" - }, - input: { - value: 0.8, - min: 0.1, - max: 3, - step: 0.05, - type: "range" - } - } + }, + choose: function(node) { + if (node.chosen != null) { + return 'unchoose'; } - , { - fisheye_zoom: { - group: "Sizing", - text: "fisheye zoom", - label: { - title: "how much magnification happens" - }, - input: { - value: 6.0, - min: 1, - max: 20, - step: 0.2, - type: "range" - } - } + }, + unchoose: function(node, engagedVerb) { + if (node.chosen == null) { + return 'choose' || engagedVerb; } - , { - fisheye_radius: { - group: "Sizing", - text: "fisheye radius", - label: { - title: "how big the fisheye is" - }, - input: { - value: 300, - min: 0, - max: 2000, - step: 20, - type: "range" - } - } + }, + wander: function(node) { + if (node.chosen != null) { + return 'wander'; } - , { - node_radius: { - group: "Sizing", - text: "node radius", - label: { - title: "how fat the nodes are" - }, - input: { - value: 3, - min: 0.5, - max: 50, - step: 0.1, - type: "range" - } - } + }, + walk: function(node) { + if (node.chosen != null) { + return 'walk'; } - , { - node_diff: { - group: "Sizing", - text: "node differentiation", - label: { - title: "size variance for node edge count" - }, - input: { - value: 1, - min: 0, - max: 10, - step: 0.1, - type: "range" - } - } + }, + label: function(node) { + if (node.labelled) { + return 'unlabel'; } - , { - focus_threshold: { - group: "Sizing", - text: "focus threshold", - label: { - title: "how fine is node recognition" - }, - input: { - value: 20, - min: 10, - max: 150, - step: 1, - type: "range" - } - } + }, + unlabel: function(node) { + if (!node.labelled) { + return 'label'; } - , { - link_distance: { - group: "Layout", - text: "link distance", - label: { - title: "how long the lines are" - }, - input: { - value: 29, - min: 5, - max: 500, - step: 2, - type: "range" - } - } + }, + unpin: function(node) { + if (!node.fixed) { + return 'pin'; } - , { - edge_width: { - group: "Sizing", - text: "line thickness", - label: { - title: "how thick the lines are" - }, - input: { - value: 0.2, - min: 0.2, - max: 10, - step: .2, - type: "range" - } - } + }, + pin: function(node) { + if (node.fixed) { + return 'unpin'; } - , { - line_edge_weight: { - group: "Sizing", - text: "line edge weight", - label: { - title: "how much thicker lines become to indicate the number of snippets" - }, - input: { - value: 0.45, - min: 0, - max: 1, - step: 0.01, - type: "range" + } + }; + + CommandController.prototype.should_be_immediate_mode = function() { + return !this.is_verb_phrase_empty() && this.is_command_object_empty() && !this.liking_all_mode; + }; + + CommandController.prototype.is_command_object_empty = function() { + return this.huviz.selected_set.length === 0 && (this.chosen_set == null); + }; + + CommandController.prototype.is_verb_phrase_empty = function() { + return this.engaged_verbs.length === 0; + }; + + CommandController.prototype.auto_change_verb_if_warranted = function(node) { + var next_verb, test, verb; + if (this.huviz.edit_mode) { + return; + } + if (this.immediate_execution_mode) { + if (this.engaged_verbs.length === 1) { + verb = this.engaged_verbs[0]; + test = this.auto_change_verb_tests[verb]; + if (test) { + next_verb = test(node, this.engaged_verbs[0]); + if (next_verb) { + this.engage_verb(next_verb, verb === this.transient_verb_engaged); } } } - , { - swayfrac: { - group: "Sizing", - text: "sway fraction", - label: { - title: "how much curvature lines have" - }, - input: { - value: 0.22, - min: -1.0, - max: 1.0, - step: 0.01, - type: "range" - } - } + return this.huviz.set_cursor_for_verbs(this.engaged_verbs); + } else { + return this.huviz.set_cursor_for_verbs([]); + } + }; + + CommandController.prototype.verbs_requiring_regarding = ['show', 'suppress', 'emphasize', 'deemphasize']; + + CommandController.prototype.verbs_override = { + choose: ['discard', 'unchoose', 'shelve', 'hide', 'wander', 'walk'], + wander: ['choose', 'unchoose', 'discard', 'shelve', 'hide', 'walk'], + walk: ['choose', 'unchoose', 'discard', 'shelve', 'hide', 'wander'], + shelve: ['unchoose', 'choose', 'hide', 'discard', 'retrieve', 'wander', 'walk'], + discard: ['choose', 'retrieve', 'hide', 'unchoose', 'unselect', 'select', 'wander', 'walk'], + hide: ['discard', 'undiscard', 'label', 'choose', 'unchoose', 'select', 'unselect', 'wander', 'walk'], + hunt: ['discard', 'undiscard', 'choose', 'unchoose', 'wander', 'walk', 'hide', 'unhide', 'shelve', 'pin', 'unpin'] + }; + + CommandController.prototype.verb_descriptions = { + choose: "Put nodes in the graph and pull other, connected nodes in too, so long as they haven't been discarded.", + wander: "Put nodes in the graph and pull connected nodes in followed by shelving of the nodes which had been pulled into the graph previously.", + walk: "Put nodes in the graph but keep the previous central nodes activated. Shelve previous sub-nodes.", + shelve: "Remove nodes from the graph and put them on the shelf (the circle of nodes around the graph) from which they might return if called back into the graph by a neighbor being chosen.", + hide: "Remove nodes from the graph and don't display them anywhere, though they might be called back into the graph when some other node calls it back in to show an edge.", + label: "Show the node's labels.", + unlabel: "Stop showing the node's labels.", + discard: "Put nodes in the discard bin (the small red circle which appears when you start dragging a node) from which they do not get called back into the graph unless they are first retrieved.", + undiscard: "Retrieve nodes from the discard bin (the small red circle which appears when you start dragging a node)) and put them back on the shelf.", + print: "Print associated snippets.", + redact: "Hide the associated snippets.", + show: "Show edges: 'Show (nodes) regarding (edges).' Add to the existing state of the graph edges from nodes of the classes indicated edges of the types indicated.", + suppress: "Stop showing: 'Suppress (nodes) regarding (edges).' Remove from the existing sate of the graph edges of the types indicated from nodes of the types classes indicated.", + specify: "Immediately specify the entire state of the graph with the constantly updating set of edges indicated from nodes of the classes indicated.", + load: "Load knowledge from the given uri.", + pin: "Make a node immobile", + unpin: "Make a node mobile again", + hunt: "Animate binary search for the node" + }; + + CommandController.prototype.verb_cursors = { + choose: "←", + unchoose: "⇠", + wander: "🚶", + walk: "🚶", + shelve: "↺", + label: "☭", + unlabel: "☢", + discard: "☣", + undiscard: "☯", + hide: "☠", + select: "☘", + unselect: "☺", + pin: "p", + unpin: "u", + hunt: "X" + }; + + CommandController.prototype.build_form = function() { + this.build_verb_form(); + this.build_depth(); + this.build_like(); + this.nextcommand = this.nextcommandbox.append('div').attr('class', 'nextcommand command'); + this.nextcommandstr = this.nextcommand.append('code'); + $(this.nextcommandstr[0][0]).addClass('nextcommand_str'); + if (this.nextcommand_prompts_visible && this.nextcommand_str_visible) { + this.nextcommand.append('hr'); + } + this.nextcommand_prompts = this.nextcommand.append('code'); + this.nextcommand_prompts.attr('class', 'nextcommand_prompt'); + this.nextcommand_verb_phrase = this.nextcommand_prompts.append('span'); + this.nextcommand_verb_phrase.attr('class', 'verb_phrase'); + this.nextcommand_noun_phrase = this.nextcommand_prompts.append('span'); + this.nextcommand_noun_phrase.attr('class', 'noun_phrase'); + this.nextcommand_suffix_phrase = this.nextcommand_prompts.append('span'); + this.nextcommand_suffix_phrase.attr('class', 'suffix_phrase'); + if (this.nextcommand_prompts_visible) { + $(this.nextcommand_prompts[0][0]).show(); + } else { + $(this.nextcommand_prompts[0][0]).hide(); + } + if (this.nextcommand_str_visible) { + $(this.nextcommandstr[0][0]).show(); + } else { + $(this.nextcommandstr[0][0]).hide(); + } + this.nextcommand_working = this.nextcommand.append('div').attr('class', 'cmd-spinner'); + this.nextcommand_working.style('float:right; color:red; display:none;'); + return this.build_submit(); + }; + + CommandController.prototype.working_timeout = 500; + + CommandController.prototype.start_working = function() { + log_click(); + if (this.already_working) { + clearTimeout(this.already_working); + } else { + this.show_working_on(); + } + return this.already_working = setTimeout(this.stop_working, this.working_timeout); + }; + + CommandController.prototype.stop_working = function() { + this.show_working_off(); + return this.already_working = void 0; + }; + + CommandController.prototype.show_working_on = function(cmd) { + if ((cmd != null) && !cmd.skip_history) { + this.push_command_onto_history(cmd); + } + this.nextcommand_working.attr('class', 'fa fa-spinner fa-spin'); + return this.nextcommand.attr('class', 'nextcommand command cmd-working'); + }; + + CommandController.prototype.show_working_off = function() { + this.nextcommand_working.attr('class', ''); + return this.nextcommand.attr('class', 'nextcommand command'); + }; + + CommandController.prototype.build_depth = function() { + this.depthdiv.text('Activate/Wander Depth:').classed("control_label activate_depth", true); + this.depthdiv.style('display', 'none'); + this.depthdiv.style('white-space', 'nowrap'); + this.depth_input = this.depthdiv.append('input'); + this.depth_input.attr('class', 'depth_input'); + this.depth_input.attr('placeholder', '1'); + this.depth_input.attr('type', 'number'); + this.depth_input.attr('min', '1'); + this.depth_input.attr('max', '9'); + return this.depth_input.attr('value', '1'); + }; + + CommandController.prototype.build_like = function() { + this.likediv.text('matching:').classed("control_label", true); + this.likediv.style('display', 'inline-block'); + this.likediv.style('white-space', 'nowrap'); + this.like_input = this.likediv.append('input'); + this.like_input.attr('class', 'like_input'); + this.like_input.attr('placeholder', 'node Name'); + this.liking_all_mode = false; + this.like_input.on('input', this.handle_like_input); + this.clear_like_button = this.likediv.append('button').text('⌫'); + this.clear_like_button.attr('type', 'button').classed('clear_like', true); + this.clear_like_button.attr('disabled', 'disabled'); + this.clear_like_button.attr('title', 'clear the "matching" field'); + return this.clear_like_button.on('click', this.handle_clear_like); + }; + + CommandController.prototype.handle_clear_like = function(evt) { + this.like_input.property('value', ''); + return this.handle_like_input(); + }; + + CommandController.prototype.handle_like_input = function(evt) { + var TODO, like_has_a_value, like_value; + like_value = this.get_like_string(); + like_has_a_value = !!like_value; + if (like_has_a_value) { + this.clear_like_button.attr('disabled', null); + if (this.liking_all_mode) { + TODO = "update the selection based on the like value"; + } else { + this.liking_all_mode = true; + this.chosen_set_before_liking_all = this.chosen_set_id; + this.set_immediate_execution_mode(this.is_verb_phrase_empty()); + this.huviz.click_set("all"); } - , { - label_graphed: { - group: "Labels", - text: "label graphed nodes", - style: "display:none", - label: { - title: "whether graphed nodes are always labelled" - }, - input: { - //checked: "checked" - type: "checkbox" - } + } else { + this.clear_like_button.attr('disabled', 'disabled'); + if (this.liking_all_mode) { + TODO = "restore the state before liking_all_mode " + "eg select a different set or disable all set selection"; + if (this.chosen_set_before_liking_all) { + this.huviz.click_set(this.chosen_set_before_liking_all); + this.chosen_set_before_liking_all = void 0; + } else { + this.huviz.click_set('all'); } + this.liking_all_mode = false; + this.set_immediate_execution_mode(true); + } else { + TODO = "do nothing ????"; } - , { - truncate_labels_to: { - group: "Labels", - text: "truncate and scroll", - label: { - title: "truncate and scroll labels longer than this, or zero to disable" - }, - input: { - value: 0, // 40 - min: 0, - max: 60, - step: 1, - type: "range" - } - } - } - , { - snippet_count_on_edge_labels: { - group: "Labels", - text: "snippet count on edge labels", - label: { - title: "whether edges have their snippet count shown as (#)" - }, - input: { - //checked: "checked" - type: "checkbox" - } - } - } - , { - nodes_pinnable: { - style: "display:none", - text: "nodes pinnable", - label: { - title: "whether repositioning already graphed nodes pins them at the new spot" - }, - input: { - checked: "checked", - type: "checkbox" - } - } - } - , { - use_fancy_cursor: { - style: "display:none", - text: "use fancy cursor", - label: { - title: "use custom cursor" - }, - input: { - checked: "checked", - type: "checkbox" - } + } + return this.update_command(evt); + }; + + CommandController.prototype.build_submit = function() { + this.doit_butt = this.nextcommand.append('span').append("input").attr("style", "float:right;").attr("type", "submit").attr('value', 'GO!').attr('class', 'doit_button'); + this.doit_butt.on('click', (function(_this) { + return function() { + if (_this.update_command()) { + return _this.huviz.run_command(_this.command); } + }; + })(this)); + return this.set_immediate_execution_mode(true); + }; + + CommandController.prototype.enable_doit_button = function() { + return this.doit_butt.attr('disabled', null); + }; + + CommandController.prototype.disable_doit_button = function() { + return this.doit_butt.attr('disabled', 'disabled'); + }; + + CommandController.prototype.hide_doit_button = function() { + return $(this.doit_butt[0][0]).hide(); + }; + + CommandController.prototype.show_doit_button = function() { + return $(this.doit_butt[0][0]).show(); + }; + + CommandController.prototype.set_immediate_execution_mode = function(which) { + if (which) { + this.hide_doit_button(); + } else { + this.show_doit_button(); + } + return this.immediate_execution_mode = which; + }; + + CommandController.prototype.update_immediate_execution_mode_as_warranted = function() { + return this.set_immediate_execution_mode(this.should_be_immediate_execution_mode()); + }; + + CommandController.prototype.disengage_all_verbs = function() { + var vid, _i, _len, _ref, _results; + _ref = this.engaged_verbs; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + vid = _ref[_i]; + _results.push(this.disengage_verb(vid)); + } + return _results; + }; + + CommandController.prototype.unselect_all_node_classes = function() { + var nid, _i, _len, _ref, _results; + _ref = this.engaged_taxons; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + nid = _ref[_i]; + this.unselect_node_class(nid); + _results.push(this.taxon_picker.set_direct_state(nid, 'unshowing')); + } + return _results; + }; + + CommandController.prototype.clear_like = function() { + return this.huviz.like_string(); + }; + + CommandController.prototype.get_like_string = function() { + return this.like_input[0][0].value; + }; + + CommandController.prototype.push_command = function(cmd) { + throw new Error('DEPRECATED'); + return this.push_command_onto_history(cmd); + }; + + CommandController.prototype.push_cmdArgs_onto_future = function(cmdArgs) { + return this.future_cmdArgs.push(cmdArgs); + }; + + CommandController.prototype.push_future_onto_history = function() { + var cmdArgs, _i, _len, _ref; + if (this.future_cmdArgs.length) { + this.huviz.goto_tab(3); + _ref = this.future_cmdArgs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + cmdArgs = _ref[_i]; + this.push_command_onto_history(this.new_GraphCommand(cmdArgs)); } - , { - doit_asap: { - style: "display:none", - text: "DoIt ASAP", - label: { - title: "execute commands as soon as they are complete" - }, - input: { - checked: "checked", // default to 'on' - type: "checkbox" - } - } + this.reset_command_history(); + this.command_idx0 = 0; + return this.update_script_buttons(); + } + }; + + CommandController.prototype.push_command_onto_history = function(cmd) { + var delete_button, elem, elem_and_cmd, idx_of_this_command; + this.clear_unreplayed_commands_if_needed(); + cmd.id = getRandomId('cmd'); + elem = this.oldcommands.append('div').attr('class', 'played command').attr('id', cmd.id); + this.commandhistory_JQElem.scrollTop(this.commandhistory_JQElem.scrollHeight); + elem_and_cmd = { + elem: elem, + cmd: cmd + }; + this.command_list.push(elem_and_cmd); + this.command_idx0 = this.command_list.length; + idx_of_this_command = this.command_idx0; + this.disable_play_buttons(); + elem.text(cmd.str + "\n"); + delete_button = elem.append('a'); + delete_button.attr('class', 'delete-command'); + delete_button.on('click', (function(_this) { + return function() { + return _this.delete_script_command_by_id(cmd.id); + }; + })(this)); + return this.update_script_buttons(); + }; + + CommandController.prototype.clear_unreplayed_commands_if_needed = function() { + while (this.command_idx0 < this.command_list.length) { + this.delete_script_command_by_idx(this.command_list.length - 1); + } + }; + + CommandController.prototype.delete_script_command_by_id = function(cmd_id) { + var elem_and_cmd, idx, _i, _len, _ref; + _ref = this.command_list; + for (idx = _i = 0, _len = _ref.length; _i < _len; idx = ++_i) { + elem_and_cmd = _ref[idx]; + if (elem_and_cmd.cmd.id === cmd_id) { + this.delete_script_command_by_idx(idx); + break; } - , { - show_dangerous_datasets: { - style: "display:none", - text: "Show dangerous datasets", - label: { - title: "Show the datasets which are too large or buggy" - }, - input: { - type: "checkbox" - } + } + }; + + CommandController.prototype.delete_script_command_by_idx = function(idx) { + var elem, elem_and_cmd, orphan, pops; + elem_and_cmd = this.command_list.splice(idx, 1)[0]; + elem = elem_and_cmd.elem[0]; + if (!elem || !elem[0]) { + return; + } + orphan = elem[0]; + pops = orphan.parentNode; + pops.removeChild(orphan); + if (idx < this.command_idx0) { + this.command_idx0--; + } + if (this.command_idx0 < 0) { + this.command_idx0 = 0; + } + return this.update_script_buttons(); + }; + + CommandController.prototype.update_script_buttons = function() { + if (this.command_list.length > 1) { + this.enable_save_buttons(); + } else { + this.disable_save_buttons(); + } + if (this.command_idx0 >= this.command_list.length) { + this.disable_play_buttons(); + } else { + this.enable_play_buttons(); + } + if (this.command_idx0 > 0) { + this.enable_back_buttons(); + } + if (this.command_idx0 <= 0) { + return this.disable_back_buttons(); + } + }; + + CommandController.prototype.disable_play_buttons = function() { + this.scriptPlayButton.attr('disabled', 'disabled'); + return this.scriptForwardButton.attr('disabled', 'disabled'); + }; + + CommandController.prototype.enable_play_buttons = function() { + this.scriptForwardButton.attr('disabled', null); + return this.scriptPlayButton.attr('disabled', null); + }; + + CommandController.prototype.disable_back_buttons = function() { + this.scriptBackButton.attr('disabled', 'disabled'); + return this.scriptRewindButton.attr('disabled', 'disabled'); + }; + + CommandController.prototype.enable_back_buttons = function() { + this.scriptBackButton.attr('disabled', null); + return this.scriptRewindButton.attr('disabled', null); + }; + + CommandController.prototype.disable_save_buttons = function() { + this.scriptDownloadButton.attr('disabled', 'disabled'); + return this.scriptStashButton.attr('disabled', 'disabled'); + }; + + CommandController.prototype.enable_save_buttons = function() { + this.scriptDownloadButton.attr('disabled', null); + return this.scriptStashButton.attr('disabled', null); + }; + + CommandController.prototype.build_command = function() { + var args, class_name, like_str, v, _i, _len, _ref; + args = { + verbs: [] + }; + args.object_phrase = this.object_phrase; + if (this.engaged_verbs.length > 0) { + _ref = this.engaged_verbs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + v = _ref[_i]; + if (v !== this.transient_verb_engaged) { + args.verbs.push(v); } } - , { - pill_display: { - group: "Labels", - text: "Display graph with boxed labels", - label: { - title: "Show boxed labels on graph" - }, - input: { - type: "checkbox" - } + } + if ((this.regarding != null) && this.regarding.length) { + args.regarding = this.regarding.slice(); + args.regarding_every = this.regarding_every; + } + if (this.proposed_verb) { + args.verbs.push(this.proposed_verb); + } + if (this.chosen_set_id) { + args.sets = [this.chosen_set]; + } else if (this.proposed_set) { + args.sets = [this.proposed_set]; + } else { + if (this.proposed_taxon) { + args.every_class = this.proposed_every; + args.classes = [this.proposed_taxon]; + } else { + if (this.engaged_taxons.length > 0) { + args.classes = (function() { + var _j, _len1, _ref1, _results; + _ref1 = this.engaged_taxons; + _results = []; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + class_name = _ref1[_j]; + _results.push(class_name); + } + return _results; + }).call(this); } - } - //checked: "checked" - , { - theme_colors: { - group: "Styling", - text: "Display graph with dark theme", - label: { - title: "Show graph plotted on a black background" - }, - input: { - type: "checkbox" - } + if (this.huviz.selected_set.length > 0) { + args.sets = ['selected']; } } - , { - paint_label_dropshadows: { - group: "Styling", - text: "Draw drop-shadows behind labels", - label: { - title: "Make labels more visible when overlapping" - }, - input: { - type: "checkbox", - checked: "checked" - } - } + } + like_str = (this.like_input[0][0].value || "").trim(); + if (like_str) { + args.like = like_str; + } + return this.command = this.new_GraphCommand(args); + }; + + CommandController.prototype.is_proposed = function() { + return this.proposed_verb || this.proposed_set || this.proposed_taxon; + }; + + CommandController.prototype.update_command = function(because) { + because = because || {}; + this.huviz.show_state_msg("update_command"); + this.run_any_immediate_command(because); + return this.huviz.hide_state_msg(); + }; + + CommandController.prototype.run_any_immediate_command = function(because) { + var ready; + ready = this.prepare_command(this.build_command()); + if (ready && this.huviz.doit_asap && this.immediate_execution_mode && !this.is_proposed()) { + this.perform_current_command(because); + } + }; + + CommandController.prototype.perform_current_command = function(because) { + var start; + this.show_working_on(this.command); + if (this.huviz.slow_it_down) { + start = Date.now(); + while (Date.now() < start + (this.huviz.slow_it_down * 1000)) { + console.log(Math.round((Date.now() - start) / 1000)); } - , { - display_shelf_clockwise: { - group: "Styling", - text: "Display nodes clockwise", - label: { - title: "Display clockwise (uncheck for counter-clockwise)" - }, - input: { - type: "checkbox", - checked: "checked" - } - } + } + this.command.execute(); + this.huviz.update_all_counts(); + this.perform_any_cleanup(because); + return this.show_working_off(); + }; + + CommandController.prototype.perform_any_cleanup = function(because) { + if ((because != null) && because.cleanup) { + because.cleanup(); + this.update_command(); + } + }; + + CommandController.prototype.nextcommand_prompts_visible = true; + + CommandController.prototype.nextcommand_str_visible = false; + + CommandController.prototype.prepare_command = function(cmd) { + this.command = cmd; + if (this.nextcommand_prompts_visible || true) { + this.nextcommand_verb_phrase.text(this.command.verb_phrase); + if (this.command.verb_phrase_ready) { + $(this.nextcommand_verb_phrase[0][0]).addClass('nextcommand_prompt_ready').removeClass('nextcommand_prompt_unready'); + } else { + $(this.nextcommand_verb_phrase[0][0]).removeClass('nextcommand_prompt_ready').addClass('nextcommand_prompt_unready'); } - , { - choose_node_display_angle: { - group: "Styling", - text: "Node display angle", - label: { - title: "Where on shelf to place first node" - }, - input: { - value: 0.5, - min: 0, - max: 1, - step: 0.25, - type: "range" - } - } + this.nextcommand_noun_phrase.text(this.command.noun_phrase); + if (this.command.noun_phrase_ready) { + $(this.nextcommand_noun_phrase[0][0]).addClass('nextcommand_prompt_ready').removeClass('nextcommand_prompt_unready'); + } else { + $(this.nextcommand_noun_phrase[0][0]).removeClass('nextcommand_prompt_ready').addClass('nextcommand_prompt_unready'); } - , { - language_path: { - group: "Ontological", - text: "Language Path", - label: { - title: `Using ':' as separator and with ANY and NOLANG as possible values, -a list of the languages to expose, in order of preference. -Examples: "en:fr" means show English before French or nothing; -"ANY:en" means show any language before showing English; -"en:ANY:NOLANG" means show English if available, then any other -language, then finally labels in no declared language.\ -` - }, - input: { - type: "text", - // TODO tidy up -- use browser default language then English - value: (window.navigator.language.substr(0,2) + ":en:ANY:NOLANG").replace("en:en:","en:"), - size: "16", - placeholder: "en:es:fr:de:ANY:NOLANG" + this.nextcommand_suffix_phrase.text(this.command.suffix_phrase); + } + if (this.nextcommand_str_visible || true) { + this.nextcommandstr.text(this.command.str); + } + if (this.command.ready) { + this.enable_doit_button(); + } else { + this.disable_doit_button(); + } + return this.command.ready; + }; + + CommandController.prototype.ready_to_perform = function() { + var permit_multi_select; + permit_multi_select = true; + return (this.transient_verb_engaged === 'unselect') || (!this.object_phrase && (this.engaged_verbs.length > 0)) || (permit_multi_select && (this.engaged_verbs.length === 1 && this.engaged_verbs[0] === 'select')); + }; + + CommandController.prototype.build_verb_form = function() { + var vset, _i, _len, _ref, _results; + this.verb_pretty_name = {}; + _ref = this.verb_sets; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + vset = _ref[_i]; + _results.push(this.add_verb_set(vset)); + } + return _results; + }; + + CommandController.prototype.add_verb_set = function(vset) { + var alternatives, id, label; + alternatives = this.verbdiv.append('div').attr('class', 'alternates'); + for (id in vset) { + label = vset[id]; + this.verb_pretty_name[id] = label; + this.build_verb_picker(id, label, alternatives); + } + this.verb_pretty_name['load'] = this.huviz.human_term.load; + this.verb_pretty_name['hunt'] = this.huviz.human_term.hunt; + this.verb_pretty_name['draw'] = this.huviz.human_term.draw; + this.verb_pretty_name['undraw'] = this.huviz.human_term.undraw; + return alternatives; + }; + + CommandController.prototype.get_verbs_overridden_by = function(verb_id) { + var label, override, vid, vset, _i, _len, _ref; + override = this.verbs_override[verb_id] || []; + _ref = this.verb_sets; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + vset = _ref[_i]; + if (vset[verb_id]) { + for (vid in vset) { + label = vset[vid]; + if (!(__indexOf.call(override, vid) >= 0) && verb_id !== vid) { + override.push(vid); } } } - , { - ontological_settings_preamble: { - group: "Ontological", - text: "Set before data ingestion...", - label: { - title: `The following settings must be adjusted before -data ingestion for them to take effect.` - } - } + } + return override; + }; + + CommandController.prototype.engaged_verbs = []; + + + /* + The "Do it" button is not needed if the following hold... + + If there is an object_phrase then the instant a verb is picked the command + should run. + + If there are verbs picked then the instant there is an object_phrase the + command should run and the object_phrase cleared. (what about selected_set?) + + Note that this covers immediate execution of transient verbs select/unselect + */ + + CommandController.prototype.are_non_transient_verbs = function() { + var len_transient; + len_transient = (this.transient_verb_engaged != null) && 1 || 0; + return this.engaged_verbs.length > len_transient; + }; + + CommandController.prototype.engage_transient_verb_if_needed = function(verb_id) { + if (this.engaged_verbs.length === 0 && !this.are_non_transient_verbs()) { + return this.engage_verb(verb_id, true); + } + }; + + CommandController.prototype.disengage_transient_verb_if_needed = function() { + if (this.transient_verb_engaged) { + this.disengage_verb(this.transient_verb_engaged); + this.huviz.set_cursor_for_verbs(this.engaged_verbs); + return this.update_command(); + } + }; + + CommandController.prototype.engage_verb = function(verb_id, transient) { + var overrides, vid, _i, _len, _ref; + if (transient) { + this.transient_verb_engaged = verb_id; + this.verb_control[verb_id].classed('transient', true); + } + overrides = this.get_verbs_overridden_by(verb_id); + this.verb_control[verb_id].classed('engaged', true); + _ref = this.engaged_verbs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + vid = _ref[_i]; + if (__indexOf.call(overrides, vid) >= 0) { + this.disengage_verb(vid); } - , { - show_class_instance_edges: { - group: "Ontological", - text: "Show class-instance relationships", - label: { - title: "display the class-instance relationship as an edge" - }, - input: { - type: "checkbox" - } - } + } + if (!(__indexOf.call(this.engaged_verbs, verb_id) >= 0)) { + return this.engaged_verbs.push(verb_id); + } + }; + + CommandController.prototype.disengage_verb = function(verb_id, transient) { + this.engaged_verbs = this.engaged_verbs.filter(function(verb) { + return verb !== verb_id; + }); + this.verb_control[verb_id].classed('engaged', false); + if (verb_id === this.transient_verb_engaged) { + this.transient_verb_engaged = false; + return this.verb_control[verb_id].classed('transient', false); + } + }; + + CommandController.prototype.verb_control = {}; + + CommandController.prototype.build_verb_picker = function(id, label, alternatives) { + var that, vbctl; + vbctl = alternatives.append('div').attr("class", "verb"); + if (this.verb_descriptions[id]) { + vbctl.attr("title", this.verb_descriptions[id]); + } + vbctl.attr("id", "verb-" + id); + this.verb_control[id] = vbctl; + vbctl.text(label); + that = this; + vbctl.on('click', (function(_this) { + return function() { + return _this.handle_on_verb_clicked(id, vbctl); + }; + })(this)); + vbctl.on('mouseenter', function() { + var because, click_would_engage, elem; + elem = d3.select(this); + click_would_engage = !elem.classed('engaged'); + because = {}; + if (click_would_engage) { + that.proposed_verb = id; + because = { + proposed_verb: id + }; + } else { + that.proposed_verb = null; } - //checked: "checked" - , { - use_lid_as_node_name: { - group: "Ontological", - text: "Use local-id as node name", - label: { - title: "Use the local-id of a resource as its node name, permitting display of nodes nothing else is known about." - }, - input: { - type: "checkbox" - } - } + return that.update_command(because); + }); + return vbctl.on('mouseleave', function() { + var because, elem, leaving_verb_id; + elem = d3.select(this); + leaving_verb_id = elem.classed('engaged'); + because = { + verb_leaving: leaving_verb_id + }; + that.proposed_verb = null; + return that.update_command(because); + }); + }; + + CommandController.prototype.handle_on_verb_clicked = function(id, elem) { + this.start_working(); + return setTimeout((function(_this) { + return function() { + return _this.on_verb_clicked(id, elem); + }; + })(this)); + }; + + CommandController.prototype.on_verb_clicked = function(id, elem) { + var because, newstate; + newstate = !elem.classed('engaged'); + elem.classed('engaged', newstate); + if (newstate) { + this.engage_verb(id); + if (id === "walk") { + this.taxon_picker.shield(); + this.set_picker.shield(); + } + this.proposed_verb = null; + because = { + verb_added: id, + cleanup: this.disengage_all_verbs + }; + } else { + if (id === "walk") { + this.taxon_picker.unshield(); + this.set_picker.unshield(); } - //checked: "checked" - , { - make_nodes_for_literals: { - group: "Ontological", - text: "Make nodes for literals", - label: { - title: "show literal values (dates, strings, numbers) as nodes" - }, - input: { - type: "checkbox", - checked: "checked" - }, - event_type: "change" + this.disengage_verb(id); + } + if ((this.engaged_verbs == null) || this.engaged_verbs.length === 0) { + this.huviz.set_cursor_for_verbs([]); + } + return this.update_command(because); + }; + + CommandController.prototype.run_script = function(script) { + script = script.replace(/[\u237D\u2420]/g, " "); + this.huviz.gclc.run(script); + return this.huviz.update_all_counts(); + }; + + CommandController.prototype.build_set_picker = function(label, where) { + where = (label != null) && this.control_label(label, where) || this.comdiv; + this.the_sets = { + 'all_set': [ + this.huviz.all_set.label, { + selected_set: [this.huviz.selected_set.label], + chosen_set: [this.huviz.chosen_set.label], + graphed_set: [this.huviz.graphed_set.label], + shelved_set: [this.huviz.shelved_set.label], + hidden_set: [this.huviz.hidden_set.label], + discarded_set: [this.huviz.discarded_set.label], + labelled_set: [this.huviz.labelled_set.label], + pinned_set: [this.huviz.pinned_set.label], + nameless_set: [this.huviz.nameless_set.label], + walked_set: [this.huviz.walked_set.label], + suppressed_set: [this.huviz.suppressed_set.label] } + ] + }; + this.set_picker_box = where.append('div').classed('container', true).attr('id', 'sets'); + this.set_picker = new TreePicker(this.set_picker_box, 'all', ['treepicker-vertical']); + this.set_picker.click_listener = this.handle_on_set_picked; + this.set_picker.show_tree(this.the_sets, this.set_picker_box); + this.populate_all_set_docs(); + this.make_sets_proposable(); + where.classed("set_picker_box_parent", true); + return where; + }; + + CommandController.prototype.populate_all_set_docs = function() { + var a_set, id, _ref, _results; + _ref = this.huviz.selectable_sets; + _results = []; + for (id in _ref) { + a_set = _ref[id]; + if (a_set.docs != null) { + _results.push(this.set_picker.set_title(id, a_set.docs)); + } else { + _results.push(void 0); } - , { - group_literals_by_subj_and_pred: { - group: "Ontological", - text: "Group literals by subject & predicate", - label: { - title: `Group literals together as a single node when they have -a language indicated and they share a subject and predicate, on the -theory that they are different language versions of the same text.` - }, - input: { - type: "checkbox", - checked: "checked" - } - } + } + return _results; + }; + + CommandController.prototype.make_sets_proposable = function() { + var a_set, id, make_listeners, _ref, _results; + make_listeners = (function(_this) { + return function(id, a_set) { + var set_ctl; + set_ctl = _this.set_picker.id_to_elem[id]; + set_ctl.on('mouseenter', function() { + _this.proposed_set = a_set; + return _this.update_command(); + }); + return set_ctl.on('mouseleave', function() { + _this.proposed_set = null; + return _this.update_command(); + }); + }; + })(this); + _ref = this.huviz.selectable_sets; + _results = []; + for (id in _ref) { + a_set = _ref[id]; + _results.push(make_listeners(id, a_set)); + } + return _results; + }; + + CommandController.prototype.handle_on_set_picked = function(set_id, new_state) { + this.start_working(); + return setTimeout((function(_this) { + return function() { + return _this.on_set_picked(set_id, new_state); + }; + })(this)); + }; + + CommandController.prototype.on_set_picked = function(set_id, new_state) { + var XXXcmd, because, cmd, hasVerbs; + this.clear_set_picker(); + this.set_picker.set_direct_state(set_id, new_state); + because = {}; + hasVerbs = !!this.engaged_verbs.length; + if (new_state === 'showing') { + this.taxon_picker.shield(); + this.chosen_set = this.huviz[set_id]; + this.chosen_set_id = set_id; + because = { + set_added: set_id, + cleanup: this.disengage_all_sets + }; + if (hasVerbs) { + cmd = new gcl.GraphCommand(this.huviz, { + verbs: this.engaged_verbs, + sets: [this.chosen_set.id] + }); } - , { - color_nodes_as_pies: { - group: "Ontological", - text: "Color nodes as pies", - label: { - title: "Show all a nodes types as colored pie pieces." - }, - input: { - type: "checkbox" - } - } - } //checked: "checked" - , { - suppress_annotation_edges: { - group: "Annotation", - text: "Suppress Annotation Edges", - label: { - title: `Do not show Open Annotation edges or nodes. -Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` - }, - input: { - type: "checkbox" - } - } + } else if (new_state === 'unshowing') { + this.taxon_picker.unshield(); + XXXcmd = new gcl.GraphCommand(this.huviz, { + verbs: ['unselect'], + sets: [this.chosen_set.id] + }); + this.disengage_all_sets(); + } + if (cmd != null) { + this.huviz.run_command(cmd, this.make_run_transient_and_cleanup_callback(because)); + because = {}; + } + return this.update_command(); + }; + + CommandController.prototype.disengage_all_sets = function() { + if (this.chosen_set_id) { + this.on_set_picked(this.chosen_set_id, "unshowing"); + delete this.chosen_set_id; + return delete this.chosen_set; + } + }; + + CommandController.prototype.clear_all_sets = function() { + var cleanup_verb, cmd, set_key, set_label, skip_sets, the_set, _ref; + skip_sets = ['shelved_set']; + _ref = this.the_sets.all_set[1]; + for (set_key in _ref) { + set_label = _ref[set_key]; + if (__indexOf.call(skip_sets, set_key) >= 0) { + continue; } - //checked: "checked" - , { - show_hide_endpoint_loading: { - style: "display:none", - class: "alpha_feature", - text: "Show SPARQL endpoint loading forms", - label: { - title: "Show SPARQL endpoint interface for querying for nodes" - }, - input: { - type: "checkbox" - } - } + the_set = this.huviz[set_key]; + cleanup_verb = the_set.cleanup_verb; + cmd = new gcl.GraphCommand(this.huviz, { + verbs: [cleanup_verb], + sets: [the_set.id] + }); + this.huviz.run_command(cmd); + } + }; + + CommandController.prototype.on_set_count_update = function(set_id, count) { + return this.set_picker.set_payload(set_id, count); + }; + + CommandController.prototype.on_taxon_count_update = function(taxon_id, count) { + return this.taxon_picker.set_payload(taxon_id, count); + }; + + CommandController.prototype.on_predicate_count_update = function(pred_lid, count) { + return this.predicate_picker.set_payload(pred_lid, count); + }; + + CommandController.prototype.clear_set_picker = function() { + if (this.chosen_set_id != null) { + this.set_picker.set_direct_state(this.chosen_set_id, 'unshowing'); + return delete this.chosen_set_id; + } + }; + + return CommandController; + + })(); + + (typeof exports !== "undefined" && exports !== null ? exports : this).CommandController = CommandController; + +}).call(this); +}, "graphcommandlanguage": function(exports, require, module) {(function() { + var GCLTest, GCLTestSuite, GraphCommand, GraphCommandLanguageCtrl, angliciser, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }; + + angliciser = require('angliciser').angliciser; + + GCLTest = (function() { + function GCLTest(runner, spec) { + this.runner = runner; + this.spec = spec; + console.log("GCLTest", this); + } + + GCLTest.prototype.perform = function() { + var e, exp, expected, got, msg, _i, _len, _ref, _ref1; + if (this.spec.script) { + this.runner.gclc.run(this.spec.script); + } + _ref1 = (_ref = this.spec.expectations) != null ? _ref : []; + for (_i = 0, _len = _ref1.length; _i < _len; _i++) { + exp = _ref1[_i]; + console.log("exp", exp); + try { + got = eval(exp[0]); + } catch (_error) { + e = _error; + throw new Error("while eval('" + exp[0] + "') caught: " + e); } - , { - graph_title_style: { - group: "Captions", - text: "Title display ", - label: { - title: "Select graph title style" - }, - input: { - type: "select" - }, - options : [{ - label: "Watermark", - value: "subliminal", - selected: true - } - , { - label: "Bold Titles 1", - value: "bold1" - } - , { - label: "Bold Titles 2", - value: "bold2" - } - , { - label: "Custom Captions", - value: "custom" - } - ] - } + expected = exp[1]; + if (this.runner.verbose) { + console.log("got=" + got + " expected:" + expected); } - , { - graph_custom_main_title: { - group: "Captions", - style: "display:none", - text: "Custom Title", - label: { - title: "Title that appears on the graph background" - }, - input: { - type: "text", - size: "16", - placeholder: "Enter Title" - } - } + if (got !== expected) { + msg = msg != null ? msg : "'" + this.spec.desc + "' " + exp[0] + " = " + got + " not " + expected; + return msg; } - , { - graph_custom_sub_title: { - group: "Captions", - style: "display:none", - text: "Custom Sub-title", - label: { - title: "Sub-title that appears below main title" - }, - input: { - type: "text", - size: "16", - placeholder: "Enter Sub-title" - } + } + }; + + return GCLTest; + + })(); + + GCLTestSuite = (function() { + + /* + * callback = function(){ + * this.expect(this.graph_ctrl.nodes.length,7); + * this.expect(this.graph_ctrl.shelved_set.length,0); + * } + * ts = new GCLTestSuite(gclc, [ + * {script:"choose 'abdyma'", + * expectations: [ + * ["this.graph_ctrl.nodes.length",7], + * ["this.graph_ctrl.shelved_set.length",0], + * ] + * } + * ]) + */ + function GCLTestSuite(huviz, suite) { + this.huviz = huviz; + this.suite = suite; + console.log("GCLTestSuite() arguments", arguments); + this.break_quickly = true; + } + + GCLTestSuite.prototype.emit = function(txt, id) { + return $("#testsuite-results").append("div").attr("id", id).text(txt); + }; + + GCLTestSuite.prototype.run = function() { + var e, err, errors, fail, fails, num, pass_count, passed, retval, spec, test, _i, _j, _k, _len, _len1, _len2, _ref, _results; + pass_count = 0; + errors = []; + fails = []; + num = 0; + this.emit("RUNNING", "running"); + _ref = this.suite; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + spec = _ref[_i]; + num++; + passed = false; + console.log("spec:", spec); + test = new GCLTest(this, spec); + try { + retval = test.perform(); + if (this.verbose) { + console.log(retval); } - } - , { - discover_geonames_as: { - group: "Geonames", - html_text: 'Username ', - label: { - title: "The GeoNames Username to look up geonames as" - }, - input: { - jsWidgetClass: GeoUserNameWidget, - type: "text", - value: "huviz", // "smurp_nooron" - size: "14", - placeholder: "e.g. huviz" - } + if (retval != null) { + fails.push([num, retval]); + } else { + passed = true; + pass_count++; } + } catch (_error) { + e = _error; + errors.push([num, e]); } - , { - discover_geonames_remaining: { - group: "Geonames", - text: 'GeoNames Limit ', - label: { - title: "The number of Remaining Geonames to look up" - }, - input: { - type: "integer", - value: 20, - size: 6 - } - } + if (!passed && this.break_quickly) { + break; } - , { - discover_geonames_greedily: { - group: "Geonames", - text: "Capture GeoNames Greedily", - label: { - title: "Capture not just names but populations too." - }, - input: { - type: "checkbox" - } - } + } + console.log("passed:" + pass_count + " failed:" + fails.length, " errors:" + errors.length); + for (_j = 0, _len1 = fails.length; _j < _len1; _j++) { + fail = fails[_j]; + console.log("test#" + fail[0], fail[1]); + } + _results = []; + for (_k = 0, _len2 = errors.length; _k < _len2; _k++) { + err = errors[_k]; + _results.push(console.log("err#" + err[0], err[1])); + } + return _results; + }; + + return GCLTestSuite; + + })(); + + GraphCommand = (function() { + function GraphCommand(huviz, args_or_str) { + var argn, args, argv; + this.huviz = huviz; + if (args_or_str instanceof GraphCommand) { + throw new Error("nested GraphCommand no longer permitted"); + } + this.prefixes = {}; + this.args_or_str = args_or_str; + if (typeof args_or_str === 'string') { + args = this.parse(args_or_str); + } else { + args = args_or_str; + } + if (args.skip_history == null) { + args.skip_history = false; + } + if (args.every_class == null) { + args.every_class = false; + } + for (argn in args) { + argv = args[argn]; + this[argn] = argv; + } + if (this.str == null) { + this.update_str(); + } + } + + GraphCommand.prototype.get_node = function(node_spec) { + var abbr, id, id_parts, msg, node, prefix, term, tried, _ref; + if (node_spec.id) { + node = this.huviz.nodes.get({ + 'id': node_spec.id + }); + } + if (node) { + return node; + } + tried = [node_spec]; + id_parts = node_spec.split(':'); + if (id_parts.length > 1) { + abbr = id_parts[0]; + id = id_parts[1]; + prefix = this.prefixes[abbr]; + if (prefix) { + term = prefix + id; + node = this.huviz.nodes.get({ + 'id': term + }); + tried.push(term); } - //checked: "checked" - , { - discover_geonames_deeply: { - group: "Geonames", - text: "Capture GeoNames Deeply", - label: { - title: "Capture not just directly referenced but also the containing geographical places from GeoNames." - }, - input: { - type: "checkbox" - } + } + if (!node) { + _ref = this.prefixes; + for (abbr in _ref) { + prefix = _ref[abbr]; + if (!node) { + term = prefix + id; + tried.push(term); + node = this.huviz.nodes.get({ + 'id': term + }); } } - //checked: "checked" - , { - show_edge_labels_adjacent_to_labelled_nodes: { - group: "Labels", - text: "Show adjacent edge labels", - label: { - title: "Show edge labels adjacent to labelled nodes" - }, - input: { - type: "checkbox" + } + if (!node) { + msg = "node with id = " + term + " not found among " + this.huviz.nodes.length + " nodes: " + tried; + console.warn(msg); + throw new Error(msg); + } + return node; + }; + + GraphCommand.prototype.get_nodes = function() { + var a_set, a_set_id, class_name, like_regex, n, node, node_spec, result_set, set, the_set, _i, _j, _k, _l, _len, _len1, _len2, _len3, _len4, _len5, _m, _n, _ref, _ref1, _ref2, _ref3; + result_set = SortedSet().sort_on("id"); + like_regex = null; + if (this.like) { + like_regex = new RegExp(this.like, "ig"); + } + if (this.subjects) { + _ref = this.subjects; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node_spec = _ref[_i]; + node = this.get_node(node_spec); + if (node) { + if ((like_regex == null) || node.name.match(like_regex)) { + result_set.add(node); } - } - } - //checked: "checked" - , { - show_edges: { - class: "alpha_feature", - text: "Show Edges", - label: { - title: "Do draw edges" - }, - input: { - type: "checkbox", - checked: "checked" + } else { + if (this.classes == null) { + this.classes = []; } + this.classes.push(node_spec.id); } } - , { - center_the_distinguished_node: { - class: "alpha_feature", - text: "Center the distinguished node", - label: { - title: "Center the most interesting node" - }, - input: { - type: "checkbox", - checked: "checked" + } + if (this.classes) { + _ref1 = this.classes; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + class_name = _ref1[_j]; + the_set = (_ref2 = this.huviz.taxonomy[class_name]) != null ? _ref2.get_instances() : void 0; + if (the_set != null) { + if (like_regex) { + for (_k = 0, _len2 = the_set.length; _k < _len2; _k++) { + n = the_set[_k]; + if (n.name.match(like_regex)) { + result_set.add(n); + } + } + } else { + for (_l = 0, _len3 = the_set.length; _l < _len3; _l++) { + n = the_set[_l]; + result_set.add(n); + } } } } - , { - arrows_chosen: { - class: "alpha_feature", - text: "Arrowheads on Edges", - label: { - title: "Displays directional arrowheads on the 'object' end of lines." - }, - input: { - type: "checkbox", - checked: "checked" - } + } + if (this.sets) { + _ref3 = this.sets; + for (_m = 0, _len4 = _ref3.length; _m < _len4; _m++) { + set = _ref3[_m]; + if (typeof set === 'string') { + a_set_id = set; + a_set = this.huviz.get_set_by_id(a_set_id); + } else { + a_set = set; } - } - , { - show_images_in_nodes: { - group: "Images", - class: "alpha_feature", - text: "Show Images in Nodes", - label: { - title: "Show dbpedia:thumbnail and foaf:thumbnail in nodes when available" - }, - input: { - type: "checkbox", - checked: "checked" + for (_n = 0, _len5 = a_set.length; _n < _len5; _n++) { + node = a_set[_n]; + if ((like_regex == null) || node.name.match(like_regex)) { + result_set.add(node); } } } - , { - show_thumbs_dont_graph: { - group: "Images", - class: "alpha_feature", - text: "Show thumbnails, don't graph", - label: { - title: "Treat dbpedia:thumbnail and foaf:thumbnail as images, not graph data" - }, - input: { - type: "checkbox", - checked: "checked" - } + } + return result_set; + }; + + GraphCommand.prototype.get_methods = function() { + var method, methods, msg, verb, _i, _len, _ref; + methods = []; + _ref = this.verbs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + verb = _ref[_i]; + method = this.huviz[verb]; + if (method) { + method.build_callback = this.huviz["" + verb + "__build_callback"]; + method.callback = this.huviz["" + verb + "__atLast"]; + method.atFirst = this.huviz["" + verb + "__atFirst"]; + methods.push(method); + } else { + msg = "method '" + verb + "' not found"; + console.error(msg); + } + } + return methods; + }; + + GraphCommand.prototype.get_predicate_methods = function() { + var method, methods, msg, verb, _i, _len, _ref; + methods = []; + _ref = this.verbs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + verb = _ref[_i]; + method = this.huviz[verb + "_edge_regarding"]; + if (method) { + methods.push(method); + } else { + msg = "method '" + verb + "' not found"; + console.error(msg); + } + } + return methods; + }; + + GraphCommand.prototype.regarding_required = function() { + return (this.regarding != null) && this.regarding.length > 0; + }; + + GraphCommand.prototype.execute = function() { + var USE_ASYNC, atFirst, callback, errorHandler, iter, meth, node, nodes, regarding_required, _i, _j, _k, _len, _len1, _len2, _ref, _ref1; + this.huviz.show_state_msg(this.as_msg()); + this.huviz.force.stop(); + regarding_required = this.regarding_required(); + nodes = this.get_nodes(); + console.log("%c" + this.str, "color:blue;font-size:1.5em;", "on " + nodes.length + " nodes"); + errorHandler = function(err_arg) { + if (err_arg != null) { + console.error("err =", err_arg); + if (err_arg == null) { + throw "err_arg is null"; } + throw err_arg; } - , { - show_queries_tab: { - group: "SPARQL", - class: "alpha_feature", - text: "Show Queries Tab", - label: { - title: "Expose the 'Queries' tab to be able to monitor and debug SPARQL queries" - }, - input: { - type: "checkbox" - } + }; + if (regarding_required) { + _ref = this.get_predicate_methods(); + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + meth = _ref[_i]; + iter = (function(_this) { + return function(node) { + var pred, retval, _j, _len1, _ref1; + _ref1 = _this.regarding; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + pred = _ref1[_j]; + retval = meth.call(_this.huviz, node, pred); + } + return _this.huviz.tick(); + }; + })(this); + if (nodes != null) { + async.each(nodes, iter, errorHandler); } } - //checked: "checked" - , { - max_outstanding_sparql_requests: { - group: "SPARQL", - class: "alpha_feature", - text: "Max. Outstanding Requests", - label: { - title: "Cap on the number of simultaneous SPARQL requests" - }, - input: { - value: 20, - min: 1, - max: 100, - step: 1, - type: "range" + } else if (this.verbs[0] === 'load') { + this.huviz.load_with(this.data_uri, this.with_ontologies); + console.log("load data_uri has returned"); + } else if (this.verbs[0] === 'query') { + this.huviz.query_from_seeking_limit(this.sparqlQuery); + } else { + _ref1 = this.get_methods(); + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + meth = _ref1[_j]; + if (meth.callback) { + callback = meth.callback; + } else if (meth.build_callback) { + callback = meth.build_callback(this, nodes); + } else { + callback = errorHandler; + } + atFirst = meth.atFirst; + if (atFirst != null) { + atFirst(); + } + iter = (function(_this) { + return function(node) { + var retval; + return retval = meth.call(_this.huviz, node); + }; + })(this); + if (nodes != null) { + if (USE_ASYNC = false) { + async.each(nodes, iter, callback); + } else { + for (_k = 0, _len2 = nodes.length; _k < _len2; _k++) { + node = nodes[_k]; + iter(node); + } + this.huviz.gclui.set; + callback(); } } } - , { - sparql_timeout: { - group: "SPARQL", - class: "alpha_feature", - text: "Query timeout", - label: { - title: "Number of seconds to run SPARQL queries before giving up." - }, - input: { - value: 45, - min: 1, - max: 90, - step: 1, - type: "range" - } + } + this.huviz.clean_up_all_dirt_once(); + this.huviz.hide_state_msg(); + this.huviz.force.start(); + this.huviz.tick("Tick in graphcommandlanguage"); + }; + + GraphCommand.prototype.get_pretty_verbs = function() { + var l, verb_id, _i, _len, _ref; + l = []; + _ref = this.verbs; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + verb_id = _ref[_i]; + l.push(this.huviz.gclui.verb_pretty_name[verb_id]); + } + return l; + }; + + GraphCommand.prototype.missing = '____'; + + GraphCommand.prototype.update_str = function() { + var aSet, cmd_str, like_str, maybe_every, missing, more, obj_phrase, ready, regarding_phrase, regarding_required, set, setLabel, setLabels, subj, verb, _i, _j, _len, _len1, _ref, _ref1; + missing = this.missing; + cmd_str = ""; + ready = true; + regarding_required = false; + this.verb_phrase = ''; + this.noun_phrase = ''; + this.noun_phrase_ready = false; + if (this.verbs && this.verbs.length) { + cmd_str = angliciser(this.get_pretty_verbs()); + this.verb_phrase_ready = true; + this.verb_phrase = cmd_str; + } else { + ready = false; + cmd_str = missing; + this.verb_phrase_ready = false; + this.verb_phrase = this.huviz.human_term.blank_verb; + } + this.verb_phrase += ' '; + cmd_str += " "; + obj_phrase = ""; + if (cmd_str === 'load ') { + this.str += this.data_uri + " ."; + return; + } + if (this.object_phrase == null) { + this.object_phrase = null; + } + if (this.sets != null) { + setLabels = []; + _ref = this.sets; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + set = _ref[_i]; + if (typeof set === 'string') { + aSet = this.huviz.get_set_by_id(set); + } else { + aSet = set; } + setLabel = aSet.get_label(); + setLabels.push(setLabel); } - , { - sparql_query_default_limit: { - group: "SPARQL", - class: "alpha_feature", - text: "Default Node Limit", - label: { - title: "Default value for the 'Node Limit'" - }, - input: { - value: 200, - min: 1, - max: 1000, - step: 10, - type: "range" + more = angliciser(setLabels); + more = ("the " + more + " set") + ((this.sets.length > 1) && 's' || ''); + this.object_phrase = more; + this.noun_phrase_ready = true; + obj_phrase = this.object_phrase; + this.noun_phrase = obj_phrase; + } else { + if (this.object_phrase) { + console.log("update_str() object_phrase: ", this.object_phrase); + obj_phrase = this.object_phrase; + } else if (this.classes) { + maybe_every = this.every_class && "every " || ""; + obj_phrase += maybe_every + angliciser(this.classes); + if (this.except_subjects) { + obj_phrase += ' except ' + angliciser((function() { + var _j, _len1, _ref1, _results; + _ref1 = this.subjects; + _results = []; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + subj = _ref1[_j]; + _results.push(subj.lid); + } + return _results; + }).call(this)); + } + } else if (this.subjects) { + obj_phrase = angliciser((function() { + var _j, _len1, _ref1, _results; + _ref1 = this.subjects; + _results = []; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + subj = _ref1[_j]; + _results.push(subj.lid || subj); } + return _results; + }).call(this)); + } + } + if (obj_phrase === "") { + obj_phrase = missing; + ready = false; + this.noun_phrase_ready = false; + this.noun_phrase = this.huviz.human_term.blank_noun; + } else if (obj_phrase.length > 0) { + this.noun_phrase_ready = true; + this.noun_phrase = obj_phrase; + } + cmd_str += obj_phrase; + like_str = (this.like || "").trim(); + if (this.verbs) { + _ref1 = this.verbs; + for (_j = 0, _len1 = _ref1.length; _j < _len1; _j++) { + verb = _ref1[_j]; + if (['draw', 'undraw'].indexOf(verb) > -1) { + regarding_required = true; } } - , { - debug_shelf_angles_and_flipping: { - group: "Debugging", - class: "alpha_feature", - text: "debug shelf angles and flipping", - label: { - title: "show angles and flags with labels" - }, - input: { - type: "checkbox" - } + } + if (regarding_required) { + regarding_phrase = missing; + if (this.regarding_required()) { + regarding_phrase = angliciser(this.regarding); + if (this.regarding_every) { + regarding_phrase = "every " + regarding_phrase; } - } //checked: "checked" - , { - show_performance_monitor: { - group: "Debugging", - class: "alpha_feature", - text: "Show Performance Monitor", - label: { - title: "Feedback on what HuViz is doing" - }, - input: { - type: "checkbox" - } + } else { + ready = false; + } + } + this.suffix_phrase = ''; + if (like_str) { + this.suffix_phrase += " matching '" + like_str + "'"; + } + if (regarding_phrase) { + this.suffix_phrase += " regarding " + regarding_phrase + ' .'; + } else if (this.polar_coords) { + this.suffix_phrase += " at " + (this.polar_coords.degrees.toFixed(0)) + " degrees"; + this.suffix_phrase += " and range " + (this.polar_coords.range.toFixed(2)) + " ."; + } else { + this.suffix_phrase += ' .'; + } + cmd_str += this.suffix_phrase; + this.ready = ready; + return this.str = cmd_str; + }; + + GraphCommand.prototype.toString = function() { + return this.str; + }; + + GraphCommand.prototype.parse_query_command = function(parts) { + var argName, argVal, keymap, spec; + keymap = { + query: 'serverUrl', + from: 'graphUrl', + limit: 'limit', + seeking: 'subjectUrl' + }; + spec = {}; + while (parts.length) { + argName = keymap[parts.shift()]; + argVal = unescape(parts.shift()); + if (argName != null) { + spec[argName] = argVal; + } else { + throw new Error("parse_query_command() failed at", parts.join(' ')); + } + } + return spec; + }; + + GraphCommand.prototype.parse = function(cmd_str) { + var cmd, parts, subj, verb; + parts = cmd_str.split(" "); + verb = parts[0]; + cmd = {}; + cmd.verbs = [verb]; + if (verb === 'load') { + cmd.data_uri = parts[1]; + if (parts.length > 3) { + cmd.with_ontologies = parts.slice(3); + } + } else if (verb === 'query') { + this.sparqlQuery = this.parse_query_command(parts); + } else { + subj = parts[1].replace(/\'/g, ""); + cmd.subjects = [ + { + 'id': subj } + ]; + } + return cmd; + }; + + GraphCommand.prototype.toString = function() { + return this.str; + }; + + GraphCommand.prototype.as_msg = function() { + return this.str; + }; + + return GraphCommand; + + })(); + + GraphCommandLanguageCtrl = (function() { + function GraphCommandLanguageCtrl(huviz) { + this.huviz = huviz; + this.execute = __bind(this.execute, this); + this.prefixes = {}; + } + + GraphCommandLanguageCtrl.prototype.run = function(script, callback) { + var retval; + this.huviz.before_running_command(this); + if (script == null) { + console.error("script must be defined"); + return; + } + if (script instanceof GraphCommand) { + this.commands = [script]; + } else if (typeof script === 'string') { + this.commands = script.split(';'); + } else if (script.constructor === [].constructor) { + this.commands = script; + } else { + this.commands = [script]; + } + retval = this.execute(callback); + this.huviz.after_running_command(this); + return retval; + }; + + GraphCommandLanguageCtrl.prototype.run_one = function(cmd_spec) { + var cmd; + if (cmd_spec instanceof GraphCommand) { + cmd = cmd_spec; + } else { + cmd = new GraphCommand(this.huviz, cmd_spec); + } + cmd.prefixes = this.prefixes; + return cmd.execute(); + }; + + GraphCommandLanguageCtrl.prototype.execute = function(callback) { + var cmd_spec, run_once, _i, _len, _ref; + if (this.commands.length > 0 && typeof this.commands[0] === 'string' && this.commands[0].match(/^load /)) { + this.run_one(this.commands.shift()); + run_once = (function(_this) { + return function() { + document.removeEventListener('dataset-loaded', run_once); + return _this.execute(); + }; + })(this); + document.addEventListener('dataset-loaded', run_once); + return; + } + _ref = this.commands; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + cmd_spec = _ref[_i]; + if (cmd_spec) { + this.run_one(cmd_spec); } - //checked: "checked" - , { - slow_it_down: { - group: "Debugging", - class: "alpha_feature", - text: "Slow it down (sec)", - label: { - title: "execute commands with wait states to simulate long operations" - }, - input: { - value: 0, - min: 0, - max: 10, - step: 0.1, - type: "range" - } + } + if (callback != null) { + callback(); + } + }; + + return GraphCommandLanguageCtrl; + + })(); + + (typeof exports !== "undefined" && exports !== null ? exports : this).GraphCommandLanguageCtrl = GraphCommandLanguageCtrl; + + (typeof exports !== "undefined" && exports !== null ? exports : this).GraphCommand = GraphCommand; + + (typeof exports !== "undefined" && exports !== null ? exports : this).GCLTest = GCLTest; + + (typeof exports !== "undefined" && exports !== null ? exports : this).GCLTestSuite = GCLTestSuite; + +}).call(this); +}, "greenerturtle": function(exports, require, module) {(function() { + var GreenerTurtle; + + GreenerTurtle = (function() { + var RDF_object, build_indices, count_subjects, get_incoming_predicates, obj_has_type, verbosity; + + function GreenerTurtle() {} + + verbosity = false; + + obj_has_type = function(obj, typ) { + return obj.type === typ; + }; + + RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; + + build_indices = function(graph) { + var obj, oi, p, predicate, subj, subj_id, _results; + _results = []; + for (subj_id in graph.subjects) { + subj = graph.subjects[subj_id]; + _results.push((function() { + var _results1; + _results1 = []; + for (p in subj.predicates) { + predicate = subj.predicates[p]; + oi = 0; + _results1.push((function() { + var _results2; + _results2 = []; + while (oi < predicate.objects.length) { + obj = predicate.objects[oi]; + if (obj && obj_has_type(obj, RDF_object)) { + if (typeof graph.oid_2_id_p[obj.value] === "undefined") { + graph.oid_2_id_p[obj.value] = []; + } + if (obj.value === "_:E" && verbosity) { + console.log(obj.value, "----> [", subj.id, p, "]"); + } + graph.oid_2_id_p[obj.value].push([subj.id, p]); + } + _results2.push(oi++); + } + return _results2; + })()); + } + return _results1; + })()); + } + return _results; + }; + + get_incoming_predicates = function(subj) { + var resp; + resp = this.oid_2_id_p[subj.id] || []; + return resp; + }; + + count_subjects = function(graph) { + var s, _results; + graph.num_subj = 0; + _results = []; + for (s in graph.subjects) { + _results.push(graph.num_subj++); + } + return _results; + }; + + GreenerTurtle.prototype.parse = function(data, type) { + var G; + G = GreenTurtle.implementation.parse(data, type); + if (!G.oid_2_id_p) { + G.oid_2_id_p = {}; + } + build_indices(G); + count_subjects(G); + G.get_incoming_predicates = get_incoming_predicates; + return G; + }; + + return GreenerTurtle; + + })(); + + exports.GreenerTurtle = GreenerTurtle; + +}).call(this); +}, "huviz": function(exports, require, module) {(function() { + var BASE10, BASE57, CommandController, DCE_title, DC_subject, DragAndDropLoader, DragAndDropLoaderOfScripts, Edge, EditController, FOAF_Group, FOAF_Person, FOAF_name, GeoUserNameWidget, GraphCommandLanguageCtrl, GreenerTurtle, Huviz, IndexedDBService, IndexedDBStorageController, MANY_SPACES_REGEX, NAME_SYNS, Node, OA_, OA_terms_regex, OSMT_name, OSMT_reg_name, OWL_Class, OWL_ObjectProperty, OWL_Thing, OntoViz, OntologicallyGrounded, Orlando, PEEKING_COLOR, PRIMORDIAL_ONTOLOGY, PickOrProvide, PickOrProvideScript, Predicate, RDFS_label, RDF_Class, RDF_a, RDF_literal, RDF_object, RDF_subClassOf, RDF_type, SCHEMA_name, SKOS_prefLabel, SettingsWidget, Socrata, THUMB_PREDS, TYPE_SYNS, Taxon, TextCursor, UNDEFINED, UsernameWidget, XL_literalForm, XML_TAG_REGEX, angliciser, colorlog, convert, default_node_radius_policy, dist_lt, distance, escapeHtml, gcl, getPrefixedTypeSignature, getTypeSignature, has_predicate_value, has_type, hash, hpad, id_escape, ident, ids_to_show, int_to_base, is_a_main_node, is_node_to_always_show, is_one_of, linearize, node_radius_policies, noop, orlando_human_term, sel_to_id, start_with_http, strip_surrounding_quotes, synthIdFor, tau, themeStyles, typeSigRE, unescape_unicode, unique_id, uniquer, unpad_md, wpad, + __hasProp = {}.hasOwnProperty, + __extends = function(child, parent) { for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; } function ctor() { this.constructor = child; } ctor.prototype = parent.prototype; child.prototype = new ctor(); child.__super__ = parent.prototype; return child; }, + __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, + __indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; }; + + angliciser = require('angliciser').angliciser; + + uniquer = require("uniquer").uniquer; + + gcl = require('graphcommandlanguage'); + + CommandController = require('gclui').CommandController; + + EditController = require('editui').EditController; + + IndexedDBService = require('indexeddbservice').IndexedDBService; + + IndexedDBStorageController = require('indexeddbstoragecontroller').IndexedDBStorageController; + + Edge = require('edge').Edge; + + GraphCommandLanguageCtrl = require('graphcommandlanguage').GraphCommandLanguageCtrl; + + GreenerTurtle = require('greenerturtle').GreenerTurtle; + + Node = require('node').Node; + + Predicate = require('predicate').Predicate; + + Taxon = require('taxon').Taxon; + + TextCursor = require('textcursor').TextCursor; + + MultiString.set_langpath('en:fr'); + + colorlog = function(msg, color, size) { + if (color == null) { + color = "red"; + } + if (size == null) { + size = "1.2em"; + } + return console.log("%c" + msg, "color:" + color + ";font-size:" + size + ";"); + }; + + unpad_md = function(txt, pad) { + var in_lines, line, out, out_lines, _i, _len; + pad = " "; + out_lines = []; + in_lines = txt.split("\n"); + for (_i = 0, _len = in_lines.length; _i < _len; _i++) { + line = in_lines[_i]; + if (!(line.startsWith(pad) || line.length === 0)) { + return txt; + } + out_lines.push(line.replace(/^ /, '')); + } + out = out_lines.join("\n"); + return out; + }; + + strip_surrounding_quotes = function(s) { + return s.replace(/\"$/, '').replace(/^\"/, ''); + }; + + wpad = void 0; + + hpad = 10; + + tau = Math.PI * 2; + + distance = function(p1, p2) { + var x, y; + p2 = p2 || [0, 0]; + x = (p1.x || p1[0]) - (p2.x || p2[0]); + y = (p1.y || p1[1]) - (p2.y || p2[1]); + return Math.sqrt(x * x + y * y); + }; + + dist_lt = function(mouse, d, thresh) { + var x, y; + x = mouse[0] - d.x; + y = mouse[1] - d.y; + return Math.sqrt(x * x + y * y) < thresh; + }; + + hash = function(str) { + var hsh, i; + hsh = 5381; + i = str.length; + while (i) { + hsh = (hsh * 33) ^ str.charCodeAt(--i); + } + return hsh >>> 0; + }; + + convert = function(src, srctable, desttable) { + var destlen, i, numlen, q, r, res, srclen, val; + srclen = srctable.length; + destlen = desttable.length; + val = 0; + numlen = src.length; + i = 0; + while (i < numlen) { + val = val * srclen + srctable.indexOf(src.charAt(i)); + i++; + } + if (val < 0) { + return 0; + } + r = val % destlen; + res = desttable.charAt(r); + q = Math.floor(val / destlen); + while (q) { + r = q % destlen; + q = Math.floor(q / destlen); + res = desttable.charAt(r) + res; + } + return res; + }; + + BASE57 = "23456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"; + + BASE10 = "0123456789"; + + int_to_base = function(intgr) { + return convert("" + intgr, BASE10, BASE57); + }; + + synthIdFor = function(str) { + return 'h' + int_to_base(hash(str)).substr(0, 6); + }; + + window.synthIdFor = synthIdFor; + + unescape_unicode = function(u) { + return JSON.parse('"' + u.replace('"', '\\"') + '"'); + }; + + linearize = function(msgRecipient, streamoid) { + var i, l, line, recurse; + if (streamoid.idx === 0) { + return msgRecipient.postMessage({ + event: 'finish' + }); + } else { + i = streamoid.idx + 1; + l = 0; + while (streamoid.data[i](!'\n')) { + l++; + i++; + } + line = streamoid.data.substr(streamoid.idx, l + 1).trim(); + msgRecipient.postMessage({ + event: 'line', + line: line + }); + streamoid.idx = i; + recurse = function() { + return linearize(msgRecipient, streamoid); + }; + return setTimeout(recurse, 0); + } + }; + + ident = function(data) { + return data; + }; + + unique_id = function(prefix) { + if (prefix == null) { + prefix = 'uid_'; + } + return prefix + Math.random().toString(36).substr(2, 10); + }; + + sel_to_id = function(selector) { + return selector.replace(/^\#/, ''); + }; + + window.log_click = function() { + return console.log("%cCLICK", "color:red;font-size:1.8em"); + }; + + DC_subject = "http://purl.org/dc/terms/subject"; + + DCE_title = "http://purl.org/dc/elements/1.1/title"; + + FOAF_Group = "http://xmlns.com/foaf/0.1/Group"; + + FOAF_Person = "http://xmlns.com/foaf/0.1/Person"; + + FOAF_name = "http://xmlns.com/foaf/0.1/name"; + + OA_ = "http://www.w3.org/ns/oa#"; + + OA_terms_regex = /^(Annotation|Choice|CssSelector|CssStyle|DataPositionSelector|Direction|FragmentSelector|HttpRequestState|Motivation|PreferContainedDescriptions|PreferContainedIRIs|RangeSelector|ResourceSelection|Selector|SpecificResource|State|Style|SvgSelector|TextPositionSelector|TextQuoteSelector|TextualBody|TimeState|XPathSelector|annotationService|assessing|bodyValue|bookmarking|cachedSource|canonical|classifying|commenting|describing|editing|end|exact|hasBody|hasEndSelector|hasPurpose|hasScope|hasSelector|hasSource|hasStartSelector|hasState|hasTarget|highlighting|identifying|linking|ltrDirection|moderating|motivatedBy|prefix|processingLanguage|questioning|refinedBy|renderedVia|replying|rtlDirection|sourceDate|sourceDateEnd|sourceDateStart|start|styleClass|styledBy|suffix|tagging|textDirection|via)$/; + + OSMT_name = "https://wiki.openstreetmap.org/wiki/Key:name"; + + OSMT_reg_name = "https://wiki.openstreetmap.org/wiki/Key:reg_name"; + + OWL_Class = "http://www.w3.org/2002/07/owl#Class"; + + OWL_Thing = "http://www.w3.org/2002/07/owl#Thing"; + + OWL_ObjectProperty = "http://www.w3.org/2002/07/owl#ObjectProperty"; + + RDF_literal = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; + + RDF_object = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; + + RDF_type = "http://www.w3.org/1999/02/22-rdf-syntax-ns#type"; + + RDF_Class = "http://www.w3.org/2000/01/rdf-schema#Class"; + + RDF_subClassOf = "http://www.w3.org/2000/01/rdf-schema#subClassOf"; + + RDF_a = 'a'; + + RDFS_label = "http://www.w3.org/2000/01/rdf-schema#label"; + + SCHEMA_name = "http://schema.org/name"; + + SKOS_prefLabel = "http://www.w3.org/2004/02/skos/core#prefLabel"; + + XL_literalForm = "http://www.w3.org/2008/05/skos-xl#literalForm"; + + TYPE_SYNS = [RDF_type, RDF_a, 'rdfs:type', 'rdf:type']; + + THUMB_PREDS = ['http://dbpedia.org/ontology/thumbnail', 'http://xmlns.com/foaf/0.1/thumbnail']; + + NAME_SYNS = [FOAF_name, RDFS_label, 'rdfs:label', 'name', SKOS_prefLabel, XL_literalForm, SCHEMA_name, DCE_title, OSMT_reg_name, OSMT_name]; + + XML_TAG_REGEX = /(<([^>]+)>)/ig; + + typeSigRE = { + 'xsd': new RegExp("^http:\/\/www\.w3\.org\/2001\/XMLSchema\#(.*)$"), + 'rdf': new RegExp("^http:\/\/www\.w3\.org\/1999\/02\/22-rdf-syntax-ns#(.*)$") + }; + + getPrefixedTypeSignature = function(typeUri) { + var match, prefix, sig; + for (prefix in typeSigRE) { + sig = typeSigRE[prefix]; + match = typeUri.match(sig); + if (match) { + return "" + prefix + "__" + match[1]; + } + } + }; + + getTypeSignature = function(typeUri) { + var typeSig; + typeSig = getPrefixedTypeSignature(typeUri); + return typeSig; + }; + + PRIMORDIAL_ONTOLOGY = { + subClassOf: { + Literal: 'Thing', + "rdf__PlainLiteral": 'Literal', + "rdf__HTML": 'Literal', + "rdf__langString": 'Literal', + "rdf__type": 'Literal', + "rdf__XMLLiteral": 'Literal', + "xsd__anyURI": 'Literal', + "xsd__base64Binary": 'Literal', + "xsd__boolean": 'Literal', + "xsd__date": 'Literal', + "xsd__dateTimeStamp": 'date', + "xsd__decimal": 'Literal', + "xsd__integer": "xsd__decimal", + "xsd__long": "xsd__integer", + "xsd__int": "xsd__long", + "xsd__short": "xsd__int", + "xsd__byte": "xsd__short", + "xsd__nonNegativeInteger": "xsd__integer", + "xsd__positiveInteger": "xsd__nonNegativeInteger", + "xsd__unsignedLong": "xsd__nonNegativeInteger", + "xsd__unsignedInt": "xsd__unsignedLong", + "xsd__unsignedShort": "xsd__unsignedInt", + "xsd__unsignedByte": "xsd__unsignedShort", + "xsd__nonPositiveInteger": "xsd__integer", + "xsd__negativeInteger": "xsd__nonPositiveInteger", + "xsd__double": 'Literal', + "xsd__duration": 'Literal', + "xsd__float": 'Literal', + "xsd__gDay": 'Literal', + "xsd__gMonth": 'Literal', + "xsd__gMonthDay": 'Literal', + "xsd__gYear": 'Literal', + "xsd__gYearMonth": 'Literal', + "xsd__hexBinary": 'Literal', + "xsd__NOTATION": 'Literal', + "xsd__QName": 'Literal', + "xsd__string": 'Literal', + "xsd__normalizedString": "xsd_string", + "xsd__token": "xsd__normalizedString", + "xsd__language": "xsd__token", + "xsd__Name": "xsd__token", + "xsd__NCName": "xsd__Name", + "xsd__time": 'Literal' + }, + subPropertyOf: {}, + domain: {}, + range: {}, + label: {} + }; + + MANY_SPACES_REGEX = /\s{2,}/g; + + UNDEFINED = void 0; + + start_with_http = new RegExp("http", "ig"); + + ids_to_show = start_with_http; + + PEEKING_COLOR = "darkgray"; + + themeStyles = { + "light": { + "themeName": "theme_white", + "pageBg": "white", + "labelColor": "black", + "shelfColor": "lightgreen", + "discardColor": "salmon", + "nodeHighlightOutline": "black" + }, + "dark": { + "themeName": "theme_black", + "pageBg": "black", + "labelColor": "#ddd", + "shelfColor": "#163e00", + "discardColor": "#4b0000", + "nodeHighlightOutline": "white" + } + }; + + id_escape = function(an_id) { + var retval; + retval = an_id.replace(/\:/g, '_'); + retval = retval.replace(/\//g, '_'); + retval = retval.replace(new RegExp(' ', 'g'), '_'); + retval = retval.replace(new RegExp('\\?', 'g'), '_'); + retval = retval.replace(new RegExp('\=', 'g'), '_'); + retval = retval.replace(new RegExp('\\.', 'g'), '_'); + retval = retval.replace(new RegExp('\\#', 'g'), '_'); + return retval; + }; + + if (true) { + node_radius_policies = { + "node radius by links": function(d) { + d.radius = Math.max(this.node_radius, Math.log(d.links_shown.length)); + return d.radius; + if (d.showing_links === "none") { + d.radius = this.node_radius; + } else { + if (d.showing_links === "all") { + d.radius = Math.max(this.node_radius, 2 + Math.log(d.links_shown.length)); } } - , { - show_hunt_verb: { - group: "Debugging", - class: "alpha_feature", - text: "Show Hunt verb", - label: { - title: "Expose the 'Hunt' verb, for demonstration of SortedSet.binary_search()" - }, - input: { - type: "checkbox" - } + return d.radius; + }, + "equal dots": function(d) { + return this.node_radius; + } + }; + default_node_radius_policy = "equal dots"; + default_node_radius_policy = "node radius by links"; + has_type = function(subject, typ) { + return has_predicate_value(subject, RDF_type, typ); + }; + has_predicate_value = function(subject, predicate, value) { + var obj, objs, oi, pre; + pre = subject.predicates[predicate]; + if (pre) { + objs = pre.objects; + oi = 0; + while (oi <= objs.length) { + obj = objs[oi]; + if (obj.value === value) { + return true; } + oi++; } - //checked: "checked" - ]; - - // recognize that changing this will likely break old hybrid HuVizScripts - this.prototype.json_script_marker = "# JSON FOLLOWS"; + } + return false; + }; + is_a_main_node = function(d) { + return (BLANK_HACK && d.s.id[7] !== "/") || (!BLANK_HACK && d.s.id[0] !== "_"); + }; + is_node_to_always_show = is_a_main_node; + is_one_of = function(itm, array) { + return array.indexOf(itm) > -1; + }; + } + + if (!is_one_of(2, [3, 2, 4])) { + alert("is_one_of() fails"); + } + + window.blurt = function(str, type, noButton) { + throw new Error('global blurt() is defunct, use @blurt() on HuViz'); + }; + + escapeHtml = function(unsafe) { + return unsafe.replace(/&/g, "&").replace(//g, ">").replace(/"/g, """).replace(/'/g, "'"); + }; + + noop = function() {}; + + SettingsWidget = (function() { + function SettingsWidget(huviz, inputElem, state) { + this.huviz = huviz; + this.inputElem = inputElem; + this.id = unique_id('widget_'); + this.inputJQElem = $(this.inputElem); + } + + SettingsWidget.prototype.wrap = function(html) { + return $(this.inputElem).wrap(html); + }; + + return SettingsWidget; + + })(); + + UsernameWidget = (function(_super) { + __extends(UsernameWidget, _super); + + UsernameWidget.prototype.state_to_state_icon = { + bad: 'fa-times', + good: 'fa-check', + untried: 'fa-question', + trying: 'fa-spinner fa-pulse', + empty: 'fa-ellipsis-h', + looking: 'fa-map-marker-alt fa-spin' + }; + + UsernameWidget.prototype.state_to_color = { + bad: 'red', + good: 'green', + untried: 'orange', + trying: 'orange', + empty: 'grey', + looking: 'green' + }; + + function UsernameWidget() { + UsernameWidget.__super__.constructor.apply(this, arguments); + this.wrap("
"); + this.widgetJQElem = $('#' + this.id); + this.widgetJQElem.prepend(""); + this.stateIconJQElem = this.widgetJQElem.find('.stateIcon'); + this.userIconJQElem = this.widgetJQElem.find('.userIcon'); + this.set_state('empty'); } - how_heavy_are(n, label, cb) { - let retval; - const memories = []; + UsernameWidget.prototype.set_state = function(state) { + var color, stateIcon; + if (false && this.state && this.state === state) { + console.log("not bothering to change the state to", state, "cause it already is"); + return; + } + this.state = state; + console.log(state, this.inputJQElem.val()); + stateIcon = this.state_to_state_icon[state]; + this.stateIconJQElem.attr('class', "stateIcon fa " + stateIcon); + color = this.state_to_color[state]; + this.widgetJQElem.css('border-color', color); + this.widgetJQElem.css('color', color); + }; + + return UsernameWidget; + + })(SettingsWidget); + + GeoUserNameWidget = (function(_super) { + __extends(GeoUserNameWidget, _super); + + function GeoUserNameWidget() { + GeoUserNameWidget.__super__.constructor.apply(this, arguments); + this.stateIconJQElem.on('click', this.huviz.show_geonames_instructions); + this.userIconJQElem.on('click', this.huviz.show_geonames_instructions); + } + + return GeoUserNameWidget; + + })(UsernameWidget); + + orlando_human_term = { + all: 'All', + chosen: 'Activated', + unchosen: 'Deactivated', + selected: 'Selected', + shelved: 'Shelved', + discarded: 'Discarded', + hidden: 'Hidden', + graphed: 'Graphed', + fixed: 'Pinned', + labelled: 'Labelled', + choose: 'Activate', + unchoose: 'Deactivate', + wander: 'Wander', + walk: 'Walk', + walked: "Walked", + select: 'Select', + unselect: 'Unselect', + label: 'Label', + unlabel: 'Unlabel', + shelve: 'Shelve', + hide: 'Hide', + discard: 'Discard', + undiscard: 'Retrieve', + pin: 'Pin', + unpin: 'Unpin', + unpinned: 'Unpinned', + nameless: 'Nameless', + blank_verb: 'VERB', + blank_noun: 'SET/SELECTION', + hunt: 'Hunt', + load: 'Load', + draw: 'Draw', + undraw: 'Undraw', + connect: 'Connect', + spawn: 'Spawn', + specialize: 'Specialize', + annotate: 'Annotate', + seeking_object: 'Object node', + suppress: 'Suppress', + suppressed: 'Suppresssed' + }; + + Huviz = (function() { + var nodeOrderAngle, node_display_type, renderStyles; + + Huviz.prototype.hash = hash; + + Huviz.prototype.class_list = []; + + Huviz.prototype.HHH = {}; + + Huviz.prototype.edges_by_id = {}; + + Huviz.prototype.edge_count = 0; + + Huviz.prototype.snippet_db = {}; + + Huviz.prototype.class_index = {}; + + Huviz.prototype.hierarchy = {}; + + Huviz.prototype.default_color = "brown"; + + Huviz.prototype.DEFAULT_CONTEXT = 'http://universal.org/'; + + Huviz.prototype.turtle_parser = 'GreenerTurtle'; + + Huviz.prototype.use_canvas = true; + + Huviz.prototype.use_svg = false; + + Huviz.prototype.use_webgl = false; + + Huviz.prototype.nodes = void 0; + + Huviz.prototype.links_set = void 0; + + Huviz.prototype.node = void 0; + + Huviz.prototype.link = void 0; + + Huviz.prototype.lariat = void 0; + + Huviz.prototype.verbose = true; + + Huviz.prototype.verbosity = 0; + + Huviz.prototype.TEMP = 5; + + Huviz.prototype.COARSE = 10; + + Huviz.prototype.MODERATE = 20; + + Huviz.prototype.DEBUG = 40; + + Huviz.prototype.DUMP = false; + + Huviz.prototype.node_radius_policy = void 0; + + Huviz.prototype.draw_circle_around_focused = true; + + Huviz.prototype.draw_lariat_labels_rotated = true; + + Huviz.prototype.run_force_after_mouseup_msec = 2000; + + Huviz.prototype.nodes_pinnable = true; + + Huviz.prototype.BLANK_HACK = false; + + Huviz.prototype.width = void 0; + + Huviz.prototype.height = 0; + + Huviz.prototype.cx = 0; + + Huviz.prototype.cy = 0; + + Huviz.prototype.snippet_body_em = .7; + + Huviz.prototype.line_length_min = 4; + + Huviz.prototype.link_distance = 29; + + Huviz.prototype.fisheye_zoom = 4.0; + + Huviz.prototype.peeking_line_thicker = 4; + + Huviz.prototype.show_snippets_constantly = false; + + Huviz.prototype.charge = -193; + + Huviz.prototype.gravity = 0.025; + + Huviz.prototype.snippet_count_on_edge_labels = true; + + Huviz.prototype.label_show_range = null; + + Huviz.prototype.focus_threshold = 100; + + Huviz.prototype.discard_radius = 200; + + Huviz.prototype.fisheye_radius = 300; + + Huviz.prototype.focus_radius = null; + + Huviz.prototype.drag_dist_threshold = 5; + + Huviz.prototype.snippet_size = 300; + + Huviz.prototype.dragging = false; + + Huviz.prototype.last_status = void 0; + + Huviz.prototype.edge_x_offset = 5; + + Huviz.prototype.shadow_offset = 1; + + Huviz.prototype.shadow_color = 'DarkGray'; + + Huviz.prototype.my_graph = { + predicates: {}, + subjects: {}, + objects: {} + }; + + Huviz.prototype.G = {}; + + Huviz.prototype.local_file_data = ""; + + Huviz.prototype.search_regex = new RegExp("^$", "ig"); + + Huviz.prototype.node_radius = 3.2; + + Huviz.prototype.mousedown_point = false; + + Huviz.prototype.discard_center = [0, 0]; + + Huviz.prototype.lariat_center = [0, 0]; + + Huviz.prototype.last_mouse_pos = [0, 0]; + + renderStyles = themeStyles.light; + + Huviz.prototype.display_shelf_clockwise = true; + + nodeOrderAngle = 0.5; + + node_display_type = ''; + + Huviz.prototype.pfm_data = { + tick: { + total_count: 0, + prev_total_count: 0, + timed_count: [], + label: "Ticks/sec." + }, + add_quad: { + total_count: 0, + prev_total_count: 0, + timed_count: [], + label: "Add Quad/sec" + }, + hatch: { + total_count: 0, + prev_total_count: 0, + timed_count: [], + label: "Hatch/sec" + }, + taxonomy: { + total_count: 0, + label: "Number of Classes:" + }, + sparql: { + total_count: 0, + prev_total_count: 0, + timed_count: [], + label: "Sparql Queries/sec" + } + }; + + Huviz.prototype.p_total_sprql_requests = 0; + + Huviz.prototype.how_heavy_are = function(n, label, cb) { + var after, before, buncha, diff, k, m, memories, per, retval, _i; + memories = []; memories.push(window.performance.memory); - if (this.heavy_things == null) { this.heavy_things = {}; } - const buncha = []; + if (this.heavy_things == null) { + this.heavy_things = {}; + } + buncha = []; this.heavy_things[label] = buncha; - for (let m = 1, end = n, asc = 1 <= end; asc ? m <= end : m >= end; asc ? m++ : m--) { - retval = cb.call(this,n); - //console.log(retval) + for (m = _i = 1; 1 <= n ? _i <= n : _i >= n; m = 1 <= n ? ++_i : --_i) { + retval = cb.call(this, n); buncha.push(retval); } memories.push(window.performance.memory); memories.push({}); memories.push({}); - const [before,after,diff,per] = Array.from(memories); - for (let k in memories[0]) { + before = memories[0], after = memories[1], diff = memories[2], per = memories[3]; + for (k in memories[0]) { diff[k] = after[k] - before[k]; per[k] = diff[k] / n; } - per.what = 'B/'+label; + per.what = 'B/' + label; before.what = 'before'; after.what = 'after'; diff.what = 'diff'; - //console.log(per) colorlog(label + ' occupy ' + per.totalJSHeapSize + ' Bytes each'); console.log('eg', retval); - //console.table(memories) - } + }; - how_heavy(n) { - // Purpose: - // Find out how many Bytes each of the following objects occupy in RAM. - // Example: - // HVZ[0].how_heavy(100000) - this.how_heavy_are(n, 'Array', x => new Array(100)); - this.how_heavy_are(n, 'Object', x => (new Object())[x] = x); - this.how_heavy_are(n, 'String', x => ""+x); - this.how_heavy_are(n, 'Random', x => Math.random()); - return this.how_heavy_are(n, 'SortedSet', x => SortedSet().named(x)); - } + Huviz.prototype.how_heavy = function(n) { + this.how_heavy_are(n, 'Array', function(x) { + return new Array(100); + }); + this.how_heavy_are(n, 'Object', function(x) { + return (new Object())[x] = x; + }); + this.how_heavy_are(n, 'String', function(x) { + return "" + x; + }); + this.how_heavy_are(n, 'Random', function(x) { + return Math.random(); + }); + return this.how_heavy_are(n, 'SortedSet', function(x) { + return SortedSet().named(x); + }); + }; - compose_object_from_defaults_and_incoming(defs, incoming) { - // Purpose: - // To return an object with the properties of defs and incoming layered into it in turn - // Intended Use Case: - // It is frequently the case that one wants to have and object with contains - // the default arguments for something and that one also wants the ability to - // pass in another object which contains the specifics for the call. - // This method joins those things together properly (they can even be null) - // to return the amalgamation of the defaults and the incoming arguments. - if (defs == null) { defs = {}; } - if (incoming == null) { incoming = {}; } + Huviz.prototype.compose_object_from_defaults_and_incoming = function(defs, incoming) { + if (defs == null) { + defs = {}; + } + if (incoming == null) { + incoming = {}; + } return Object.assign(Object.assign({}, defs), incoming); - } + }; - gen_dialog_html(contents, id, in_args) { - const args = this.compose_object_from_defaults_and_incoming(this.default_dialog_args, in_args); - //args = Object.assign(default_args, in_args) - return `
-
-
${args.title}
- -
- ${contents} -
`; // """ for emacs coffeescript mode - } + Huviz.prototype.default_dialog_args = { + width: 200, + height: 200, + left: 100, + top: 100, + head_bg_color: '#157fcc', + classes: "contextMenu temp", + title: '' + }; + + Huviz.prototype.gen_dialog_html = function(contents, id, in_args) { + var args; + args = this.compose_object_from_defaults_and_incoming(this.default_dialog_args, in_args); + return "
\n
\n
" + args.title + "
\n \n
\n " + contents + "\n
"; + }; - make_dialog(content_html, id, args) { - if (id == null) { id = this.unique_id('dialog_'); } // if you do not have an id, an id will be provided for you + Huviz.prototype.make_dialog = function(content_html, id, args) { + var elem; + if (id == null) { + id = this.unique_id('dialog_'); + } this.addHTML(this.gen_dialog_html(content_html, id, args)); - const elem = document.querySelector('#'+id); - $(elem).on('drag',this.pop_div_to_top); + elem = document.querySelector('#' + id); + $(elem).on('drag', this.pop_div_to_top); $(elem).draggable().resizable(); $(elem.querySelector(' .close_node_details')).on('click', args.close || this.destroy_dialog); return elem; - } + }; - pop_div_to_top(elem) { + Huviz.prototype.pop_div_to_top = function(elem) { return $(elem.currentTarget).parent().append(elem.currentTarget); - } + }; - destroy_dialog(e) { - const box = e.currentTarget.offsetParent; + Huviz.prototype.destroy_dialog = function(e) { + var box; + box = e.currentTarget.offsetParent; return $(box).remove(); - } + }; - make_markdown_dialog(markdown, id, args) { - if (args == null) { args = {}; } + Huviz.prototype.make_markdown_dialog = function(markdown, id, args) { + if (args == null) { + args = {}; + } args.extraClasses += " markdownDialog"; return this.make_dialog(marked(markdown || ''), id, args); - } + }; - make_pre_dialog(textToPre, id, args) { - if (args == null) { args = {}; } + Huviz.prototype.make_pre_dialog = function(textToPre, id, args) { + if (args == null) { + args = {}; + } args.extraClasses += " preformattedDialog"; - return this.make_dialog(`
${textToPre}
`, id, args); - } + return this.make_dialog("
" + textToPre + "
", id, args); + }; - make_json_dialog(json, id, args) { - if (args == null) { args = {}; } + Huviz.prototype.make_json_dialog = function(json, id, args) { + var jsonString; + if (args == null) { + args = {}; + } args.extraClasses += " preformattedDialog"; - const jsonString = JSON.stringify(json, null, args.json_indent || 2); - return this.make_dialog(`
${jsonString}
`, id, args); - } + jsonString = JSON.stringify(json, null, args.json_indent || 2); + return this.make_dialog("
" + jsonString + "
", id, args); + }; - unique_id(prefix) { - if (prefix == null) { prefix = 'uid_'; } - return prefix + Math.random().toString(36).substr(2,10); - } + Huviz.prototype.unique_id = function(prefix) { + if (prefix == null) { + prefix = 'uid_'; + } + return prefix + Math.random().toString(36).substr(2, 10); + }; - change_sort_order(array, cmp) { + Huviz.prototype.change_sort_order = function(array, cmp) { array.__current_sort_order = cmp; return array.sort(array.__current_sort_order); - } - isArray(thing) { + }; + + Huviz.prototype.isArray = function(thing) { return Object.prototype.toString.call(thing) === "[object Array]"; - } - cmp_on_name(a, b) { - if (a.name === b.name) { return 0; } - if (a.name < b.name) { return -1; } + }; + + Huviz.prototype.cmp_on_name = function(a, b) { + if (a.name === b.name) { + return 0; + } + if (a.name < b.name) { + return -1; + } return 1; - } - cmp_on_id(a, b) { - if (a.id === b.id) { return 0; } - if (a.id < b.id) { return -1; } + }; + + Huviz.prototype.cmp_on_id = function(a, b) { + if (a.id === b.id) { + return 0; + } + if (a.id < b.id) { + return -1; + } return 1; - } - binary_search_on(sorted_array, sought, cmp, ret_ins_idx) { - // return -1 or the idx of sought in sorted_array - // if ret_ins_idx instead of -1 return [n] where n is where it ought to be - // AKA "RETurn the INSertion INdeX" + }; + + Huviz.prototype.binary_search_on = function(sorted_array, sought, cmp, ret_ins_idx) { + var bot, c, mid, seeking, top; cmp = cmp || sorted_array.__current_sort_order || this.cmp_on_id; ret_ins_idx = ret_ins_idx || false; - const seeking = true; + seeking = true; if (sorted_array.length < 1) { - if (ret_ins_idx) { return {idx: 0}; } + if (ret_ins_idx) { + return { + idx: 0 + }; + } return -1; } - let mid = undefined; - let bot = 0; - let top = sorted_array.length; + mid = void 0; + bot = 0; + top = sorted_array.length; while (seeking) { mid = bot + Math.floor((top - bot) / 2); - const c = cmp(sorted_array[mid], sought); - - //console.log(" c =",c); - if (c === 0) { return mid; } - if (c < 0) { // ie sorted_array[mid] < sought + c = cmp(sorted_array[mid], sought); + if (c === 0) { + return mid; + } + if (c < 0) { bot = mid + 1; } else { top = mid; } if (bot === top) { - if (ret_ins_idx) { return {idx: bot}; } + if (ret_ins_idx) { + return { + idx: bot + }; + } return -1; } } - } + }; - // Objective: - // Maintain a sorted array which acts like a set. - // It is sorted so insertions and tests can be fast. - // cmp: a comparison function returning -1,0,1 - // an integer was returned, ie it was found - - // Perform the set .add operation, adding itm only if not already present - - //if (Array.__proto__.add == null) Array.prototype.add = add; - // the nodes the user has chosen to see expanded - // the nodes the user has discarded - // the nodes which are in the graph, linked together - // the nodes not displaying links and not discarded - // keep synced with html - // bugged - roughSizeOfObject(object) { - // http://stackoverflow.com/questions/1248302/javascript-object-size - const objectList = []; - const stack = [object]; - let bytes = 0; + Huviz.prototype.roughSizeOfObject = function(object) { + var bytes, i, objectList, stack, value; + objectList = []; + stack = [object]; + bytes = 0; while (stack.length) { - const value = stack.pop(); + value = stack.pop(); if (typeof value === "boolean") { bytes += 4; } else if (typeof value === "string") { bytes += value.length * 2; } else if (typeof value === "number") { bytes += 8; - } else if ((typeof value === "object") && (objectList.indexOf(value) === -1)) { + } else if (typeof value === "object" && objectList.indexOf(value) === -1) { objectList.push(value); - for (let i in value) { + for (i in value) { stack.push(value[i]); } } } return bytes; - } + }; - move_node_to_point(node, point) { + Huviz.prototype.move_node_to_point = function(node, point) { node.x = point[0]; return node.y = point[1]; - } + }; - click_node(node_or_id) { - // motivated by testing. Should this also be used by normal click handling? - let node; + Huviz.prototype.click_node = function(node_or_id) { + var evt, node; console.warn("click_node() is deprecated"); if (typeof node_or_id === 'string') { node = this.nodes.get_by('id', node_or_id); @@ -7387,25 +6209,26 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` node = node_or_id; } this.set_focused_node(node); - const evt = new MouseEvent("mouseup", { + evt = new MouseEvent("mouseup", { screenX: node.x, screenY: node.y - } - ); + }); this.canvas.dispatchEvent(evt); return this; - } + }; - click_verb(id) { - const verbs = $(`#verb-${id}`); + Huviz.prototype.click_verb = function(id) { + var verbs; + verbs = $("#verb-" + id); if (!verbs.length) { - throw new Error(`verb '${id}' not found`); + throw new Error("verb '" + id + "' not found"); } verbs.trigger("click"); return this; - } + }; - click_set(id) { + Huviz.prototype.click_set = function(id) { + var sel, sets; if (id === 'nodes') { alert("set 'nodes' is deprecated"); console.error("set 'nodes' is deprecated"); @@ -7414,79 +6237,72 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` id = id + '_set'; } } - const sel = `#${id}`; - const sets = $(sel); + sel = "#" + id; + sets = $(sel); if (!sets.length) { - throw new Error(`set '${id}' not found using selector: '${sel}'`); + throw new Error("set '" + id + "' not found using selector: '" + sel + "'"); } sets.trigger("click"); return this; - } + }; - click_predicate(id) { + Huviz.prototype.click_predicate = function(id) { this.gclui.predicate_picker.handle_click(id); return this; - } + }; - click_taxon(id) { - $(`#${id}`).trigger("click"); + Huviz.prototype.click_taxon = function(id) { + $("#" + id).trigger("click"); return this; - } + }; - like_string(str) { - // Ideally we'd trigger an actual 'input' event but that is not possible - //$(".like_input").val(str) + Huviz.prototype.like_string = function(str) { this.gclui.like_input.val(str); this.gclui.handle_like_input(); - //debugger if @DEBUG and str is "" return this; - } + }; - toggle_expander(id) { - this.topJQElem.find(`#${id} span.expander:first`).trigger("click"); + Huviz.prototype.toggle_expander = function(id) { + this.topJQElem.find("#" + id + " span.expander:first").trigger("click"); return this; - } + }; - doit() { + Huviz.prototype.doit = function() { this.topJQElem.find(".doit_button").trigger("click"); return this; - } + }; - make_cursor_text_while_dragging(action) { - let drag_or_drop; - if (['seeking_object'].includes(action)) { + Huviz.prototype.make_cursor_text_while_dragging = function(action) { + var drag_or_drop; + if (action === 'seeking_object') { drag_or_drop = 'drag'; } else { drag_or_drop = 'drop'; } - return `${this.human_term[drag_or_drop] || drag_or_drop} to ${this.human_term[action] || action}`; - } + return "" + (this.human_term[drag_or_drop] || drag_or_drop) + " to " + (this.human_term[action] || action); + }; - get_mouse_point(d3_event) { - if (d3_event == null) { d3_event = this.mouse_receiver[0][0]; } + Huviz.prototype.get_mouse_point = function(d3_event) { + if (d3_event == null) { + d3_event = this.mouse_receiver[0][0]; + } return d3.mouse(d3_event); - } + }; - should_start_dragging() { - // We can only know that the users intention is to drag - // a node once sufficient motion has started, when there - // is a focused_node - //console.log "state_name == '" + @focused_node.state.state_name + "' and selected? == " + @focused_node.selected? - //console.log "START_DRAG: \n dragging",@dragging,"\n mousedown_point:",@mousedown_point,"\n @focused_node:",@focused_node - return !this.dragging && - this.mousedown_point && - this.focused_node && - (distance(this.last_mouse_pos, this.mousedown_point) > this.drag_dist_threshold); - } + Huviz.prototype.should_start_dragging = function() { + return !this.dragging && this.mousedown_point && this.focused_node && distance(this.last_mouse_pos, this.mousedown_point) > this.drag_dist_threshold; + }; - mousemove() { + Huviz.prototype.mousemove = function() { + var action, cursor_text, e, edge, edit_state, pair, _i, _len, _ref, _ref1, _ref2; this.last_mouse_pos = this.get_mouse_point(); if (this.should_start_dragging()) { this.dragging = this.focused_node; if (this.args.drag_start_handler) { try { this.args.drag_start_handler.call(this, this.dragging); - } catch (e) { + } catch (_error) { + e = _error; console.warn(e); } } @@ -7499,54 +6315,50 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` this.graphed_set.acquire(this.dragging); } } - if (this.dragging) { - this.force.resume(); // why? - if (!this.args.skip_log_tick) { - console.log("Tick in @force.resume() mousemove"); - } - this.move_node_to_point(this.dragging, this.last_mouse_pos); - if (this.editui.is_state('connecting')) { - this.text_cursor.pause("", "drop on object node"); + this.force.resume(); + if (!this.args.skip_log_tick) { + console.log("Tick in @force.resume() mousemove"); + } + this.move_node_to_point(this.dragging, this.last_mouse_pos); + if (this.editui.is_state('connecting')) { + this.text_cursor.pause("", "drop on object node"); + } else { + if (this.dragging.links_shown.length === 0) { + action = "choose"; + } else if (this.dragging.fixed) { + action = "unpin"; } else { - let action, edit_state; - if (this.dragging.links_shown.length === 0) { - action = "choose"; - } else if (this.dragging.fixed) { - action = "unpin"; - } else { - action = "pin"; - } - if ((edit_state = this.editui.get_state()) !== 'not_editing') { - action = edit_state; - } else if (this.in_disconnect_dropzone(this.dragging)) { - action = "shelve"; - } else if (this.in_discard_dropzone(this.dragging)) { - action = "discard"; - } - const cursor_text = this.make_cursor_text_while_dragging(action); - this.text_cursor.pause("", cursor_text); + action = "pin"; } + if ((edit_state = this.editui.get_state()) !== 'not_editing') { + action = edit_state; + } else if (this.in_disconnect_dropzone(this.dragging)) { + action = "shelve"; + } else if (this.in_discard_dropzone(this.dragging)) { + action = "discard"; + } + cursor_text = this.make_cursor_text_while_dragging(action); + this.text_cursor.pause("", cursor_text); + } } else { - // TODO put block "if not @dragging and @mousedown_point and @focused_node and distance" here - if (this.editui.is_state('connecting')) { - if (this.editui.object_node || !this.editui.subject_node) { - if (this.editui.object_datatype_is_literal) { - this.text_cursor.set_text("click subject node"); - } else { - this.text_cursor.set_text("drag subject node"); - } + if (this.editui.is_state('connecting')) { + if (this.editui.object_node || !this.editui.subject_node) { + if (this.editui.object_datatype_is_literal) { + this.text_cursor.set_text("click subject node"); + } else { + this.text_cursor.set_text("drag subject node"); } } } + } if (this.peeking_node != null) { - // console.log "PEEKING at node: " + @peeking_node.id - if ((this.focused_node != null) && (this.focused_node !== this.peeking_node)) { - const pair = [ this.peeking_node.id, this.focused_node.id ]; - //console.log " PEEKING at edge between" + @peeking_node.id + " and " + @focused_node.id - for (let edge of Array.from(this.peeking_node.links_shown)) { - if (Array.from(pair).includes(edge.source.id) && Array.from(pair).includes(edge.target.id)) { - //console.log "PEEK edge.id is '" + edge.id + "'" + if ((this.focused_node != null) && this.focused_node !== this.peeking_node) { + pair = [this.peeking_node.id, this.focused_node.id]; + _ref = this.peeking_node.links_shown; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + edge = _ref[_i]; + if ((_ref1 = edge.source.id, __indexOf.call(pair, _ref1) >= 0) && (_ref2 = edge.target.id, __indexOf.call(pair, _ref2) >= 0)) { edge.focused = true; this.print_edge(edge); } else { @@ -7556,56 +6368,52 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` } } return this.tick("Tick in mousemove"); - } + }; - mousedown() { + Huviz.prototype.mousedown = function() { this.mousedown_point = this.get_mouse_point(); return this.last_mouse_pos = this.mousedown_point; - } + }; - mouseup() { + Huviz.prototype.mouseup = function() { + var d3_event, drag_dist, point; window.log_click(); - const d3_event = this.mouse_receiver[0][0]; + d3_event = this.mouse_receiver[0][0]; this.mousedown_point = false; - const point = this.get_mouse_point(d3_event); - if (d3.event.button === 2) { // Right click event so don't alter selected state - if (this.focused_node) { $(`#${this.focused_node.lid}`).removeClass("temp"); } + point = this.get_mouse_point(d3_event); + if (d3.event.button === 2) { + if (this.focused_node) { + $("#" + this.focused_node.lid).removeClass("temp"); + } return; } - // if something was being dragged then handle the drop if (this.dragging) { - //@log_mouse_activity('FINISH A DRAG') this.move_node_to_point(this.dragging, point); if (this.in_discard_dropzone(this.dragging)) { this.run_verb_on_object('discard', this.dragging); - } else if (this.in_disconnect_dropzone(this.dragging)) { // TODO rename to shelve_dropzone + } else if (this.in_disconnect_dropzone(this.dragging)) { this.run_verb_on_object('shelve', this.dragging); - // @unselect(@dragging) # this might be confusing } else if (this.dragging.links_shown.length === 0) { this.run_verb_on_object('choose', this.dragging); } else if (this.nodes_pinnable) { if (this.editui.is_state('connecting') && (this.dragging === this.editui.subject_node)) { console.log("not pinning subject_node when dropping"); - } else if (this.dragging.fixed) { // aka pinned + } else if (this.dragging.fixed) { this.run_verb_on_object('unpin', this.dragging); } else { this.run_verb_on_object('pin', this.dragging); } } this.dragging = false; - this.text_cursor.continue(); + this.text_cursor["continue"](); return; } - if (this.editui.is_state('connecting') && this.focused_node && this.editui.object_datatype_is_literal) { this.editui.set_subject_node(this.focused_node); - //console.log("edit mode and focused note and editui is literal") this.tick("Tick in mouseup 1"); return; } - - // this is the node being clickedRDF_literal - if (this.focused_node) { // and @focused_node.state is @graphed_set + if (this.focused_node) { if (window.location.hostname === 'localhost') { console.log(this.focused_node); } @@ -7613,20 +6421,11 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` this.tick("Tick in mouseup 2"); return; } - if (this.focused_edge) { - // FIXME do the edge equivalent of @perform_current_command - //@update_snippet() # useful when hover-shows-snippet this.print_edge(this.focused_edge); return; } - - // it was a drag, not a click - const drag_dist = distance(point, this.mousedown_point); - //if drag_dist > @drag_dist_threshold - // console.log "drag detection probably bugged",point,@mousedown_point,drag_dist - // return - + drag_dist = distance(point, this.mousedown_point); if (this.focused_node) { if (this.focused_node.state !== this.graphed_set) { this.run_verb_on_object('choose', this.focused_node); @@ -7635,54 +6434,53 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` } else { this.run_verb_on_object('choose', this.focused_node); } - // TODO(smurp) are these still needed? this.force.links(this.links_set); if (!this.args.skip_log_tick) { console.log("Tick in @force.links() mouseup"); } this.restart(); } + }; - } - - log_mouse_activity(label) { - return console.log(label,"\n dragging", this.dragging, - "\n mousedown_point:",this.mousedown_point, - "\n @focused_node:", this.focused_node); - } + Huviz.prototype.log_mouse_activity = function(label) { + return console.log(label, "\n dragging", this.dragging, "\n mousedown_point:", this.mousedown_point, "\n @focused_node:", this.focused_node); + }; - mouseright() { + Huviz.prototype.mouseright = function() { + var doesnt_exist; d3.event.preventDefault(); - const doesnt_exist = this.focused_node ? true : false; + doesnt_exist = this.focused_node ? true : false; if (this.focused_node && doesnt_exist) { return this.render_node_info_box(this.focused_node); } - } + }; - render_node_info_box(info_node) { - let color, width; - const node_inspector_id = "NODE_INSPECTOR__" + info_node.lid; + Huviz.prototype.render_node_info_box = function(info_node) { + var all_names, color, color_headers, dialogArgs, id_display, link_from, name, names_all_langs, node_info_html, node_inspector_id, node_out_links, node_type, note, other_types, target, target_prefix, width, _i, _j, _k, _l, _len, _len1, _len2, _len3, _ref, _ref1, _ref2, _ref3; + node_inspector_id = "NODE_INSPECTOR__" + info_node.lid; if (info_node._inspector != null) { this.hilight_dialog(info_node._inspector); return; } console.log("inspect node:", info_node); - const all_names = Object.values(info_node.name); - let names_all_langs = ""; - let note = ""; - let color_headers = ""; - let node_out_links = ""; - - for (let name of Array.from(all_names)) { + all_names = Object.values(info_node.name); + names_all_langs = ""; + note = ""; + color_headers = ""; + node_out_links = ""; + for (_i = 0, _len = all_names.length; _i < _len; _i++) { + name = all_names[_i]; if (names_all_langs) { names_all_langs = names_all_langs + " -- " + name; } else { names_all_langs = name; } } - let other_types = ""; + other_types = ""; if (info_node._types.length > 1) { - for (let node_type of Array.from(info_node._types)) { + _ref = info_node._types; + for (_j = 0, _len1 = _ref.length; _j < _len1; _j++) { + node_type = _ref[_j]; if (node_type !== info_node.type) { if (other_types) { other_types = other_types + ", " + node_type; @@ -7693,132 +6491,107 @@ Summarize them as a hasAnnotation edge and enable the Annotation Inspector.` } other_types = " (" + other_types + ")"; } - //console.log info_node - //console.log info_node.links_from.length if (info_node.links_from.length > 0) { - for (let link_from of Array.from(info_node.links_from)) { - const [target_prefix, target] = Array.from(this.render_target_for_display(link_from.target)); - node_out_links = node_out_links + `\ -
  • - ${link_from.predicate.lid} - ${target_prefix} ${target} -
  • \ -`; - } // """ + _ref1 = info_node.links_from; + for (_k = 0, _len2 = _ref1.length; _k < _len2; _k++) { + link_from = _ref1[_k]; + _ref2 = this.render_target_for_display(link_from.target), target_prefix = _ref2[0], target = _ref2[1]; + node_out_links = node_out_links + ("
  • \n " + link_from.predicate.lid + "\n " + target_prefix + " " + target + "\n
  • "); + } node_out_links = "
      " + node_out_links + "
    "; } - //console.log info_node if (info_node._colors) { width = 100 / info_node._colors.length; - for (color of Array.from(info_node._colors)) { - color_headers = color_headers + - `
    `; + _ref3 = info_node._colors; + for (_l = 0, _len3 = _ref3.length; _l < _len3; _l++) { + color = _ref3[_l]; + color_headers = color_headers + ("
    "); } } if (this.endpoint_loader.value) { if (this.endpoint_loader.value && info_node.fully_loaded) { note = "

    Node Fully Loaded"; } else { - note = `

    Note: -This node may not yet be fully loaded from remote server. -Link details may not be accurate. Activate to load.`; // """ + note = "

    Note:\nThis node may not yet be fully loaded from remote server.\nLink details may not be accurate. Activate to load."; } } - - const dialogArgs = { + dialogArgs = { width: this.width * 0.50, height: this.height * 0.80, top: d3.event.clientY, left: d3.event.clientX, close: this.close_node_inspector }; - if (info_node) { dialogArgs.head_bg_color = info_node.color; - const id_display = this.create_link_if_url(info_node.id); - const node_info_html = `\ -

    -

    id: ${id_display}

    -

    name: ${names_all_langs}

    -

    type(s): ${info_node.type} ${other_types}

    -

    Links To: ${info_node.links_to.length}
    - Links From: ${info_node.links_from.length}

    - ${note} - ${node_out_links} -
    \ -`; // """ - + id_display = this.create_link_if_url(info_node.id); + node_info_html = "
    \n

    id: " + id_display + "

    \n

    name: " + names_all_langs + "

    \n

    type(s): " + info_node.type + " " + other_types + "

    \n

    Links To: " + info_node.links_to.length + "
    \n Links From: " + info_node.links_from.length + "

    \n " + note + "\n " + node_out_links + "\n
    "; info_node._inspector = this.make_dialog(node_info_html, node_inspector_id, dialogArgs); info_node._inspector.dataset.node_id = info_node.id; } - } + }; - close_node_inspector(event, ui) { // fat because it is called by click handler - const box = event.currentTarget.offsetParent; - const { - node_id - } = box.dataset; + Huviz.prototype.close_node_inspector = function(event, ui) { + var box, node, node_id; + box = event.currentTarget.offsetParent; + node_id = box.dataset.node_id; if (node_id != null) { - const node = this.all_set.get_by('id', node_id); + node = this.all_set.get_by('id', node_id); if (node != null) { delete node._inspector; } } this.destroy_dialog(event); - } + }; - create_link_if_url(possible_link) { - let target; - const url_check = possible_link.substring(0,4); + Huviz.prototype.create_link_if_url = function(possible_link) { + var target, url_check; + url_check = possible_link.substring(0, 4); if (url_check === "http") { - return target = `${possible_link}`; + return target = "" + possible_link + ""; } else { return target = possible_link; } - } + }; - render_target_for_display(node) { + Huviz.prototype.render_target_for_display = function(node) { + var arrow, colon, lines, showBlock, typeCURIE; if (node.isLiteral) { - const typeCURIE = node.type.replace('__',':'); - const lines = node.name.toString().split(/\r\n|\r|\n/); - const showBlock = (lines.length > 1) || (node.name.toString().length > 30); - const colon = ":"; + typeCURIE = node.type.replace('__', ':'); + lines = node.name.toString().split(/\r\n|\r|\n/); + showBlock = lines.length > 1 || node.name.toString().length > 30; + colon = ":"; if (showBlock) { - return [colon, `
    ${node.name}
    `]; + return [colon, "
    " + node.name + "
    "]; } else { - return [colon, `${node.name}`]; + return [colon, "" + node.name + ""]; } } else { - const arrow = ""; + arrow = ""; return [arrow, this.create_link_if_url(node.id)]; } - } + }; - perform_current_command(node) { + Huviz.prototype.perform_current_command = function(node) { + var cmd; if (this.gclui.ready_to_perform()) { - const cmd = new gcl.GraphCommand(this, { + cmd = new gcl.GraphCommand(this, { verbs: this.gclui.engaged_verbs, subjects: [node] }); this.run_command(cmd); } - //else - // @toggle_selected(node) return this.clean_up_all_dirt_once(); - } + }; - run_command(cmd, callback) { - //@show_state_msg(cmd.as_msg()) + Huviz.prototype.run_command = function(cmd, callback) { this.gclui.show_working_on(cmd); this.gclc.run(cmd, callback); this.gclui.show_working_off(); - //@hide_state_msg() - } + }; - ///////////////////////////////////////////////////////////////////////////// - // resize-svg-when-window-is-resized-in-d3-js - // http://stackoverflow.com/questions/16265123/ - updateWindow() { + Huviz.prototype.updateWindow = function() { + var instance_container; if (!this.container) { console.warn('updateWindow() skipped until @container'); return; @@ -7830,9 +6603,7 @@ Link details may not be accurate. Activate to load.`; // """ this.update_discard_zone(); this.update_lariat_zone(); if (this.svg) { - this.svg. - attr("width", this.width). - attr("height", this.height); + this.svg.attr("width", this.width).attr("height", this.height); } if (this.canvas) { this.canvas.width = this.width; @@ -7842,45 +6613,36 @@ Link details may not be accurate. Activate to load.`; // """ if (!this.args.skip_log_tick) { console.log("Tick in @force.size() updateWindow"); } - // FIXME all selectors must be localized so if there are two huviz - // instances on a page they do not interact - const instance_container = this.args.huviz_top_sel; - $(`${instance_container} .graph_title_set`).css("width", this.width); - if (this.tabsJQElem && (this.tabsJQElem.length > 0)) { + instance_container = this.args.huviz_top_sel; + $("" + instance_container + " .graph_title_set").css("width", this.width); + if (this.tabsJQElem && this.tabsJQElem.length > 0) { this.tabsJQElem.css("left", "auto"); } return this.restart(); - } + }; - ///////////////////////////////////////////////////////////////////////////// - // - // http://bl.ocks.org/mbostock/929623 - get_charge(d) { - const graphed = d.state === this.graphed_set; - let retval = (graphed && this.charge) || 0; // zero so shelf has no influence + Huviz.prototype.get_charge = function(d) { + var graphed, retval; + graphed = d.state === this.graphed_set; + retval = graphed && this.charge || 0; if (d.charge != null) { retval = d.charge; } - //if retval is 0 and graphed - // console.error "bad combo of retval and graphed?",retval,graphed,d.name return retval; - } + }; - get_gravity() { + Huviz.prototype.get_gravity = function() { return this.gravity; - } + }; - // lines: 5845 5848 5852 of d3.v3.js object to - // mouse_receiver.call(force.drag); - // when mouse_receiver == viscanvas - init_webgl() { + Huviz.prototype.init_webgl = function() { this.init(); return this.animate(); - } + }; - //dump_line(add_line(scene,cx,cy,width,height,'ray')) - draw_circle(cx, cy, radius, strclr, filclr, start_angle, end_angle, special_focus) { - const incl_cntr = (start_angle != null) || (end_angle != null); + Huviz.prototype.draw_circle = function(cx, cy, radius, strclr, filclr, start_angle, end_angle, special_focus) { + var incl_cntr; + incl_cntr = (start_angle != null) || (end_angle != null); start_angle = start_angle || 0; end_angle = end_angle || tau; if (strclr) { @@ -7890,9 +6652,6 @@ Link details may not be accurate. Activate to load.`; // """ this.ctx.fillStyle = filclr || "blue"; } this.ctx.beginPath(); - //if incl_cntr - //@ctx.moveTo(cx, cy) # so the arcs are wedges not chords - // do not incl_cntr when drawing a whole circle this.ctx.arc(cx, cy, radius, start_angle, end_angle, true); this.ctx.closePath(); if (strclr) { @@ -7901,29 +6660,28 @@ Link details may not be accurate. Activate to load.`; // """ if (filclr) { this.ctx.fill(); } - - if (special_focus) { // true if this is a wander or walk highlighted node + if (special_focus) { this.ctx.beginPath(); - radius = radius/2; - this.ctx.arc(cx, cy, radius, 0, Math.PI*2); + radius = radius / 2; + this.ctx.arc(cx, cy, radius, 0, Math.PI * 2); this.ctx.closePath(); this.ctx.fillStyle = "black"; return this.ctx.fill(); } - } + }; - draw_round_img(cx, cy, radius, strclr, filclr, special_focus, imageData, url) { - const incl_cntr = (start_angle != null) || (end_angle != null); - var start_angle = start_angle || 0; - var end_angle = end_angle || tau; + Huviz.prototype.draw_round_img = function(cx, cy, radius, strclr, filclr, special_focus, imageData, url) { + var end_angle, img, incl_cntr, start_angle, wh; + incl_cntr = (typeof start_angle !== "undefined" && start_angle !== null) || (typeof end_angle !== "undefined" && end_angle !== null); + start_angle = start_angle || 0; + end_angle = end_angle || tau; if (strclr) { this.ctx.strokeStyle = strclr || "blue"; } this.ctx.beginPath(); if (incl_cntr) { - this.ctx.moveTo(cx, cy); // so the arcs are wedges not chords + this.ctx.moveTo(cx, cy); } - // do not incl_cntr when drawing a whole circle this.ctx.arc(cx, cy, radius, start_angle, end_angle, true); this.ctx.closePath(); if (strclr) { @@ -7932,31 +6690,25 @@ Link details may not be accurate. Activate to load.`; // """ if (filclr) { this.ctx.fill(); } - const wh = radius*2; + wh = radius * 2; if (imageData != null) { - // note that drawImage can clip for the centering task - // https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/drawImage - this.ctx.drawImage(imageData, cx-radius, cy-radius, wh, wh); + this.ctx.drawImage(imageData, cx - radius, cy - radius, wh, wh); } else { - const img = new Image(); + img = new Image(); img.src = url; - this.ctx.drawImage(img, - 0, 0, img.width, img.height, - cx-radius, cy-radius, wh, wh); + this.ctx.drawImage(img, 0, 0, img.width, img.height, cx - radius, cy - radius, wh, wh); } - - if (special_focus) { // true if this is a wander or walk highlighted node + if (special_focus) { this.ctx.beginPath(); - radius = radius/2; - this.ctx.arc(cx, cy, radius, 0, Math.PI*2); + radius = radius / 2; + this.ctx.arc(cx, cy, radius, 0, Math.PI * 2); this.ctx.closePath(); this.ctx.fillStyle = "black"; return this.ctx.fill(); } - } - + }; - draw_triangle(x, y, color, x1, y1, x2, y2) { + Huviz.prototype.draw_triangle = function(x, y, color, x1, y1, x2, y2) { this.ctx.beginPath(); this.ctx.moveTo(x, y); this.ctx.strokeStyle = color; @@ -7967,82 +6719,81 @@ Link details may not be accurate. Activate to load.`; // """ this.ctx.fillStyle = color; this.ctx.fill(); return this.ctx.closePath(); - } + }; - draw_pie(cx, cy, radius, strclr, filclrs, special_focus) { - const num = filclrs.length; + Huviz.prototype.draw_pie = function(cx, cy, radius, strclr, filclrs, special_focus) { + var arc, end_angle, filclr, num, start_angle, _i, _len, _results; + num = filclrs.length; if (!num) { throw new Error("no colors specified"); } if (num === 1) { - this.draw_circle(cx, cy, radius, strclr, filclrs[0],false,false,special_focus); + this.draw_circle(cx, cy, radius, strclr, filclrs[0], false, false, special_focus); return; } - const arc = tau/num; - let start_angle = 0; - return (() => { - const result = []; - for (let filclr of Array.from(filclrs)) { - const end_angle = start_angle + arc; - this.draw_circle(cx, cy, radius, strclr, filclr, end_angle, start_angle, special_focus); - result.push(start_angle = start_angle + arc); - } - return result; - })(); - } + arc = tau / num; + start_angle = 0; + _results = []; + for (_i = 0, _len = filclrs.length; _i < _len; _i++) { + filclr = filclrs[_i]; + end_angle = start_angle + arc; + this.draw_circle(cx, cy, radius, strclr, filclr, end_angle, start_angle, special_focus); + _results.push(start_angle = start_angle + arc); + } + return _results; + }; - draw_line(x1, y1, x2, y2, clr) { + Huviz.prototype.draw_line = function(x1, y1, x2, y2, clr) { this.ctx.strokeStyle = clr || 'red'; this.ctx.beginPath(); this.ctx.moveTo(x1, y1); this.ctx.lineTo(x2, y2); this.ctx.closePath(); return this.ctx.stroke(); - } + }; - draw_curvedline(x1, y1, x2, y2, sway_inc, clr, num_contexts, line_width, edge, directional_edge) { - let tip_x, tip_y; - const pdist = distance([x1,y1],[x2,y2]); - const sway = this.swayfrac * sway_inc * pdist; + Huviz.prototype.draw_curvedline = function(x1, y1, x2, y2, sway_inc, clr, num_contexts, line_width, edge, directional_edge) { + var a_l, a_w, ang, arr_side, arrow_base_x, arrow_base_y, arrow_color, arw_angl, check_range, ctrl_angle, flip, hd_angl, node_radius, orig_angle, pdist, pnt_x, pnt_y, sway, tip_x, tip_y, xctrl, xhndl, xmid, xo1, xo2, yctrl, yhndl, ymid, yo1, yo2; + pdist = distance([x1, y1], [x2, y2]); + sway = this.swayfrac * sway_inc * pdist; if (pdist < this.line_length_min) { return; } if (sway === 0) { return; } - // sway is the distance to offset the control point from the midline - const orig_angle = Math.atan2(x2 - x1, y2 - y1); - const ctrl_angle = (orig_angle + (Math.PI / 2)); - let ang = ctrl_angle; + orig_angle = Math.atan2(x2 - x1, y2 - y1); + ctrl_angle = orig_angle + (Math.PI / 2); + ang = ctrl_angle; ang = orig_angle; - const check_range = function(val,name) { + check_range = function(val, name) { + var range; window.maxes = window.maxes || {}; window.ranges = window.ranges || {}; - const range = window.ranges[name] || {max: -Infinity, min: Infinity}; + range = window.ranges[name] || { + max: -Infinity, + min: Infinity + }; range.max = Math.max(range.max, val); return range.min = Math.min(range.min, val); }; - //check_range(orig_angle,'orig_angle') - //check_range(ctrl_angle,'ctrl_angle') - const xmid = x1 + ((x2-x1)/2); - const ymid = y1 + ((y2-y1)/2); - const xctrl = xmid + (Math.sin(ctrl_angle) * sway); - const yctrl = ymid + (Math.cos(ctrl_angle) * sway); + xmid = x1 + (x2 - x1) / 2; + ymid = y1 + (y2 - y1) / 2; + xctrl = xmid + Math.sin(ctrl_angle) * sway; + yctrl = ymid + Math.cos(ctrl_angle) * sway; this.ctx.strokeStyle = clr || 'red'; this.ctx.beginPath(); this.ctx.lineWidth = line_width; this.ctx.moveTo(x1, y1); this.ctx.quadraticCurveTo(xctrl, yctrl, x2, y2); - //@ctx.closePath() this.ctx.stroke(); - - const xhndl = xmid + (Math.sin(ctrl_angle) * (sway/2)); - const yhndl = ymid + (Math.cos(ctrl_angle)* (sway/2)); + xhndl = xmid + Math.sin(ctrl_angle) * (sway / 2); + yhndl = ymid + Math.cos(ctrl_angle) * (sway / 2); edge.handle = { x: xhndl, y: yhndl }; - this.draw_circle(xhndl, yhndl, (line_width/2), clr); // draw a circle at the midpoint of the line + this.draw_circle(xhndl, yhndl, line_width / 2, clr); if (directional_edge === "forward") { tip_x = x2; tip_y = y2; @@ -8050,292 +6801,153 @@ Link details may not be accurate. Activate to load.`; // """ tip_x = x1; tip_y = y1; } - - // --------- ARROWS on Edges ----------- if (this.arrows_chosen) { - let flip; - const a_l = 8; // arrow length - const a_w = 2; // arrow width - const arr_side = Math.sqrt((a_l * a_l) + (a_w * a_w)); - - const arrow_color = clr; - const node_radius = this.calc_node_radius(edge.target); - - const arw_angl = Math.atan((yctrl - y2)/(xctrl - x2)); - const hd_angl = Math.tan(a_w/a_l); - if (xctrl < x2) { flip = -1; } else { flip = 1; } // Flip sign depending on angle - - const pnt_x = x2 + (flip * node_radius * Math.cos(arw_angl)); - const pnt_y = y2 + (flip * node_radius * Math.sin(arw_angl)); - const arrow_base_x = x2 + (flip * (node_radius + a_l) * Math.cos(arw_angl)); - const arrow_base_y = y2 + (flip * (node_radius + a_l) * Math.sin(arw_angl)); - const xo1 = pnt_x + (flip * arr_side * Math.cos(arw_angl + hd_angl)); - const yo1 = pnt_y + (flip * arr_side * Math.sin(arw_angl + hd_angl)); - const xo2 = pnt_x + (flip * arr_side * Math.cos(arw_angl - hd_angl)); - const yo2 = pnt_y + (flip * arr_side * Math.sin(arw_angl - hd_angl)); + a_l = 8; + a_w = 2; + arr_side = Math.sqrt(a_l * a_l + a_w * a_w); + arrow_color = clr; + node_radius = this.calc_node_radius(edge.target); + arw_angl = Math.atan((yctrl - y2) / (xctrl - x2)); + hd_angl = Math.tan(a_w / a_l); + if (xctrl < x2) { + flip = -1; + } else { + flip = 1; + } + pnt_x = x2 + flip * node_radius * Math.cos(arw_angl); + pnt_y = y2 + flip * node_radius * Math.sin(arw_angl); + arrow_base_x = x2 + flip * (node_radius + a_l) * Math.cos(arw_angl); + arrow_base_y = y2 + flip * (node_radius + a_l) * Math.sin(arw_angl); + xo1 = pnt_x + flip * arr_side * Math.cos(arw_angl + hd_angl); + yo1 = pnt_y + flip * arr_side * Math.sin(arw_angl + hd_angl); + xo2 = pnt_x + flip * arr_side * Math.cos(arw_angl - hd_angl); + yo2 = pnt_y + flip * arr_side * Math.sin(arw_angl - hd_angl); return this.draw_triangle(pnt_x, pnt_y, arrow_color, xo1, yo1, xo2, yo2); } - } + }; - draw_self_edge_circle(cx, cy, strclr, length, line_width, e, arw_angle) { - let node_radius = this.calc_node_radius(e.source); - const arw_radius = node_radius * 5; - //if (arw_radius > 75) then arw_radius = 75 - const x_offset = Math.cos(arw_angle) * arw_radius; - const y_offset = Math.sin(arw_angle) * arw_radius; - const cx2 = cx + x_offset; - const cy2 = cy + y_offset; + Huviz.prototype.draw_self_edge_circle = function(cx, cy, strclr, length, line_width, e, arw_angle) { + var a_l, a_w, arr_side, arrow_adjust, arrow_base_x, arrow_base_y, arrow_color, arw_angl, arw_radius, cx2, cy2, end_angle, filclr, flip, hd_angl, node_radius, pnt_x, pnt_y, special_focus, start_angle, x2, x_arrow_offset, x_offset, xo1, xo2, y2, y_arrow_offset, y_offset, yo1, yo2; + node_radius = this.calc_node_radius(e.source); + arw_radius = node_radius * 5; + x_offset = Math.cos(arw_angle) * arw_radius; + y_offset = Math.sin(arw_angle) * arw_radius; + cx2 = cx + x_offset; + cy2 = cy + y_offset; strclr = e.color; - const filclr = false; - const start_angle = 0; - const end_angle = 0; - const special_focus = false; + filclr = false; + start_angle = 0; + end_angle = 0; + special_focus = false; this.draw_circle(cx2, cy2, arw_radius, strclr, filclr, start_angle, end_angle, special_focus); - - const x_arrow_offset = Math.cos(arw_angle) * this.calc_node_radius(e.source); - const y_arrow_offset = Math.sin(arw_angle) * this.calc_node_radius(e.source); - - const a_l = 8; // arrow length - const a_w = 2; // arrow width - const arr_side = Math.sqrt((a_l * a_l) + (a_w * a_w)); - - const arrow_color = e.color; + x_arrow_offset = Math.cos(arw_angle) * this.calc_node_radius(e.source); + y_arrow_offset = Math.sin(arw_angle) * this.calc_node_radius(e.source); + a_l = 8; + a_w = 2; + arr_side = Math.sqrt(a_l * a_l + a_w * a_w); + arrow_color = e.color; node_radius = this.calc_node_radius(e.source); - - let arw_angl = arw_angle + 1; - const x2 = cx; - const y2 = cy; - - const hd_angl = Math.tan(a_w/a_l); // Adjusts the arrow shape - const flip = 1; - + arw_angl = arw_angle + 1; + x2 = cx; + y2 = cy; + hd_angl = Math.tan(a_w / a_l); + flip = 1; arw_angl = arw_angle + 1.45; - const arrow_adjust = Math.atan(a_l/arw_radius); - - const pnt_x = x2 + (flip * node_radius * Math.cos(arw_angl)); - const pnt_y = y2 + (flip * node_radius * Math.sin(arw_angl)); - - const arrow_base_x = x2 + (flip * (node_radius + a_l) * Math.cos(arw_angl)); - const arrow_base_y = y2 + (flip * (node_radius + a_l) * Math.sin(arw_angl)); - const xo1 = pnt_x + (flip * arr_side * Math.cos((arw_angl + hd_angl) - arrow_adjust)); - const yo1 = pnt_y + (flip * arr_side * Math.sin((arw_angl + hd_angl) - arrow_adjust)); - const xo2 = pnt_x + (flip * arr_side * Math.cos(arw_angl - hd_angl - arrow_adjust)); - const yo2 = pnt_y + (flip * arr_side * Math.sin(arw_angl - hd_angl - arrow_adjust)); + arrow_adjust = Math.atan(a_l / arw_radius); + pnt_x = x2 + flip * node_radius * Math.cos(arw_angl); + pnt_y = y2 + flip * node_radius * Math.sin(arw_angl); + arrow_base_x = x2 + flip * (node_radius + a_l) * Math.cos(arw_angl); + arrow_base_y = y2 + flip * (node_radius + a_l) * Math.sin(arw_angl); + xo1 = pnt_x + flip * arr_side * Math.cos(arw_angl + hd_angl - arrow_adjust); + yo1 = pnt_y + flip * arr_side * Math.sin(arw_angl + hd_angl - arrow_adjust); + xo2 = pnt_x + flip * arr_side * Math.cos(arw_angl - hd_angl - arrow_adjust); + yo2 = pnt_y + flip * arr_side * Math.sin(arw_angl - hd_angl - arrow_adjust); this.draw_triangle(pnt_x, pnt_y, arrow_color, xo1, yo1, xo2, yo2); e.handle = { x: cx2 + x_offset, y: cy2 + y_offset }; - return this.draw_circle(e.handle.x, e.handle.y, (line_width/2), arrow_color); - } + return this.draw_circle(e.handle.x, e.handle.y, line_width / 2, arrow_color); + }; - draw_disconnect_dropzone() { + Huviz.prototype.draw_disconnect_dropzone = function() { this.ctx.save(); this.ctx.lineWidth = this.graph_radius * 0.1; this.draw_circle(this.lariat_center[0], this.lariat_center[1], this.graph_radius, renderStyles.shelfColor); return this.ctx.restore(); - } - draw_discard_dropzone() { + }; + + Huviz.prototype.draw_discard_dropzone = function() { this.ctx.save(); this.ctx.lineWidth = this.discard_radius * 0.1; this.draw_circle(this.discard_center[0], this.discard_center[1], this.discard_radius, "", renderStyles.discardColor); return this.ctx.restore(); - } - draw_dropzones() { + }; + + Huviz.prototype.draw_dropzones = function() { if (this.dragging) { this.draw_disconnect_dropzone(); return this.draw_discard_dropzone(); } - } - in_disconnect_dropzone(node) { - // is it within the RIM of the disconnect circle? - const dist = distance(node, this.lariat_center); - return ((this.graph_radius * 0.9) < dist) && ((this.graph_radius * 1.1) > dist); - } - in_discard_dropzone(node) { - // is it ANYWHERE within the circle? - const dist = distance(node, this.discard_center); - return (this.discard_radius * 1.1) > dist; - } + }; - init_sets() { - // #### states are mutually exclusive - // - // * graphed: in the graph, connected to other nodes - // * shelved: on the shelf, available for choosing - // * discarded: in the discard zone, findable but ignored by show_links_* - // * hidden: findable, but not displayed anywhere (when found, will become shelved) - // * embryonic: incomplete, not ready to be used - // - // #### flags able to co-exist - // - // * chosen: (aka Activated) these nodes are graphed and pull other nodes into - // the graph with them - // * selected: the predicates of the edges terminating at these nodes populate the - // _predicate picker_ with the label **Edges of the Selected Nodes** - // * pinned: in the graph and at fixed positions - // * labelled: these nodes have their name (or id) showing all the time - // * nameless: these nodes do not have names which are distinct from their urls - - this.nodes = SortedSet().named('all'). - sort_on("id"). - labelled(this.human_term.all); - this.nodes.docs = `${this.nodes.label} nodes are in this set, regardless of state.`; - this.all_set = this.nodes; + Huviz.prototype.in_disconnect_dropzone = function(node) { + var dist; + dist = distance(node, this.lariat_center); + return this.graph_radius * 0.9 < dist && this.graph_radius * 1.1 > dist; + }; - this.embryonic_set = SortedSet().named("embryo"). - sort_on("id"). - isFlag(); - this.embryonic_set.docs = `\ -Nodes which are not yet complete are 'embryonic' and not yet \ -in '${this.all_set.label}'. Nodes need to have a class and a label to \ -no longer be embryonic.`; - - this.chosen_set = SortedSet().named("chosen"). - sort_on("id"). - isFlag(). - labelled(this.human_term.chosen). - sub_of(this.all_set); - this.chosen_set.docs = `\ -Nodes which the user has specifically '${this.chosen_set.label}' by either \ -dragging them into the graph from the surrounding green \ -'shelf'. '${this.chosen_set.label}' nodes can drag other nodes into the \ -graph if the others are ${this.human_term.hidden} or ${this.human_term.shelved} but \ -not if they are ${this.human_term.discarded}.`; - this.chosen_set.cleanup_verb = 'shelve'; + Huviz.prototype.in_discard_dropzone = function(node) { + var dist; + dist = distance(node, this.discard_center); + return this.discard_radius * 1.1 > dist; + }; - this.selected_set = SortedSet().named("selected"). - sort_on("id"). - isFlag(). - labelled(this.human_term.selected). - sub_of(this.all_set); + Huviz.prototype.init_sets = function() { + this.nodes = SortedSet().named('all').sort_on("id").labelled(this.human_term.all); + this.nodes.docs = "" + this.nodes.label + " nodes are in this set, regardless of state."; + this.all_set = this.nodes; + this.embryonic_set = SortedSet().named("embryo").sort_on("id").isFlag(); + this.embryonic_set.docs = "Nodes which are not yet complete are 'embryonic' and not yet in '" + this.all_set.label + "'. Nodes need to have a class and a label to no longer be embryonic."; + this.chosen_set = SortedSet().named("chosen").sort_on("id").isFlag().labelled(this.human_term.chosen).sub_of(this.all_set); + this.chosen_set.docs = "Nodes which the user has specifically '" + this.chosen_set.label + "' by either dragging them into the graph from the surrounding green 'shelf'. '" + this.chosen_set.label + "' nodes can drag other nodes into the graph if the others are " + this.human_term.hidden + " or " + this.human_term.shelved + " but not if they are " + this.human_term.discarded + "."; + this.chosen_set.cleanup_verb = 'shelve'; + this.selected_set = SortedSet().named("selected").sort_on("id").isFlag().labelled(this.human_term.selected).sub_of(this.all_set); this.selected_set.cleanup_verb = "unselect"; - this.selected_set.docs = `\ -Nodes which have been '${this.selected_set.label}' using the class picker, \ -ie which are highlighted and a little larger.`; - - this.shelved_set = SortedSet(). - named("shelved"). - sort_on('name'). - case_insensitive_sort(true). - labelled(this.human_term.shelved). - sub_of(this.all_set). - isState(); - this.shelved_set.docs = `\ -Nodes which are '${this.shelved_set.label}' on the green surrounding 'shelf', \ -either because they have been dragged there or released back to there \ -when the node which pulled them into the graph was \ -'${this.human_term.unchosen}.`; - - this.discarded_set = SortedSet().named("discarded"). - labelled(this.human_term.discarded). - sort_on('name'). - case_insensitive_sort(true). - sub_of(this.all_set). - isState(); - this.discarded_set.cleanup_verb = "shelve"; // TODO confirm this - this.discarded_set.docs = `\ -Nodes which have been '${this.discarded_set.label}' by being dragged into \ -the red 'discard bin' in the bottom right corner. \ -'${this.discarded_set.label}' nodes are not pulled into the graph when \ -nodes they are connected to become '${this.chosen_set.label}'.`; - - this.hidden_set = SortedSet().named("hidden"). - sort_on("id"). - labelled(this.human_term.hidden). - sub_of(this.all_set). - isState(); - this.hidden_set.docs = `\ -Nodes which are '${this.hidden_set.label}' but can be pulled into \ -the graph by other nodes when those become \ -'${this.human_term.chosen}'.`; + this.selected_set.docs = "Nodes which have been '" + this.selected_set.label + "' using the class picker, ie which are highlighted and a little larger."; + this.shelved_set = SortedSet().named("shelved").sort_on('name').case_insensitive_sort(true).labelled(this.human_term.shelved).sub_of(this.all_set).isState(); + this.shelved_set.docs = "Nodes which are '" + this.shelved_set.label + "' on the green surrounding 'shelf', either because they have been dragged there or released back to there when the node which pulled them into the graph was '" + this.human_term.unchosen + "."; + this.discarded_set = SortedSet().named("discarded").labelled(this.human_term.discarded).sort_on('name').case_insensitive_sort(true).sub_of(this.all_set).isState(); + this.discarded_set.cleanup_verb = "shelve"; + this.discarded_set.docs = "Nodes which have been '" + this.discarded_set.label + "' by being dragged into the red 'discard bin' in the bottom right corner. '" + this.discarded_set.label + "' nodes are not pulled into the graph when nodes they are connected to become '" + this.chosen_set.label + "'."; + this.hidden_set = SortedSet().named("hidden").sort_on("id").labelled(this.human_term.hidden).sub_of(this.all_set).isState(); + this.hidden_set.docs = "Nodes which are '" + this.hidden_set.label + "' but can be pulled into the graph by other nodes when those become '" + this.human_term.chosen + "'."; this.hidden_set.cleanup_verb = "shelve"; - - this.graphed_set = SortedSet().named("graphed"). - sort_on("id"). - labelled(this.human_term.graphed). - sub_of(this.all_set). - isState(); - this.graphed_set.docs = `\ -Nodes which are included in the central graph either by having been \ -'${this.human_term.chosen}' themselves or which are pulled into the \ -graph by those which have been.`; + this.graphed_set = SortedSet().named("graphed").sort_on("id").labelled(this.human_term.graphed).sub_of(this.all_set).isState(); + this.graphed_set.docs = "Nodes which are included in the central graph either by having been '" + this.human_term.chosen + "' themselves or which are pulled into the graph by those which have been."; this.graphed_set.cleanup_verb = "unchoose"; - - this.wasChosen_set = SortedSet().named("wasChosen"). - sort_on("id"). - labelled("Was Chosen"). - isFlag(); // membership is not mutually exclusive with the isState() sets - this.wasChosen_set.docs = `\ -Nodes are marked wasChosen by wander__atFirst for later comparison \ -with nowChosen.`; - - this.nowChosen_set = SortedSet().named("nowChosen"). - sort_on("id"). - labelled("Now Graphed"). - isFlag(); // membership is not mutually exclusive with the isState() sets - this.nowChosen_set.docs = `\ -Nodes pulled in by @choose() are marked nowChosen for later comparison \ -against wasChosen by wander__atLast.`; - - this.pinned_set = SortedSet().named('fixed'). - sort_on("id"). - labelled(this.human_term.fixed). - sub_of(this.all_set). - isFlag(); - this.pinned_set.docs = `\ -Nodes which are '${this.pinned_set.label}' to the canvas as a result of \ -being dragged and dropped while already being '${this.human_term.graphed}'. \ -${this.pinned_set.label} nodes can be ${this.human_term.unpinned} by dragging \ -them from their ${this.pinned_set.label} location.`; + this.wasChosen_set = SortedSet().named("wasChosen").sort_on("id").labelled("Was Chosen").isFlag(); + this.wasChosen_set.docs = "Nodes are marked wasChosen by wander__atFirst for later comparison with nowChosen."; + this.nowChosen_set = SortedSet().named("nowChosen").sort_on("id").labelled("Now Graphed").isFlag(); + this.nowChosen_set.docs = "Nodes pulled in by @choose() are marked nowChosen for later comparison against wasChosen by wander__atLast."; + this.pinned_set = SortedSet().named('fixed').sort_on("id").labelled(this.human_term.fixed).sub_of(this.all_set).isFlag(); + this.pinned_set.docs = "Nodes which are '" + this.pinned_set.label + "' to the canvas as a result of being dragged and dropped while already being '" + this.human_term.graphed + "'. " + this.pinned_set.label + " nodes can be " + this.human_term.unpinned + " by dragging them from their " + this.pinned_set.label + " location."; this.pinned_set.cleanup_verb = "unpin"; - - this.labelled_set = SortedSet().named("labelled"). - sort_on("id"). - labelled(this.human_term.labelled). - isFlag(). - sub_of(this.all_set); + this.labelled_set = SortedSet().named("labelled").sort_on("id").labelled(this.human_term.labelled).isFlag().sub_of(this.all_set); this.labelled_set.docs = "Nodes which have their labels permanently shown."; this.labelled_set.cleanup_verb = "unlabel"; - - this.nameless_set = SortedSet().named("nameless"). - sort_on("id"). - labelled(this.human_term.nameless). - sub_of(this.all_set). - isFlag('nameless'); + this.nameless_set = SortedSet().named("nameless").sort_on("id").labelled(this.human_term.nameless).sub_of(this.all_set).isFlag('nameless'); this.nameless_set.docs = "Nodes for which no name is yet known"; - - this.links_set = SortedSet(). - named("shown"). - sort_on("id"). - isFlag(); + this.links_set = SortedSet().named("shown").sort_on("id").isFlag(); this.links_set.docs = "Links which are shown."; - - this.walked_set = SortedSet(). - named("walked"). - isFlag(). - labelled(this.human_term.walked). - sub_of(this.chosen_set). - sort_on('walkedIdx0'); // sort on index of position in the path; the 0 means zero-based idx + this.walked_set = SortedSet().named("walked").isFlag().labelled(this.human_term.walked).sub_of(this.chosen_set).sort_on('walkedIdx0'); this.walked_set.docs = "Nodes in order of their walkedness"; - - this.suppressed_set = SortedSet().named("suppressed"). - sort_on("id"). - labelled(this.human_term.suppressed). - sub_of(this.all_set). - isState(); - this.suppressed_set.docs = `\ -Nodes which are '${this.suppressed_set.label}' by a suppression algorithm \ -such as Suppress Annotation Entities. Suppression is mutually exclusive \ -with Shelved, Discarded, Graphed and Hidden.`; + this.suppressed_set = SortedSet().named("suppressed").sort_on("id").labelled(this.human_term.suppressed).sub_of(this.all_set).isState(); + this.suppressed_set.docs = "Nodes which are '" + this.suppressed_set.label + "' by a suppression algorithm such as Suppress Annotation Entities. Suppression is mutually exclusive with Shelved, Discarded, Graphed and Hidden."; this.suppressed_set.cleanup_verb = "shelve"; - this.predicate_set = SortedSet().named("predicate").isFlag().sort_on("id"); - this.context_set = SortedSet().named("context").isFlag().sort_on("id"); + this.context_set = SortedSet().named("context").isFlag().sort_on("id"); this.context_set.docs = "The set of quad contexts."; - - // TODO make selectable_sets drive gclui.build_set_picker - // with the nesting data coming from .sub_of(@all) as above return this.selectable_sets = { all_set: this.all_set, chosen_set: this.chosen_set, @@ -8350,170 +6962,180 @@ with Shelved, Discarded, Graphed and Hidden.`; walked_set: this.walked_set, suppressed_set: this.suppressed_set }; - } + }; - get_set_by_id(setId) { - setId = ((setId === 'fixed') && 'pinned') || setId; // because pinned uses fixed as its 'name' + Huviz.prototype.get_set_by_id = function(setId) { + setId = setId === 'fixed' && 'pinned' || setId; return this[setId + '_set']; - } + }; - update_all_counts() { + Huviz.prototype.update_all_counts = function() { return this.update_set_counts(); - } - //@update_predicate_counts() + }; - update_predicate_counts() { + Huviz.prototype.update_predicate_counts = function() { + var a_set, name, _i, _len, _ref, _results; console.warn('the unproven method update_predicate_counts() has just been called'); - return (() => { - const result = []; - for (let a_set of Array.from(this.predicate_set)) { - const name = a_set.lid; - result.push(this.gclui.on_predicate_count_update(name, a_set.length)); - } - return result; - })(); - } + _ref = this.predicate_set; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + a_set = _ref[_i]; + name = a_set.lid; + _results.push(this.gclui.on_predicate_count_update(name, a_set.length)); + } + return _results; + }; - update_set_counts() { - return (() => { - const result = []; - for (let name in this.selectable_sets) { - const a_set = this.selectable_sets[name]; - result.push(this.gclui.on_set_count_update(name, a_set.length)); - } - return result; - })(); - } + Huviz.prototype.update_set_counts = function() { + var a_set, name, _ref, _results; + _ref = this.selectable_sets; + _results = []; + for (name in _ref) { + a_set = _ref[name]; + _results.push(this.gclui.on_set_count_update(name, a_set.length)); + } + return _results; + }; - create_taxonomy() { - // The taxonomy is intertwined with the taxon_picker - return this.taxonomy = {}; // make driven by the hierarchy - } + Huviz.prototype.create_taxonomy = function() { + return this.taxonomy = {}; + }; - summarize_taxonomy() { - let out = ""; - const tree = {}; - for (let id in this.taxonomy) { - const taxon = this.taxonomy[id]; - out += `${id}: ${taxon.state}\n`; + Huviz.prototype.summarize_taxonomy = function() { + var id, out, taxon, tree, _ref; + out = ""; + tree = {}; + _ref = this.taxonomy; + for (id in _ref) { + taxon = _ref[id]; + out += "" + id + ": " + taxon.state + "\n"; tree[id] = taxon.state; } return tree; - } + }; - regenerate_english() { - const root = 'Thing'; - if (this.taxonomy[root] != null) { // TODO this should be the ROOT, not literally Thing + Huviz.prototype.regenerate_english = function() { + var root; + root = 'Thing'; + if (this.taxonomy[root] != null) { this.taxonomy[root].update_english(); } else { - console.log(`not regenerating english because no taxonomy[${root}]`); + console.log("not regenerating english because no taxonomy[" + root + "]"); } - } + }; - get_or_create_taxon(taxon_url) { - const taxon_id = taxon_url; - if ((this.taxonomy[taxon_id] == null)) { - let label; - const taxon = new Taxon(taxon_id); + Huviz.prototype.get_or_create_taxon = function(taxon_url) { + var label, parent, parent_lid, taxon, taxon_id; + taxon_id = taxon_url; + if (this.taxonomy[taxon_id] == null) { + taxon = new Taxon(taxon_id); this.taxonomy[taxon_id] = taxon; - const parent_lid = this.ontology.subClassOf[taxon_id] || this.HHH[taxon_id] || 'Thing'; + parent_lid = this.ontology.subClassOf[taxon_id] || this.HHH[taxon_id] || 'Thing'; if (parent_lid != null) { - const parent = this.get_or_create_taxon(parent_lid); + parent = this.get_or_create_taxon(parent_lid); taxon.register_superclass(parent); label = this.ontology.label[taxon_id]; } - this.gclui.add_taxon(taxon_id, parent_lid, label, taxon); // FIXME should this be an event on the Taxon constructor? + this.gclui.add_taxon(taxon_id, parent_lid, label, taxon); } return this.taxonomy[taxon_id]; - } + }; - update_labels_on_pickers() { - return (() => { - const result = []; - for (let term_id in this.ontology.label) { - // a label might be for a taxon or a predicate, so we must sort out which - const term_label = this.ontology.label[term_id]; - if (this.gclui.taxon_picker.id_to_name[term_id] != null) { - this.gclui.taxon_picker.set_name_for_id(term_label, term_id); - } - if (this.gclui.predicate_picker.id_to_name[term_id] != null) { - result.push(this.gclui.predicate_picker.set_name_for_id(term_label, term_id)); - } else { - result.push(undefined); - } + Huviz.prototype.update_labels_on_pickers = function() { + var term_id, term_label, _ref, _results; + _ref = this.ontology.label; + _results = []; + for (term_id in _ref) { + term_label = _ref[term_id]; + if (this.gclui.taxon_picker.id_to_name[term_id] != null) { + this.gclui.taxon_picker.set_name_for_id(term_label, term_id); } - return result; - })(); - } + if (this.gclui.predicate_picker.id_to_name[term_id] != null) { + _results.push(this.gclui.predicate_picker.set_name_for_id(term_label, term_id)); + } else { + _results.push(void 0); + } + } + return _results; + }; - toggle_taxon(id, hier, callback) { - let left; + Huviz.prototype.toggle_taxon = function(id, hier, callback) { + var _ref; if (callback != null) { this.gclui.set_taxa_click_storm_callback(callback); } - // TODO preserve the state of collapsedness? - hier = (left = (hier != null)) != null ? left : {hier : true}; // default to true + hier = (_ref = hier != null) != null ? _ref : { + hier: true + }; if (hier) { this.gclui.taxon_picker.collapse_by_id(id); } - this.topJQElem.find(`#${id}`).trigger("click"); + this.topJQElem.find("#" + id).trigger("click"); if (hier) { return this.gclui.taxon_picker.expand_by_id(id); } - } + }; - do(args) { - const cmd = new gcl.GraphCommand(this, args); + Huviz.prototype["do"] = function(args) { + var cmd; + cmd = new gcl.GraphCommand(this, args); return this.gclc.run(cmd); - } + }; - reset_data() { - // TODO fix gclc.run so it can handle empty sets + Huviz.prototype.reset_data = function() { if (this.discarded_set.length) { - this.do({verbs: ['shelve'], sets: [this.discarded_set.id]}); + this["do"]({ + verbs: ['shelve'], + sets: [this.discarded_set.id] + }); } if (this.graphed_set.length) { - this.do({verbs: ['shelve'], sets: [this.graphed_set.id]}); + this["do"]({ + verbs: ['shelve'], + sets: [this.graphed_set.id] + }); } if (this.hidden_set.length) { - this.do({verbs: ['shelve'], sets: [this.hidden_set.id]}); + this["do"]({ + verbs: ['shelve'], + sets: [this.hidden_set.id] + }); } if (this.selected_set.length) { - this.do({verbs: ['unselect'], sets: [this.selected_set.id]}); + this["do"]({ + verbs: ['unselect'], + sets: [this.selected_set.id] + }); } this.gclui.reset_editor(); return this.gclui.select_the_initial_set(); - } + }; - perform_tasks_after_dataset_loaded() { + Huviz.prototype.perform_tasks_after_dataset_loaded = function() { this.gclui.select_the_initial_set(); if (!this.args.skip_discover_names) { return this.discover_names(); } - } + }; - reset_graph() { - this.G = {}; // is this deprecated? + Huviz.prototype.reset_graph = function() { + this.G = {}; this.init_sets(); this.init_gclc(); this.init_editc_or_not(); - this.indexed_dbservice(); // REVIEW is this needed? - this.init_indexddbstorage(); // REVIEW and this? - + this.indexed_dbservice(); + this.init_indexddbstorage(); this.force.nodes(this.nodes); this.force.links(this.links_set); if (!this.args.skip_log_tick) { console.log("Tick in @force.nodes() reset_graph"); } - - // TODO move this SVG code to own renderer - d3.select(`${this.args.huviz_top_sel} .link`).remove(); - d3.select(`${this.args.huviz_top_sel} .node`).remove(); - d3.select(`${this.args.huviz_top_sel} .lariat`).remove(); - this.node = this.svg.selectAll(`${this.args.huviz_top_sel} .node`); - this.link = this.svg.selectAll(`${this.args.huviz_top_sel} .link`); // looks bogus, see @link assignment below - this.lariat = this.svg.selectAll(`${this.args.huviz_top_sel} .lariat`); - + d3.select("" + this.args.huviz_top_sel + " .link").remove(); + d3.select("" + this.args.huviz_top_sel + " .node").remove(); + d3.select("" + this.args.huviz_top_sel + " .lariat").remove(); + this.node = this.svg.selectAll("" + this.args.huviz_top_sel + " .node"); + this.link = this.svg.selectAll("" + this.args.huviz_top_sel + " .link"); + this.lariat = this.svg.selectAll("" + this.args.huviz_top_sel + " .lariat"); this.link = this.link.data(this.links_set); this.link.exit().remove(); this.node = this.node.data(this.nodes); @@ -8522,62 +7144,63 @@ with Shelved, Discarded, Graphed and Hidden.`; if (!this.args.skip_log_tick) { return console.log("Tick in @force.start() reset_graph2"); } - } + }; - set_node_radius_policy(evt) { - // TODO(shawn) remove or replace this whole method - const f = $("select#node_radius_policy option:selected").val(); - if (!f) { return; } + Huviz.prototype.set_node_radius_policy = function(evt) { + var f; + f = $("select#node_radius_policy option:selected").val(); + if (!f) { + return; + } if (typeof f === typeof "str") { return this.node_radius_policy = node_radius_policies[f]; } else if (typeof f === typeof this.set_node_radius_policy) { return this.node_radius_policy = f; } - } - //else - // console.log("f =", f) + }; - DEPRECATED_init_node_radius_policy() { - const policy_box = d3.select("#huvis_controls").append("div", "node_radius_policy_box"); - const policy_picker = policy_box.append("select", "node_radius_policy"); + Huviz.prototype.DEPRECATED_init_node_radius_policy = function() { + var policy_box, policy_name, policy_picker, _results; + policy_box = d3.select("#huvis_controls").append("div", "node_radius_policy_box"); + policy_picker = policy_box.append("select", "node_radius_policy"); policy_picker.on("change", set_node_radius_policy); - return (() => { - const result = []; - for (let policy_name in node_radius_policies) { - result.push(policy_picker.append("option").attr("value", policy_name).text(policy_name)); - } - return result; - })(); - } + _results = []; + for (policy_name in node_radius_policies) { + _results.push(policy_picker.append("option").attr("value", policy_name).text(policy_name)); + } + return _results; + }; - calc_node_radius(d) { - const total_links = d.links_to.length + d.links_from.length; - const diff_adjustment = 10 * (total_links/(total_links+9)); - const final_adjustment = this.node_diff * (diff_adjustment - 1); + Huviz.prototype.calc_node_radius = function(d) { + var diff_adjustment, final_adjustment, total_links; + total_links = d.links_to.length + d.links_from.length; + diff_adjustment = 10 * (total_links / (total_links + 9)); + final_adjustment = this.node_diff * (diff_adjustment - 1); if (d.radius != null) { return d.radius; } - return (this.node_radius * (((d.selected == null) && 1) || this.selected_mag)) + final_adjustment; - } - //@node_radius_policy d - names_in_edges(set) { - const out = []; - set.forEach((itm, i) => out.push(itm.source.name + " ---> " + itm.target.name)); + return this.node_radius * ((d.selected == null) && 1 || this.selected_mag) + final_adjustment; + }; + + Huviz.prototype.names_in_edges = function(set) { + var out; + out = []; + set.forEach(function(itm, i) { + return out.push(itm.source.name + " ---> " + itm.target.name); + }); return out; - } - dump_details(node) { - if (!window.dump_details) { return; } - // - // if (! DUMP){ - // if (node.s.id != '_:E') return; - // } - // + }; + + Huviz.prototype.dump_details = function(node) { + if (!window.dump_details) { + return; + } console.log("================================================="); console.log(node.name); console.log(" x,y:", node.x, node.y); try { console.log(" state:", node.state.state_name, node.state); - } catch (error) {} + } catch (_error) {} console.log(" chosen:", node.chosen); console.log(" fisheye:", node.fisheye); console.log(" fixed:", node.fixed); @@ -8586,43 +7209,34 @@ with Shelved, Discarded, Graphed and Hidden.`; console.log(" links_from:", node.links_from.length, this.names_in_edges(node.links_from)); console.log(" showing_links:", node.showing_links); return console.log(" in_sets:", node.in_sets); - } + }; - // Return the nodes which can be seen and are worth checking for proximity, etc. - is_node_visible(node) { + Huviz.prototype.is_node_visible = function(node) { return !this.hidden_set.has(node); - } + }; - // Return an array (not a SortedSet) of nodes which are visible - get_visible_subset(super_set) { - if (super_set == null) { super_set = this.all_set; } - const retlist = []; - for (let node of Array.from(super_set)) { + Huviz.prototype.get_visible_subset = function(super_set) { + var node, retlist, _i, _len; + if (super_set == null) { + super_set = this.all_set; + } + retlist = []; + for (_i = 0, _len = super_set.length; _i < _len; _i++) { + node = super_set[_i]; if (this.is_node_visible(node)) { retlist.push(node); } } return super_set; - } + }; - // # References: - // https://github.com/d3/d3-quadtree - // - // # Examples - // - // * http://bl.ocks.org/patricksurry/6478178 - // * https://bl.ocks.org/mbostock/9078690 - // - // # Status - // - // Having trouble getting access to the addAll method - WIP_find_node_or_edge_closest_to_pointer_using_quadtrees() { - const quadtree = d3.geom.quadtree() - .extent([[-1, -1], [this.width + 1, this.height + 1]]) - .addAll(this.get_visible_subset()); - const [mx, my] = Array.from(this.last_mouse_pos); - const qNodes = function(qTree) { - const ret = []; + Huviz.prototype.WIP_find_node_or_edge_closest_to_pointer_using_quadtrees = function() { + var data, found, mx, my, qNodes, quadtree, _ref; + quadtree = d3.geom.quadtree().extent([[-1, -1], [this.width + 1, this.height + 1]]).addAll(this.get_visible_subset()); + _ref = this.last_mouse_pos, mx = _ref[0], my = _ref[1]; + qNodes = function(qTree) { + var ret; + ret = []; return qTree.visit(function(node, x0, y0, x1, y1) { node.x0 = x0; node.y0 = y0; @@ -8631,23 +7245,21 @@ with Shelved, Discarded, Graphed and Hidden.`; return ret.push(node); }); }; - const data = qNodes(quadtree); - const found = quadtree.find(mx, my); + data = qNodes(quadtree); + found = quadtree.find(mx, my); throw new Error("under construction"); - } + }; - find_node_or_edge_closest_to_pointer() { + Huviz.prototype.find_node_or_edge_closest_to_pointer = function() { + var closest_dist, closest_point, focus_threshold, new_focused_edge, new_focused_idx, new_focused_node, seeking; this.highwater('find_node_or_edge', true); - let new_focused_node = null; - let new_focused_edge = null; - let new_focused_idx = null; - let { - focus_threshold - } = this; - let closest_dist = this.width; - let closest_point = null; - - let seeking = null; // holds property name of the thing we are seeking: 'focused_node'/'object_node'/false + new_focused_node = null; + new_focused_edge = null; + new_focused_idx = null; + focus_threshold = this.focus_threshold; + closest_dist = this.width; + closest_point = null; + seeking = null; if (this.dragging) { if (!this.editui.is_state('connecting')) { return; @@ -8656,130 +7268,133 @@ with Shelved, Discarded, Graphed and Hidden.`; } else { seeking = "focused_node"; } - - // TODO build a spatial index!!!! OMG https://github.com/smurp/huviz/issues/25 - // Examine every node to find the closest one within the focus_threshold - this.all_set.forEach((d, i) => { - const n_dist = distance(d.fisheye || d, this.last_mouse_pos); - //console.log(d) - if (n_dist < closest_dist) { - closest_dist = n_dist; - closest_point = d.fisheye || d; - } - if (!((seeking === 'object_node') && this.dragging && (this.dragging.id === d.id))) { - if (n_dist <= focus_threshold) { - new_focused_node = d; - focus_threshold = n_dist; - return new_focused_idx = i; + this.all_set.forEach((function(_this) { + return function(d, i) { + var n_dist; + n_dist = distance(d.fisheye || d, _this.last_mouse_pos); + if (n_dist < closest_dist) { + closest_dist = n_dist; + closest_point = d.fisheye || d; } - } - }); - - // Examine the center of every edge and make it the new_focused_edge - // if close enough and the closest thing - this.links_set.forEach((e, i) => { - if (e.handle != null) { - const e_dist = distance(e.handle, this.last_mouse_pos); - if (e_dist < closest_dist) { - closest_dist = e_dist; - closest_point = e.handle; + if (!(seeking === 'object_node' && _this.dragging && _this.dragging.id === d.id)) { + if (n_dist <= focus_threshold) { + new_focused_node = d; + focus_threshold = n_dist; + return new_focused_idx = i; + } } - if (e_dist <= focus_threshold) { - let new_focused_edge_idx; - new_focused_edge = e; - focus_threshold = e_dist; - return new_focused_edge_idx = i; + }; + })(this)); + this.links_set.forEach((function(_this) { + return function(e, i) { + var e_dist, new_focused_edge_idx; + if (e.handle != null) { + e_dist = distance(e.handle, _this.last_mouse_pos); + if (e_dist < closest_dist) { + closest_dist = e_dist; + closest_point = e.handle; + } + if (e_dist <= focus_threshold) { + new_focused_edge = e; + focus_threshold = e_dist; + return new_focused_edge_idx = i; + } } - } - }); - - if (new_focused_edge) { // the mouse is closer to an edge than a node + }; + })(this)); + if (new_focused_edge) { new_focused_node = null; seeking = null; } - if (closest_point) { if (this.draw_circle_around_focused) { this.draw_circle(closest_point.x, closest_point.y, this.node_radius * 3, "red"); } } - this.set_focused_node(new_focused_node); this.set_focused_edge(new_focused_edge); - if (seeking === 'object_node') { this.editui.set_object_node(new_focused_node); } this.highwater('find_node_or_edge'); - } + }; - highwater_incr(id) { - if (this.highwatermarks == null) { this.highwatermarks = {}; } - const hwm = this.highwatermarks; - return hwm[id] = (((hwm[id] != null) && hwm[id]) || 0) + 1; - } + Huviz.prototype.highwater_incr = function(id) { + var hwm; + if (this.highwatermarks == null) { + this.highwatermarks = {}; + } + hwm = this.highwatermarks; + return hwm[id] = ((hwm[id] != null) && hwm[id] || 0) + 1; + }; - highwater(id, start) { - if (this.highwatermarks == null) { this.highwatermarks = {}; } - const hwm = this.highwatermarks; + Huviz.prototype.highwater = function(id, start) { + var diff, hwm; + if (this.highwatermarks == null) { + this.highwatermarks = {}; + } + hwm = this.highwatermarks; if (start != null) { return hwm[id + '__'] = performance.now(); } else { - const diff = performance.now() - hwm[id + '__']; - if (hwm[id] == null) { hwm[id] = diff; } + diff = performance.now() - hwm[id + '__']; + if (hwm[id] == null) { + hwm[id] = diff; + } if (hwm[id] < diff) { return hwm[id] = diff; } } - } + }; + + Huviz.prototype.DEPRECATED_showing_links_to_cursor_map = { + all: 'not-allowed', + some: 'all-scroll', + none: 'pointer' + }; - set_focused_node(node) { // node might be null + Huviz.prototype.set_focused_node = function(node) { + var svg_node; if (this.focused_node === node) { - return; // no change so skip + return; } if (this.focused_node) { - // unfocus the previously focused_node if (this.use_svg) { d3.select(".focused_node").classed("focused_node", false); } - //@unscroll_pretty_name(@focused_node) this.focused_node.focused_node = false; } if (node) { if (this.use_svg) { - const svg_node = node[0][new_focused_idx]; + svg_node = node[0][new_focused_idx]; d3.select(svg_node).classed("focused_node", true); } node.focused_node = true; } - this.focused_node = node; // might be null + this.focused_node = node; if (this.focused_node) { - //console.log("focused_node:", @focused_node) - return this.gclui.engage_transient_verb_if_needed("select"); // select is default verb + return this.gclui.engage_transient_verb_if_needed("select"); } else { return this.gclui.disengage_transient_verb_if_needed(); } - } + }; - set_focused_edge(new_focused_edge) { - if (this.proposed_edge && this.focused_edge) { // TODO why bail now??? + Huviz.prototype.set_focused_edge = function(new_focused_edge) { + if (this.proposed_edge && this.focused_edge) { return; } - //console.log "set_focused_edge(#{new_focused_edge and new_focused_edge.id})" if (this.focused_edge !== new_focused_edge) { - if (this.focused_edge != null) { //and @focused_edge isnt new_focused_edge - //console.log "removing focus from previous focused_edge" + if (this.focused_edge != null) { this.focused_edge.focused = false; delete this.focused_edge.source.focused_edge; delete this.focused_edge.target.focused_edge; } if (new_focused_edge != null) { - // FIXME add use_svg stanza new_focused_edge.focused = true; new_focused_edge.source.focused_edge = true; new_focused_edge.target.focused_edge = true; } - this.focused_edge = new_focused_edge; // blank it or set it + this.focused_edge = new_focused_edge; if (this.focused_edge != null) { if (this.editui.is_state('connecting')) { return this.text_cursor.pause("", "edit this edge"); @@ -8787,75 +7402,92 @@ with Shelved, Discarded, Graphed and Hidden.`; return this.text_cursor.pause("", "show edge sources"); } } else { - return this.text_cursor.continue(); //initialization (no proposed edge active) + return this.text_cursor["continue"](); } } - } - set_proposed_edge(new_proposed_edge) { + }; + + Huviz.proposed_edge = null; + + Huviz.prototype.set_proposed_edge = function(new_proposed_edge) { console.log("Setting proposed edge...", new_proposed_edge); if (this.proposed_edge) { - delete this.proposed_edge.proposed; // remove .proposed flag from old one + delete this.proposed_edge.proposed; } if (new_proposed_edge) { - new_proposed_edge.proposed = true; // flag the new one + new_proposed_edge.proposed = true; } - this.proposed_edge = new_proposed_edge; // might be null - return this.set_focused_edge(new_proposed_edge); // a proposed_edge also becomes focused - } + this.proposed_edge = new_proposed_edge; + return this.set_focused_edge(new_proposed_edge); + }; - install_update_pointer_togglers() { + Huviz.prototype.install_update_pointer_togglers = function() { console.warn("the update_pointer_togglers are being called too often"); - d3.select("#huvis_controls").on("mouseover", () => { - this.update_pointer = false; - return this.text_cursor.pause("default"); - }); - //console.log "update_pointer: #{@update_pointer}" - return d3.select("#huvis_controls").on("mouseout", () => { - this.update_pointer = true; - return this.text_cursor.continue(); - }); - } - //console.log "update_pointer: #{@update_pointer}" + d3.select("#huvis_controls").on("mouseover", (function(_this) { + return function() { + _this.update_pointer = false; + return _this.text_cursor.pause("default"); + }; + })(this)); + return d3.select("#huvis_controls").on("mouseout", (function(_this) { + return function() { + _this.update_pointer = true; + return _this.text_cursor["continue"](); + }; + })(this)); + }; - DEPRECATED_adjust_cursor() { - // http://css-tricks.com/almanac/properties/c/cursor/ - let next; + Huviz.prototype.DEPRECATED_adjust_cursor = function() { + var next; if (this.focused_node) { next = this.showing_links_to_cursor_map[this.focused_node.showing_links]; } else { next = 'default'; } return this.text_cursor.set_cursor(next); - } + }; - set_cursor_for_verbs(verbs) { + Huviz.prototype.set_cursor_for_verbs = function(verbs) { + var text, verb; if (!this.use_fancy_cursor) { return; } - const text = [Array.from(verbs).map((verb) => this.human_term[verb])].join("\n"); + text = [ + (function() { + var _i, _len, _results; + _results = []; + for (_i = 0, _len = verbs.length; _i < _len; _i++) { + verb = verbs[_i]; + _results.push(this.human_term[verb]); + } + return _results; + }).call(this) + ].join("\n"); if (this.last_cursor_text !== text) { this.text_cursor.set_text(text); return this.last_cursor_text = text; } - } + }; - auto_change_verb() { + Huviz.prototype.auto_change_verb = function() { if (this.focused_node) { return this.gclui.auto_change_verb_if_warranted(this.focused_node); } - } + }; - get_focused_node_and_its_state() { - const focused = this.focused_node; + Huviz.prototype.get_focused_node_and_its_state = function() { + var focused, msg, retval; + focused = this.focused_node; if (!focused) { return; } - let retval = (focused.lid || '') + ' '; - if ((focused.state == null)) { - const msg = retval + ' has no state!!! This is unpossible!!!! name:'; - if (focused._warnings == null) { focused._warnings = {}; } + retval = (focused.lid || '') + ' '; + if (focused.state == null) { + msg = retval + ' has no state!!! This is unpossible!!!! name:'; + if (focused._warnings == null) { + focused._warnings = {}; + } if (!focused._warnings[msg]) { - // warn each unique message once console.warn(msg, focused.name); focused._warnings[msg] = true; } @@ -8863,56 +7495,68 @@ with Shelved, Discarded, Graphed and Hidden.`; } retval += focused.state.id; return retval; - } + }; - on_tick_change_current_command_if_warranted() { - // It is warranted if we are hovering over nodes and the last state and this stat differ. - // The status of the current command might change even if the mouse has not moved, because - // for instance the graph has wiggled around under a stationary mouse. For that reason - // it is legit to go to the trouble of updating the command on the tick. When though? - // The command should be changed if one of a number of things has changed since last tick: - // * the focused node - // * the state of the focused node - if (this.prior_node_and_state !== this.get_focused_node_and_its_state()) { // ie if it has changed + Huviz.prototype.on_tick_change_current_command_if_warranted = function() { + var nodes; + if (this.prior_node_and_state !== this.get_focused_node_and_its_state()) { if (this.gclui.engaged_verbs.length) { - const nodes = ((this.focused_node != null) && [this.focused_node]) || []; - return this.gclui.prepare_command( - this.gclui.new_GraphCommand({verbs: this.gclui.engaged_verbs, subjects: nodes})); + nodes = (this.focused_node != null) && [this.focused_node] || []; + return this.gclui.prepare_command(this.gclui.new_GraphCommand({ + verbs: this.gclui.engaged_verbs, + subjects: nodes + })); } } - } + }; - position_nodes_by_force() { - const only_move_subject = this.editui.is_state('connecting') && this.dragging && this.editui.subject_node; - return this.nodes.forEach((node, i) => { - return this.reposition_node_by_force(node, only_move_subject); - }); - } + Huviz.prototype.position_nodes_by_force = function() { + var only_move_subject; + only_move_subject = this.editui.is_state('connecting') && this.dragging && this.editui.subject_node; + return this.nodes.forEach((function(_this) { + return function(node, i) { + return _this.reposition_node_by_force(node, only_move_subject); + }; + })(this)); + }; - reposition_node_by_force(node, only_move_subject) { + Huviz.prototype.reposition_node_by_force = function(node, only_move_subject) { if (this.dragging === node) { this.move_node_to_point(node, this.last_mouse_pos); } if (only_move_subject) { return; } - if (!this.graphed_set.has(node)) { // slower - //if node.showing_links is 'none' # faster + if (!this.graphed_set.has(node)) { return; } return node.fisheye = this.fisheye(node); - } - - apply_fisheye() { - this.links_set.forEach(e => { - if (!e.target.fisheye) { return e.target.fisheye = this.fisheye(e.target); } - }); + }; + Huviz.prototype.apply_fisheye = function() { + this.links_set.forEach((function(_this) { + return function(e) { + if (!e.target.fisheye) { + return e.target.fisheye = _this.fisheye(e.target); + } + }; + })(this)); if (this.use_svg) { - return link.attr("x1", d => d.source.fisheye.x).attr("y1", d => d.source.fisheye.y).attr("x2", d => d.target.fisheye.x).attr("y2", d => d.target.fisheye.y); + return link.attr("x1", function(d) { + return d.source.fisheye.x; + }).attr("y1", function(d) { + return d.source.fisheye.y; + }).attr("x2", function(d) { + return d.target.fisheye.x; + }).attr("y2", function(d) { + return d.target.fisheye.y; + }); } - } - show_message_once(msg, alert_too) { + }; + + Huviz.prototype.shown_messages = []; + + Huviz.prototype.show_message_once = function(msg, alert_too) { if (this.shown_messages.indexOf(msg) === -1) { this.shown_messages.push(msg); console.log(msg); @@ -8920,338 +7564,305 @@ with Shelved, Discarded, Graphed and Hidden.`; return alert(msg); } } - } + }; - draw_edges_from(node) { - let e, n_n; - const num_edges = node.links_to.length; - //@show_message_once "draw_edges_from(#{node.id}) "+ num_edges - if (!num_edges) { return; } - - const draw_n_n = {}; - for (e of Array.from(node.links_shown)) { - let msg = ""; - //if e.source is node - //continue + Huviz.prototype.draw_edges_from = function(node) { + var arw_angle, draw_n_n, e, edge_width, edges_between, line_width, msg, n_n, num_edges, sway, x2, y2, _i, _len, _ref, _results; + num_edges = node.links_to.length; + if (!num_edges) { + return; + } + draw_n_n = {}; + _ref = node.links_shown; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + e = _ref[_i]; + msg = ""; if (e.source.embryo) { - msg += `source ${e.source.name} is embryo ${e.source.id}; `; + msg += "source " + e.source.name + " is embryo " + e.source.id + "; "; msg += e.id + " "; } if (e.target.embryo) { - msg += `target ${e.target.name} is embryo ${e.target.id}`; + msg += "target " + e.target.name + " is embryo " + e.target.id; } if (msg !== "") { - //@show_message_once(msg) continue; } n_n = e.source.lid + " " + e.target.lid; - if ((draw_n_n[n_n] == null)) { + if (draw_n_n[n_n] == null) { draw_n_n[n_n] = []; } draw_n_n[n_n].push(e); } - //@show_message_once("will draw edge() n_n:#{n_n} e.id:#{e.id}") - const { - edge_width - } = this; - return (() => { - const result = []; - for (n_n in draw_n_n) { - var edges_between = draw_n_n[n_n]; - var sway = 1; - result.push((() => { - const result1 = []; - for (e of Array.from(edges_between)) { - //console.log e - var line_width; - if ((e.focused != null) && e.focused) { - line_width = this.edge_width * this.peeking_line_thicker; - } else { - line_width = edge_width; - } - line_width = line_width + (this.line_edge_weight * e.contexts.length); - //@show_message_once("will draw line() n_n:#{n_n} e.id:#{e.id}") - if ((e.source.fisheye.x === e.target.fisheye.x) && (e.source.fisheye.y === e.target.fisheye.y)) { - const x2 = this.width/2; // Find centre of draw area - const y2 = this.height/2; - //arw_angle = Math.atan((e.source.fisheye.y - y2)/(e.source.fisheye.x - x2)) # find angle between node center and draw area center - let arw_angle = Math.atan((e.source.fisheye.y - y2)/(e.source.fisheye.x - x2)); - //console.log arw_angle - //console.log (e.source.fisheye.y - y2)/(e.source.fisheye.x - x2) - if (x2 > e.source.fisheye.x) { arw_angle = arw_angle + 3; } - this.draw_self_edge_circle(e.source.fisheye.x, e.source.fisheye.y, e.color, e.contexts.length, line_width, e, arw_angle); - } else { - this.draw_curvedline(e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, - e.target.fisheye.y, sway, e.color, e.contexts.length, line_width, e); - } - - if (node.walked) { // ie is part of the walk path - this.draw_walk_edge_from(node, e, sway); + edge_width = this.edge_width; + _results = []; + for (n_n in draw_n_n) { + edges_between = draw_n_n[n_n]; + sway = 1; + _results.push((function() { + var _j, _len1, _results1; + _results1 = []; + for (_j = 0, _len1 = edges_between.length; _j < _len1; _j++) { + e = edges_between[_j]; + if ((e.focused != null) && e.focused) { + line_width = this.edge_width * this.peeking_line_thicker; + } else { + line_width = edge_width; + } + line_width = line_width + (this.line_edge_weight * e.contexts.length); + if ((e.source.fisheye.x === e.target.fisheye.x) && (e.source.fisheye.y === e.target.fisheye.y)) { + x2 = this.width / 2; + y2 = this.height / 2; + arw_angle = Math.atan((e.source.fisheye.y - y2) / (e.source.fisheye.x - x2)); + if (x2 > e.source.fisheye.x) { + arw_angle = arw_angle + 3; } - result1.push(sway++); + this.draw_self_edge_circle(e.source.fisheye.x, e.source.fisheye.y, e.color, e.contexts.length, line_width, e, arw_angle); + } else { + this.draw_curvedline(e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, e.target.fisheye.y, sway, e.color, e.contexts.length, line_width, e); } - return result1; - })()); - } - return result; - })(); - } + if (node.walked) { + this.draw_walk_edge_from(node, e, sway); + } + _results1.push(sway++); + } + return _results1; + }).call(this)); + } + return _results; + }; - draw_walk_edge_from(node, edge, sway) { - //if this line from path node to path node then add black highlight + Huviz.prototype.draw_walk_edge_from = function(node, edge, sway) { + var directional_edge, e; if (this.edgeIsOnWalkedPath(edge)) { - const directional_edge = ((edge.source.walkedIdx0 > edge.source.walkedIdx0) && 'forward') || 'backward'; - const e = edge; + directional_edge = (edge.source.walkedIdx0 > edge.source.walkedIdx0) && 'forward' || 'backward'; + e = edge; if (directional_edge) { - return this.draw_curvedline(e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, - e.target.fisheye.y, sway, "black", e.contexts.length, 1, e, directional_edge); + return this.draw_curvedline(e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, e.target.fisheye.y, sway, "black", e.contexts.length, 1, e, directional_edge); } } - } + }; - draw_edges() { + Huviz.prototype.draw_edges = function() { + var dx, dy; if (!this.show_edges) { return; } if (this.use_canvas) { - this.graphed_set.forEach((node, i) => { - return this.draw_edges_from(node); - }); + this.graphed_set.forEach((function(_this) { + return function(node, i) { + return _this.draw_edges_from(node); + }; + })(this)); } - if (this.use_webgl) { - let dx = this.width * xmult; - let dy = this.height * ymult; + dx = this.width * xmult; + dy = this.height * ymult; dx = -1 * this.cx; dy = -1 * this.cy; - this.links_set.forEach(e => { - //e.target.fisheye = @fisheye(e.target) unless e.target.fisheye - if (!e.gl) { this.add_webgl_line(e); } - const l = e.gl; - - // - // if (e.source.fisheye.x != e.target.fisheye.x && - // e.source.fisheye.y != e.target.fisheye.y){ - // alert(e.id + " edge has a length"); - // } - // - this.mv_line(l, e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, e.target.fisheye.y); - return this.dump_line(l); - }); + this.links_set.forEach((function(_this) { + return function(e) { + var l; + if (!e.gl) { + _this.add_webgl_line(e); + } + l = e.gl; + _this.mv_line(l, e.source.fisheye.x, e.source.fisheye.y, e.target.fisheye.x, e.target.fisheye.y); + return _this.dump_line(l); + }; + })(this)); } - if (this.use_webgl && false) { - return this.links_set.forEach((e, i) => { - if (!e.gl) { return; } - const v = e.gl.geometry.vertices; - v[0].x = e.source.fisheye.x; - v[0].y = e.source.fisheye.y; - v[1].x = e.target.fisheye.x; - return v[1].y = e.target.fisheye.y; - }); + return this.links_set.forEach((function(_this) { + return function(e, i) { + var v; + if (!e.gl) { + return; + } + v = e.gl.geometry.vertices; + v[0].x = e.source.fisheye.x; + v[0].y = e.source.fisheye.y; + v[1].x = e.target.fisheye.x; + return v[1].y = e.target.fisheye.y; + }; + })(this)); } - } - - draw_nodes_in_set(set, radius, center) { - // cx and cy are local here TODO(smurp) rename cx and cy - const cx = center[0]; - const cy = center[1]; - const num = set.length; - return set.forEach((node, i) => { - //clockwise = false - // 0 or 1 starts at 6, 0.5 starts at 12, 0.75 starts at 9, 0.25 starts at 3 - let rad; - const start = 1 - nodeOrderAngle; - if (this.display_shelf_clockwise) { - rad = tau * (start - (i / num)); - } else { - rad = tau * ((i / num) + start); - } + }; - node.rad = rad; - node.x = cx + (Math.sin(rad) * radius); - node.y = cy + (Math.cos(rad) * radius); - node.fisheye = this.fisheye(node); - if (this.use_canvas) { - const filclrs = this.get_node_color_or_color_list( - node, renderStyles.nodeHighlightOutline); - this.draw_pie(node.fisheye.x, node.fisheye.y, - this.calc_node_radius(node), - node.color || "yellow", - filclrs); - } - if (this.use_webgl) { - return this.mv_node(node.gl, node.fisheye.x, node.fisheye.y); - } - }); - } + Huviz.prototype.draw_nodes_in_set = function(set, radius, center) { + var cx, cy, num; + cx = center[0]; + cy = center[1]; + num = set.length; + return set.forEach((function(_this) { + return function(node, i) { + var filclrs, rad, start; + start = 1 - nodeOrderAngle; + if (_this.display_shelf_clockwise) { + rad = tau * (start - i / num); + } else { + rad = tau * (i / num + start); + } + node.rad = rad; + node.x = cx + Math.sin(rad) * radius; + node.y = cy + Math.cos(rad) * radius; + node.fisheye = _this.fisheye(node); + if (_this.use_canvas) { + filclrs = _this.get_node_color_or_color_list(node, renderStyles.nodeHighlightOutline); + _this.draw_pie(node.fisheye.x, node.fisheye.y, _this.calc_node_radius(node), node.color || "yellow", filclrs); + } + if (_this.use_webgl) { + return _this.mv_node(node.gl, node.fisheye.x, node.fisheye.y); + } + }; + })(this)); + }; - draw_discards() { + Huviz.prototype.draw_discards = function() { return this.draw_nodes_in_set(this.discarded_set, this.discard_radius, this.discard_center); - } - draw_shelf() { + }; + + Huviz.prototype.draw_shelf = function() { return this.draw_nodes_in_set(this.shelved_set, this.graph_radius, this.lariat_center); - } - draw_nodes() { + }; + + Huviz.prototype.draw_nodes = function() { if (this.use_svg) { - node.attr("transform", (d, i) => "translate(" + d.fisheye.x + "," + d.fisheye.y + ")").attr("r", calc_node_radius); + node.attr("transform", function(d, i) { + return "translate(" + d.fisheye.x + "," + d.fisheye.y + ")"; + }).attr("r", calc_node_radius); } if (this.use_canvas || this.use_webgl) { - return this.graphed_set.forEach((d, i) => { - let x, y; - d.fisheye = this.fisheye(d); - //console.log d.name.NOLANG - if (this.use_canvas) { - let filclr, imgUrl, special_focus; - const node_radius = this.calc_node_radius(d); - let stroke_color = d.color || 'yellow'; - if (d.chosen != null) { - stroke_color = renderStyles.nodeHighlightOutline; - // if the node d is in the @walked_set it needs special_focus - special_focus = !!d.walked; // "not not" forces boolean - } - // if 'pills' is selected; change node shape to rounded squares - if (node_display_type === 'pills') { - const pill_width = node_radius * 2; - const pill_height = node_radius * 2; - filclr = this.get_node_color_or_color_list(d); - const rndng = 1; - ({ - x - } = d.fisheye); - ({ - y - } = d.fisheye); - this.rounded_rectangle(x, y, - pill_width, - pill_height, - rndng, - stroke_color, - filclr); - } else if (this.show_images_in_nodes && - (imgUrl = (d.__thumbnail || this.args.default_node_url))) { - let imageData; - try { - imageData = this.get_or_create_round_img(imgUrl); - } catch (e) { - console.error(e); + return this.graphed_set.forEach((function(_this) { + return function(d, i) { + var e, filclr, imageData, imgUrl, node_radius, pill_height, pill_width, rndng, special_focus, stroke_color, x, y; + d.fisheye = _this.fisheye(d); + if (_this.use_canvas) { + node_radius = _this.calc_node_radius(d); + stroke_color = d.color || 'yellow'; + if (d.chosen != null) { + stroke_color = renderStyles.nodeHighlightOutline; + special_focus = !!d.walked; + } + if (node_display_type === 'pills') { + pill_width = node_radius * 2; + pill_height = node_radius * 2; + filclr = _this.get_node_color_or_color_list(d); + rndng = 1; + x = d.fisheye.x; + y = d.fisheye.y; + _this.rounded_rectangle(x, y, pill_width, pill_height, rndng, stroke_color, filclr); + } else if (_this.show_images_in_nodes && (imgUrl = d.__thumbnail || _this.args.default_node_url)) { + try { + imageData = _this.get_or_create_round_img(imgUrl); + } catch (_error) { + e = _error; + console.error(e); + } + _this.draw_round_img(d.fisheye.x, d.fisheye.y, node_radius, stroke_color, filclr, special_focus, imageData, imgUrl); + } else { + _this.draw_pie(d.fisheye.x, d.fisheye.y, node_radius, stroke_color, _this.get_node_color_or_color_list(d), special_focus); } - this.draw_round_img( - d.fisheye.x, d.fisheye.y, - node_radius, - stroke_color, - filclr, - special_focus, - imageData, - imgUrl); - } else { - this.draw_pie(d.fisheye.x, d.fisheye.y, - node_radius, - stroke_color, - this.get_node_color_or_color_list(d), - special_focus); } - } - if (this.use_webgl) { - return this.mv_node(d.gl, d.fisheye.x, d.fisheye.y); - } - }); + if (_this.use_webgl) { + return _this.mv_node(d.gl, d.fisheye.x, d.fisheye.y); + } + }; + })(this)); } - } + }; - get_node_color_or_color_list(n, default_color) { - if (default_color == null) { default_color = 'black'; } - if (this.color_nodes_as_pies && n._types && (n._types.length > 1)) { + Huviz.prototype.get_node_color_or_color_list = function(n, default_color) { + if (default_color == null) { + default_color = 'black'; + } + if (this.color_nodes_as_pies && n._types && n._types.length > 1) { this.recolor_node(n, default_color); return n._colors; } return [n.color || default_color]; - } + }; - get_or_create_round_img(url) { - let img, roundImage; - if (this.round_img_cache == null) { this.round_img_cache = {}; } - const display_image_size = 128; + Huviz.prototype.get_or_create_round_img = function(url) { + var ctx, display_image_size, img, imgId, origImage, roundImage, round_image_maker; + if (this.round_img_cache == null) { + this.round_img_cache = {}; + } + display_image_size = 128; if (!(img = this.round_img_cache[url])) { - const imgId = this.unique_id('round_img_'); + imgId = this.unique_id('round_img_'); roundImage = document.createElement('img'); - const round_image_maker = document.createElement("CANVAS"); - round_image_maker.width = display_image_size; // size of ultimate image + round_image_maker = document.createElement("CANVAS"); + round_image_maker.width = display_image_size; round_image_maker.height = display_image_size; - const ctx = round_image_maker.getContext("2d"); - - const origImage = new Image(); + ctx = round_image_maker.getContext("2d"); + origImage = new Image(); origImage.crossOrigin = "Anonymous"; - origImage.src = url; // path to image file - - origImage.onload = function() { // When image is loaded create a new round image - let h, w, x, y; + origImage.src = url; + origImage.onload = function() { + var h, w, x, y; ctx.beginPath(); - // This needs to be half the size of height/width to fill canvas area - ctx.arc(display_image_size/2, display_image_size/2, - display_image_size/2, 0, 2 * Math.PI, false); + ctx.arc(display_image_size / 2, display_image_size / 2, display_image_size / 2, 0, 2 * Math.PI, false); ctx.clip(); ctx.fillStyle = renderStyles.pageBg; ctx.fill(); - - if (origImage.width > origImage.height) { // Landscape image - w = Math.round((origImage.width * display_image_size)/origImage.height); + if (origImage.width > origImage.height) { + w = Math.round(origImage.width * display_image_size / origImage.height); h = Math.round(display_image_size); - x = - Math.round((w - h)/2); + x = -Math.round((w - h) / 2); y = 0; - } else { // Portrait image + } else { w = Math.round(display_image_size); - h = Math.round((origImage.height * display_image_size)/origImage.width); + h = Math.round(origImage.height * display_image_size / origImage.width); x = 0; - y = Math.round((w - h)/2); + y = Math.round((w - h) / 2); } - ctx.drawImage(origImage, x, y, w, h); // This just paints the image as is + ctx.drawImage(origImage, x, y, w, h); return roundImage.src = round_image_maker.toDataURL(); }; this.round_img_cache[url] = roundImage; } return roundImage; - } + }; - get_label_attributes(d) { - let max_line_length, width_default; - const text = d.pretty_name; - const label_measure = this.ctx.measureText(text); //this is total length of text (in ems?) - const browser_font_size = 12.8; // -- Setting or auto from browser? - const focused_font_size = this.label_em * browser_font_size * this.focused_mag; - const padding = focused_font_size * 0.5; - const line_height = focused_font_size * 1.25; // set line height to 125% - const max_len = 250; - const min_len = 100; - const label_length = label_measure.width + (2 * padding); - const num_lines_raw = label_length/max_len; - const num_lines = (Math.floor(num_lines_raw)) + 1; + Huviz.prototype.get_label_attributes = function(d) { + var browser_font_size, bubble_text, focused_font_size, font_size, height, i, label_length, label_measure, line_height, line_length, ln_i, max_len, max_line_length, min_len, new_line_length, new_line_width, num_lines, num_lines_raw, padding, real_line_length, text, text_cuts, text_split, width, width_default, word, word_length, _i, _len; + text = d.pretty_name; + label_measure = this.ctx.measureText(text); + browser_font_size = 12.8; + focused_font_size = this.label_em * browser_font_size * this.focused_mag; + padding = focused_font_size * 0.5; + line_height = focused_font_size * 1.25; + max_len = 250; + min_len = 100; + label_length = label_measure.width + 2 * padding; + num_lines_raw = label_length / max_len; + num_lines = (Math.floor(num_lines_raw)) + 1; if (num_lines > 1) { - width_default = (this.label_em * label_measure.width)/num_lines; + width_default = this.label_em * label_measure.width / num_lines; } else { width_default = max_len; } - const bubble_text = []; - const text_cuts = []; - let ln_i = 0; + bubble_text = []; + text_cuts = []; + ln_i = 0; bubble_text[ln_i] = ""; - if (label_length < (width_default + (2 * padding))) { // single line label + if (label_length < (width_default + 2 * padding)) { max_line_length = label_length - padding; - } else { // more than one line so calculate how many and create text lines array - const text_split = text.split(' '); // array of words + } else { + text_split = text.split(' '); max_line_length = 0; - for (let i = 0; i < text_split.length; i++) { - const word = text_split[i]; - const word_length = this.ctx.measureText(word); //Get length of next word - const line_length = this.ctx.measureText(bubble_text[ln_i]); //Get current line length - const new_line_length = word_length.width + line_length.width; //add together for testing - if (new_line_length < width_default) { //if line length is still less than max - bubble_text[ln_i] = bubble_text[ln_i] + word + " "; //add word to bubble_text - } else { //new line needed + for (i = _i = 0, _len = text_split.length; _i < _len; i = ++_i) { + word = text_split[i]; + word_length = this.ctx.measureText(word); + line_length = this.ctx.measureText(bubble_text[ln_i]); + new_line_length = word_length.width + line_length.width; + if (new_line_length < width_default) { + bubble_text[ln_i] = bubble_text[ln_i] + word + " "; + } else { text_cuts[ln_i] = i; - const real_line_length = this.ctx.measureText(bubble_text[ln_i]); - const new_line_width = real_line_length.width; - if (new_line_width > max_line_length) { // remember longest line lengthth + real_line_length = this.ctx.measureText(bubble_text[ln_i]); + new_line_width = real_line_length.width; + if (new_line_width > max_line_length) { max_line_length = real_line_length.width; } ln_i++; @@ -9259,30 +7870,18 @@ with Shelved, Discarded, Graphed and Hidden.`; } } } - const width = max_line_length + (2 * padding); //set actual width of box to longest line of text - const height = ((ln_i + 1) * line_height) + (2 * padding); // calculate height using wrapping text - const font_size = this.label_em; - //console.log text - //console.log "focused_font_size: " + focused_font_size - //console.log "line height: " + line_height - //console.log "padding: " + padding - //console.log "label_length: " + label_length - //console.log "bubble height: " + height - //console.log "max_line_length: " + max_line_length - //console.log "bubble width: " + width - //console.log "bubble cut points: " - //console.log text_cuts + width = max_line_length + 2 * padding; + height = (ln_i + 1) * line_height + 2 * padding; + font_size = this.label_em; return d.bub_txt = [width, height, line_height, text_cuts, font_size]; - } + }; - should_show_label(node) { - return (node.labelled || - node.focused_edge || - (this.label_graphed && (node.state === this.graphed_set)) || - dist_lt(this.last_mouse_pos, node, this.label_show_range) || - ((node.name != null) && node.name.match(this.search_regex))); // FIXME make this a flag that gets updated ONCE when the regex changes not something deep in loop!!! - } - draw_labels() { + Huviz.prototype.should_show_label = function(node) { + return node.labelled || node.focused_edge || (this.label_graphed && node.state === this.graphed_set) || dist_lt(this.last_mouse_pos, node, this.label_show_range) || ((node.name != null) && node.name.match(this.search_regex)); + }; + + Huviz.prototype.draw_labels = function() { + var focused_font, focused_font_size, focused_pill_font, label_node, unfocused_font; if (this.use_svg) { label.attr("style", function(d) { if (this.should_show_label(d)) { @@ -9293,86 +7892,138 @@ with Shelved, Discarded, Graphed and Hidden.`; }); } if (this.use_canvas || this.use_webgl) { - // http://stackoverflow.com/questions/3167928/drawing-rotated-text-on-a-html5-canvas - // http://diveintohtml5.info/canvas.html#text - // http://stackoverflow.com/a/10337796/1234699 - const focused_font_size = this.label_em * this.focused_mag; - const focused_font = `${focused_font_size}em sans-serif`; - const unfocused_font = `${this.label_em}em sans-serif`; - const focused_pill_font = `${this.label_em}em sans-serif`; - - const label_node = node => { - if (!this.should_show_label(node)) { return; } - const { - ctx - } = this; - ctx.textBaseline = "middle"; - // perhaps scrolling should happen here - //if not node_display_type and (node.focused_node or node.focused_edge?) - if (node.focused_node || (node.focused_edge != null)) { - const label = this.scroll_pretty_name(node); - ctx.fillStyle = node.color; - ctx.font = focused_font; - } else { - ctx.fillStyle = renderStyles.labelColor; //"white" is default - ctx.font = unfocused_font; - } - if ((node.fisheye == null)) { - return; - } - - let flip_point = this.cx; - if (this.discarded_set.has(node)) { - flip_point = this.discard_center[0]; - } else if (this.shelved_set.has(node)) { - flip_point = this.lariat_center[0]; - } - - if (!this.graphed_set.has(node) && this.draw_lariat_labels_rotated) { - // Flip label rather than write upside down - // var flip = (node.rad > Math.PI) ? -1 : 1; - // view-source:http://www.jasondavies.com/d3-dependencies/ - let radians = node.rad; - const flip = node.fisheye.x < flip_point; // @cx # flip labels on the left of center line - let textAlign = 'left'; - if (flip) { - radians = radians - Math.PI; - textAlign = 'right'; + focused_font_size = this.label_em * this.focused_mag; + focused_font = "" + focused_font_size + "em sans-serif"; + unfocused_font = "" + this.label_em + "em sans-serif"; + focused_pill_font = "" + this.label_em + "em sans-serif"; + label_node = (function(_this) { + return function(node) { + var adjust_x, adjust_y, alpha, ctx, cuts, fill, flip, flip_point, i, label, line_height, node_font_size, outline, pill_height, pill_width, print_label, radians, radius, result, text, textAlign, text_split, x, y, _i, _len; + if (!_this.should_show_label(node)) { + return; + } + ctx = _this.ctx; + ctx.textBaseline = "middle"; + if (node.focused_node || (node.focused_edge != null)) { + label = _this.scroll_pretty_name(node); + ctx.fillStyle = node.color; + ctx.font = focused_font; + } else { + ctx.fillStyle = renderStyles.labelColor; + ctx.font = unfocused_font; + } + if (node.fisheye == null) { + return; } - ctx.save(); - ctx.translate(node.fisheye.x, node.fisheye.y); - ctx.rotate((-1 * radians) + (Math.PI / 2)); - ctx.textAlign = textAlign; - if (this.debug_shelf_angles_and_flipping) { - if (flip) { //radians < 0 - ctx.fillStyle = 'rgb(255,0,0)'; + flip_point = _this.cx; + if (_this.discarded_set.has(node)) { + flip_point = _this.discard_center[0]; + } else if (_this.shelved_set.has(node)) { + flip_point = _this.lariat_center[0]; + } + if (!_this.graphed_set.has(node) && _this.draw_lariat_labels_rotated) { + radians = node.rad; + flip = node.fisheye.x < flip_point; + textAlign = 'left'; + if (flip) { + radians = radians - Math.PI; + textAlign = 'right'; + } + ctx.save(); + ctx.translate(node.fisheye.x, node.fisheye.y); + ctx.rotate(-1 * radians + Math.PI / 2); + ctx.textAlign = textAlign; + if (_this.debug_shelf_angles_and_flipping) { + if (flip) { + ctx.fillStyle = 'rgb(255,0,0)'; + } + ctx.fillText((" " + flip + " " + radians).substr(0, 14), 0, 0); + } else { + ctx.fillText(" " + node.pretty_name + " ", 0, 0); } - ctx.fillText((" " + flip + " " + radians).substr(0,14), 0, 0); + return ctx.restore(); } else { - ctx.fillText(" " + node.pretty_name + " ", 0, 0); + if (node_display_type === 'pills') { + node_font_size = node.bub_txt[4]; + result = node_font_size !== _this.label_em; + if (!node.bub_txt.length || result) { + _this.get_label_attributes(node); + } + line_height = node.bub_txt[2]; + adjust_x = node.bub_txt[0] / 2 - line_height / 2; + adjust_y = node.bub_txt[1] / 2 - line_height; + pill_width = node.bub_txt[0]; + pill_height = node.bub_txt[1]; + x = node.fisheye.x - pill_width / 2; + y = node.fisheye.y - pill_height / 2; + radius = 10 * _this.label_em; + alpha = 1; + outline = node.color; + if (node.focused_node || (node.focused_edge != null)) { + ctx.lineWidth = 2; + fill = "#f2f2f2"; + } else { + ctx.lineWidth = 1; + fill = "white"; + } + _this.rounded_rectangle(x, y, pill_width, pill_height, radius, fill, outline, alpha); + ctx.fillStyle = "#000"; + text = node.pretty_name; + text_split = text.split(' '); + cuts = node.bub_txt[3]; + print_label = ""; + for (i = _i = 0, _len = text_split.length; _i < _len; i = ++_i) { + text = text_split[i]; + if (cuts && __indexOf.call(cuts, i) >= 0) { + ctx.fillText(print_label.slice(0, -1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); + adjust_y = adjust_y - line_height; + print_label = text + " "; + } else { + print_label = print_label + text + " "; + } + } + if (print_label) { + return ctx.fillText(print_label.slice(0, -1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); + } + } else { + return ctx.fillText(" " + node.pretty_name + " ", node.fisheye.x, node.fisheye.y); + } } - return ctx.restore(); - } else { - let x, y; + }; + })(this); + this.graphed_set.forEach(label_node); + this.shelved_set.forEach(label_node); + return this.discarded_set.forEach(label_node); + } + }; + + Huviz.prototype.draw_focused_labels = function() { + var ctx, focused_font, focused_font_size, focused_pill_font, highlight_node; + ctx = this.ctx; + focused_font_size = this.label_em * this.focused_mag; + focused_font = "" + focused_font_size + "em sans-serif"; + focused_pill_font = "" + this.label_em + "em sans-serif"; + highlight_node = (function(_this) { + return function(node) { + var adjust_x, adjust_y, alpha, cart_label, cuts, fill, i, label, line_height, node_font_size, outline, pill_height, pill_width, print_label, radius, result, text, text_split, x, y, _i, _len; + if (node.focused_node || (node.focused_edge != null)) { if (node_display_type === 'pills') { - let fill; - const node_font_size = node.bub_txt[4]; - const result = node_font_size !== this.label_em; + ctx.font = focused_pill_font; + node_font_size = node.bub_txt[4]; + result = node_font_size !== _this.label_em; if (!node.bub_txt.length || result) { - this.get_label_attributes(node); + _this.get_label_attributes(node); } - const line_height = node.bub_txt[2]; // Line height calculated from text size ? - const adjust_x = (node.bub_txt[0] / 2) - (line_height/2);// Location of first line of text - let adjust_y = (node.bub_txt[1] / 2) - line_height; - const pill_width = node.bub_txt[0]; // box size - const pill_height = node.bub_txt[1]; - - x = node.fisheye.x - (pill_width/2); - y = node.fisheye.y - (pill_height/2); - const radius = 10 * this.label_em; - const alpha = 1; - const outline = node.color; - // change box edge thickness and fill if node selected + line_height = node.bub_txt[2]; + adjust_x = node.bub_txt[0] / 2 - line_height / 2; + adjust_y = node.bub_txt[1] / 2 - line_height; + pill_width = node.bub_txt[0]; + pill_height = node.bub_txt[1]; + x = node.fisheye.x - pill_width / 2; + y = node.fisheye.y - pill_height / 2; + radius = 10 * _this.label_em; + alpha = 1; + outline = node.color; if (node.focused_node || (node.focused_edge != null)) { ctx.lineWidth = 2; fill = "#f2f2f2"; @@ -9380,184 +8031,104 @@ with Shelved, Discarded, Graphed and Hidden.`; ctx.lineWidth = 1; fill = "white"; } - this.rounded_rectangle(x, y, pill_width, pill_height, radius, fill, outline, alpha); + _this.rounded_rectangle(x, y, pill_width, pill_height, radius, fill, outline, alpha); ctx.fillStyle = "#000"; - // Paint multi-line text - let text = node.pretty_name; - const text_split = text.split(' '); // array of words - const cuts = node.bub_txt[3]; - let print_label = ""; - for (let i = 0; i < text_split.length; i++) { + text = node.pretty_name; + text_split = text.split(' '); + cuts = node.bub_txt[3]; + print_label = ""; + for (i = _i = 0, _len = text_split.length; _i < _len; i = ++_i) { text = text_split[i]; - if (cuts && Array.from(cuts).includes(i)) { - ctx.fillText(print_label.slice(0,-1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); + if (cuts && __indexOf.call(cuts, i) >= 0) { + ctx.fillText(print_label.slice(0, -1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); adjust_y = adjust_y - line_height; print_label = text + " "; } else { print_label = print_label + text + " "; } } - if (print_label) { // print last line, or single line if no cuts - return ctx.fillText(print_label.slice(0,-1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); + if (print_label) { + return ctx.fillText(print_label.slice(0, -1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); } } else { + label = _this.scroll_pretty_name(node); + if (node.state.id === "graphed") { + cart_label = node.pretty_name; + ctx.measureText(cart_label).width; + if (_this.paint_label_dropshadows) { + _this.paint_dropshadow(cart_label, focused_font_size, node.fisheye.x, node.fisheye.y); + } + } + ctx.fillStyle = node.color; + ctx.font = focused_font; return ctx.fillText(" " + node.pretty_name + " ", node.fisheye.x, node.fisheye.y); } } }; - - this.graphed_set.forEach(label_node); - this.shelved_set.forEach(label_node); - return this.discarded_set.forEach(label_node); - } - } - - draw_focused_labels() { - const { - ctx - } = this; - const focused_font_size = this.label_em * this.focused_mag; - const focused_font = `${focused_font_size}em sans-serif`; - const focused_pill_font = `${this.label_em}em sans-serif`; - const highlight_node = node => { - if (node.focused_node || (node.focused_edge != null)) { - let x, y; - if (node_display_type === 'pills') { - let fill; - ctx.font = focused_pill_font; - const node_font_size = node.bub_txt[4]; - const result = node_font_size !== this.label_em; - if (!node.bub_txt.length || result) { - this.get_label_attributes(node); - } - const line_height = node.bub_txt[2]; // Line height calculated from text size ? - const adjust_x = (node.bub_txt[0] / 2) - (line_height/2);// Location of first line of text - let adjust_y = (node.bub_txt[1] / 2) - line_height; - const pill_width = node.bub_txt[0]; // box size - const pill_height = node.bub_txt[1]; - - x = node.fisheye.x - (pill_width/2); - y = node.fisheye.y - (pill_height/2); - const radius = 10 * this.label_em; - const alpha = 1; - const outline = node.color; - // change box edge thickness and fill if node selected - if (node.focused_node || (node.focused_edge != null)) { - ctx.lineWidth = 2; - fill = "#f2f2f2"; - } else { - ctx.lineWidth = 1; - fill = "white"; - } - this.rounded_rectangle(x, y, pill_width, pill_height, radius, fill, outline, alpha); - ctx.fillStyle = "#000"; - // Paint multi-line text - let text = node.pretty_name; - const text_split = text.split(' '); // array of words - const cuts = node.bub_txt[3]; - let print_label = ""; - for (let i = 0; i < text_split.length; i++) { - text = text_split[i]; - if (cuts && Array.from(cuts).includes(i)) { - ctx.fillText(print_label.slice(0,-1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); - adjust_y = adjust_y - line_height; - print_label = text + " "; - } else { - print_label = print_label + text + " "; - } - } - if (print_label) { // print last line, or single line if no cuts - return ctx.fillText(print_label.slice(0,-1), node.fisheye.x - adjust_x, node.fisheye.y - adjust_y); - } - } else { - const label = this.scroll_pretty_name(node); - if (node.state.id === "graphed") { - const cart_label = node.pretty_name; - ctx.measureText(cart_label).width; //forces proper label measurement (?) - if (this.paint_label_dropshadows) { - this.paint_dropshadow(cart_label, focused_font_size, node.fisheye.x, node.fisheye.y); - } - } - ctx.fillStyle = node.color; // This is the mouseover highlight color when GRAPHED - ctx.font = focused_font; - return ctx.fillText(" " + node.pretty_name + " ", node.fisheye.x, node.fisheye.y); - } - } - }; + })(this); return this.graphed_set.forEach(highlight_node); - } + }; - clear_canvas() { + Huviz.prototype.clear_canvas = function() { return this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height); - } - blank_screen() { - if (this.use_canvas || this.use_webgl) { return this.clear_canvas(); } - } + }; + + Huviz.prototype.blank_screen = function() { + if (this.use_canvas || this.use_webgl) { + return this.clear_canvas(); + } + }; - should_position_by_packing() { + Huviz.prototype.should_position_by_packing = function() { return !this.show_edges; - } + }; - position_nodes_by_packing() { - // https://bl.ocks.org/mbostock/3231298 + Huviz.prototype.position_nodes_by_packing = function() { + var i, n, q, _results; if (!this.should_position_by_packing()) { return; } - const q = d3.geom.quadtree(this.graphed_set); - let i = 0; - const n = this.graphed_set.length; - return (() => { - const result = []; - while (++i < n) { - result.push(q.visit(this.position_node_by_packing(this.graphed_set[i]))); - } - return result; - })(); - } + q = d3.geom.quadtree(this.graphed_set); + i = 0; + n = this.graphed_set.length; + _results = []; + while (++i < n) { + _results.push(q.visit(this.position_node_by_packing(this.graphed_set[i]))); + } + return _results; + }; - position_node_by_packing(node) { - let r = node.radius + 16; - const nx1 = node.x - r; - const nx2 = node.x + r; - const ny1 = node.y - r; - const ny2 = node.y + r; + Huviz.prototype.position_node_by_packing = function(node) { + var nx1, nx2, ny1, ny2, r; + r = node.radius + 16; + nx1 = node.x - r; + nx2 = node.x + r; + ny1 = node.y - r; + ny2 = node.y + r; return function(quad, x1, y1, x2, y2) { + var l, x, y; if (quad.point && (quad.point !== node)) { - let x = node.x - quad.point.x; - let y = node.y - quad.point.y; - let l = Math.sqrt((x * x) + (y * y)); + x = node.x - quad.point.x; + y = node.y - quad.point.y; + l = Math.sqrt(x * x + y * y); r = node.radius + quad.point.radius; if (l < r) { - l = ((l(-r)) / 1) * .5; - node.x -= (x *= l); - node.y -= (y *= l); + l = (l(-r)) / 1 * .5; + node.x -= x *= l; + node.y -= y *= l; quad.point.x += x; quad.point.y += y; } } - return (x1 > nx2) || (x2 < nx1) || (y1 > ny2) || (y2 < ny1); + return x1 > nx2 || x2 < nx1 || y1 > ny2 || y2 < ny1; }; - } + }; - // # The distinguished node - // There are phenomena which pertain to one and only one node: the distinguished_node. - // There may be only one. There does not have to be one though. - // - // Which nodes might be distinguished? - // - // * If there is only one node in the chosen_set it becomes the distinguished_node - // * Being the terminal node in the walked_set is another way to become distinguished. - // - // What are the consequences of being distinguished? - // - // * the distinguished node is displayed pinned at the center of the graph - // - // To see to it that there is no distinguished node, call `@distinguish(null)` - administer_the_distinguished_node() { - let terminal_walked; - const dirty = false; - let only_chosen = null; - let rightfully_distinguished = null; + Huviz.prototype.administer_the_distinguished_node = function() { + var dirty, emeritus, only_chosen, rightfully_distinguished, terminal_walked; + dirty = false; + only_chosen = null; + rightfully_distinguished = null; if (this.chosen_set.length === 1) { only_chosen = this.chosen_set[0]; } @@ -9567,38 +8138,40 @@ with Shelved, Discarded, Graphed and Hidden.`; rightfully_distinguished = terminal_walked || only_chosen; if (rightfully_distinguished != null) { if (rightfully_distinguished._is_distinguished != null) { - // no change is needed so we can quit now return; } if (this.center_the_distinguished_node) { this.pin_at_center(rightfully_distinguished); } } - const emeritus = this.distinguish(rightfully_distinguished); + emeritus = this.distinguish(rightfully_distinguished); if (emeritus != null) { if (this.center_the_distinguished_node) { this.unpin(emeritus); } } if (emeritus || rightfully_distinguished) { - // there was a change, so update set counts return this.update_set_counts(); } - } + }; - tick(msg) { - if ((this.ctx == null)) { + Huviz.prototype.tick = function(msg) { + var _base, _base1; + if (this.ctx == null) { return; } - if ((typeof msg === 'string') && !this.args.skip_log_tick) { + if (typeof msg === 'string' && !this.args.skip_log_tick) { console.log(msg); } - // return if @focused_node # <== policy: freeze screen when selected if (true) { if (this.clean_up_all_dirt_onceRunner != null) { if (this.clean_up_all_dirt_onceRunner.active) { - if (this.clean_up_all_dirt_onceRunner.stats.runTick == null) { this.clean_up_all_dirt_onceRunner.stats.runTick = 0; } - if (this.clean_up_all_dirt_onceRunner.stats.skipTick == null) { this.clean_up_all_dirt_onceRunner.stats.skipTick = 0; } + if ((_base = this.clean_up_all_dirt_onceRunner.stats).runTick == null) { + _base.runTick = 0; + } + if ((_base1 = this.clean_up_all_dirt_onceRunner.stats).skipTick == null) { + _base1.skipTick = 0; + } this.clean_up_all_dirt_onceRunner.stats.skipTick++; return; } else { @@ -9607,13 +8180,11 @@ with Shelved, Discarded, Graphed and Hidden.`; } } this.highwater('maxtick', true); - this.ctx.lineWidth = this.edge_width; // TODO(smurp) just edges should get this treatment + this.ctx.lineWidth = this.edge_width; this.administer_the_distinguished_node(); this.find_node_or_edge_closest_to_pointer(); - //@WIP_find_node_or_edge_closest_to_pointer_using_quadtrees() this.auto_change_verb(); this.on_tick_change_current_command_if_warranted(); - //@update_snippet() // not in use this.blank_screen(); this.draw_dropzones(); this.fisheye.focus(this.last_mouse_pos); @@ -9634,22 +8205,20 @@ with Shelved, Discarded, Graphed and Hidden.`; this.pfm_count('tick'); this.prior_node_and_state = this.get_focused_node_and_its_state(); this.highwater('maxtick'); - } + }; - rounded_rectangle(x, y, w, h, radius, fill, stroke, alpha) { - // http://stackoverflow.com/questions/1255512/how-to-draw-a-rounded-rectangle-on-html-canvas - const { - ctx - } = this; + Huviz.prototype.rounded_rectangle = function(x, y, w, h, radius, fill, stroke, alpha) { + var b, ctx, r; + ctx = this.ctx; ctx.fillStyle = fill; - const r = x + w; - const b = y + h; + r = x + w; + b = y + h; ctx.save(); ctx.beginPath(); ctx.moveTo(x + radius, y); ctx.lineTo(r - radius, y); ctx.quadraticCurveTo(r, y, r, y + radius); - ctx.lineTo(r, (y + h) - radius); + ctx.lineTo(r, y + h - radius); ctx.quadraticCurveTo(r, b, r - radius, b); ctx.lineTo(x + radius, b); ctx.quadraticCurveTo(x, b, x, b - radius); @@ -9665,22 +8234,22 @@ with Shelved, Discarded, Graphed and Hidden.`; ctx.strokeStyle = stroke; return ctx.stroke(); } - } + }; - paint_dropshadow(label, focused_font_size, x, y) { - const { - ctx - } = this; - const width = this.ctx.measureText(label).width * focused_font_size; - const focused_font = `${focused_font_size}em sans-serif`; - const height = this.label_em * this.focused_mag * 16; + Huviz.prototype.paint_dropshadow = function(label, focused_font_size, x, y) { + var ctx, focused_font, height, width; + ctx = this.ctx; + width = this.ctx.measureText(label).width * focused_font_size; + focused_font = "" + focused_font_size + "em sans-serif"; + height = this.label_em * this.focused_mag * 16; ctx.font = focused_font; ctx.strokeStyle = renderStyles.pageBg; ctx.lineWidth = 5; return ctx.strokeText(" " + label + " ", x, y); - } + }; - draw_edge_labels() { + Huviz.prototype.draw_edge_labels = function() { + var edge, _i, _len, _ref, _results; if (!this.show_edges) { return; } @@ -9688,55 +8257,51 @@ with Shelved, Discarded, Graphed and Hidden.`; this.draw_edge_label(this.focused_edge); } if (this.show_edge_labels_adjacent_to_labelled_nodes) { - return (() => { - const result = []; - for (let edge of Array.from(this.links_set)) { - if (edge.target.labelled || edge.source.labelled) { - result.push(this.draw_edge_label(edge)); - } else { - result.push(undefined); - } + _ref = this.links_set; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + edge = _ref[_i]; + if (edge.target.labelled || edge.source.labelled) { + _results.push(this.draw_edge_label(edge)); + } else { + _results.push(void 0); } - return result; - })(); + } + return _results; } - } + }; - draw_edge_label(edge) { - const { - ctx - } = this; - // TODO the edge label should really come from the pretty name of the predicate - // edge.label > edge.predicate.label > edge.predicate.lid - let label = edge.label || edge.predicate.lid; + Huviz.prototype.draw_edge_label = function(edge) { + var ctx, height, label, width; + ctx = this.ctx; + label = edge.label || edge.predicate.lid; if (this.snippet_count_on_edge_labels) { if (edge.contexts != null) { if (edge.contexts.length) { - label += ` (${edge.contexts.length})`; + label += " (" + edge.contexts.length + ")"; } } } - const { - width - } = ctx.measureText(label); - const height = this.label_em * this.focused_mag * 16; + width = ctx.measureText(label).width; + height = this.label_em * this.focused_mag * 16; if (this.paint_label_dropshadows) { if (edge.handle != null) { this.paint_dropshadow(label, this.label_em, edge.handle.x, edge.handle.y); } } - //ctx.fillStyle = '#666' #@shadow_color - //ctx.fillText " " + label, edge.handle.x + @edge_x_offset + @shadow_offset, edge.handle.y + @shadow_offset ctx.fillStyle = edge.color; return ctx.fillText(" " + label, edge.handle.x + this.edge_x_offset, edge.handle.y); - } + }; - update_snippet() { - if (this.show_snippets_constantly && (this.focused_edge != null) && (this.focused_edge !== this.printed_edge)) { + Huviz.prototype.update_snippet = function() { + if (this.show_snippets_constantly && (this.focused_edge != null) && this.focused_edge !== this.printed_edge) { return this.print_edge(this.focused_edge); } - } - show_state_msg(txt) { + }; + + Huviz.prototype.msg_history = ""; + + Huviz.prototype.show_state_msg = function(txt) { if (false) { this.msg_history += " " + txt; txt = this.msg_history; @@ -9745,130 +8310,137 @@ with Shelved, Discarded, Graphed and Hidden.`; this.state_msg_box.html("
    " + txt + "
    "); this.state_msg_box.on('click', this.hide_state_msg); return this.text_cursor.pause("wait"); - } + }; - hide_state_msg() { + Huviz.prototype.hide_state_msg = function() { this.state_msg_box.hide(); - return this.text_cursor.continue(); - } - //@text_cursor.set_cursor("default") + return this.text_cursor["continue"](); + }; - svg_restart() { - // console.log "svg_restart()" + Huviz.prototype.svg_restart = function() { + var nodeEnter; this.link = this.link.data(this.links_set); - this.link.enter(). - insert("line", ".node"). - attr("class", d => //console.log(l.geometry.vertices[0].x,l.geometry.vertices[1].x); - "link"); - + this.link.enter().insert("line", ".node").attr("class", function(d) { + return "link"; + }); this.link.exit().remove(); this.node = this.node.data(this.nodes); - this.node.exit().remove(); - - const nodeEnter = this.node.enter(). - append("g"). - attr("class", "lariat node"). - call(force.drag); - nodeEnter.append("circle"). - attr("r", calc_node_radius). - style("fill", d => d.color); - - nodeEnter.append("text"). - attr("class", "label"). - attr("style", ""). - attr("dy", ".35em"). - attr("dx", ".4em"). - text(d => d.name); - + nodeEnter = this.node.enter().append("g").attr("class", "lariat node").call(force.drag); + nodeEnter.append("circle").attr("r", calc_node_radius).style("fill", function(d) { + return d.color; + }); + nodeEnter.append("text").attr("class", "label").attr("style", "").attr("dy", ".35em").attr("dx", ".4em").text(function(d) { + return d.name; + }); return this.label = this.svg.selectAll(".label"); - } + }; - canvas_show_text(txt, x, y) { - // console.log "canvas_show_text(" + txt + ")" + Huviz.prototype.canvas_show_text = function(txt, x, y) { this.ctx.fillStyle = "black"; this.ctx.font = "12px Courier"; return this.ctx.fillText(txt, x, y); - } - pnt2str(x, y) { + }; + + Huviz.prototype.pnt2str = function(x, y) { return "[" + Math.floor(x) + ", " + Math.floor(y) + "]"; - } - show_pos(x, y, dx, dy) { + }; + + Huviz.prototype.show_pos = function(x, y, dx, dy) { dx = dx || 0; dy = dy || 0; return this.canvas_show_text(pnt2str(x, y), x + dx, y + dy); - } - show_line(x0, y0, x1, y1, dx, dy, label) { + }; + + Huviz.prototype.show_line = function(x0, y0, x1, y1, dx, dy, label) { dx = dx || 0; dy = dy || 0; - label = ((typeof label === "undefined") && "") || label; + label = typeof label === "undefined" && "" || label; return this.canvas_show_text(pnt2str(x0, y0) + "-->" + pnt2str(x0, y0) + " " + label, x1 + dx, y1 + dy); - } - add_webgl_line(e) { + }; + + Huviz.prototype.add_webgl_line = function(e) { return e.gl = this.add_line(scene, e.source.x, e.source.y, e.target.x, e.target.y, e.source.s.id + " - " + e.target.s.id, "green"); - } + }; - //dump_line(e.gl); - webgl_restart() { - return links_set.forEach(d => { - return this.add_webgl_line(d); - }); - } - restart() { - if (this.use_svg) { this.svg_restart(); } + Huviz.prototype.webgl_restart = function() { + return links_set.forEach((function(_this) { + return function(d) { + return _this.add_webgl_line(d); + }; + })(this)); + }; + + Huviz.prototype.restart = function() { + if (this.use_svg) { + this.svg_restart(); + } this.force.start(); if (!this.args.skip_log_tick) { return console.log("Tick in @force.start() restart"); } - } - show_last_mouse_pos() { + }; + + Huviz.prototype.show_last_mouse_pos = function() { return this.draw_circle(this.last_mouse_pos[0], this.last_mouse_pos[1], this.focus_radius, "yellow"); - } - remove_ghosts(e) { + }; + + Huviz.prototype.remove_ghosts = function(e) { if (this.use_webgl) { - if (e.gl) { this.remove_gl_obj(e.gl); } + if (e.gl) { + this.remove_gl_obj(e.gl); + } return delete e.gl; } - } - add_node_ghosts(d) { - if (this.use_webgl) { return d.gl = add_node(scene, d.x, d.y, 3, d.color); } - } + }; + + Huviz.prototype.add_node_ghosts = function(d) { + if (this.use_webgl) { + return d.gl = add_node(scene, d.x, d.y, 3, d.color); + } + }; - add_to(itm, array, cmp) { - // FIXME should these arrays be SortedSets instead? + Huviz.prototype.add_to = function(itm, array, cmp) { + var c; cmp = cmp || array.__current_sort_order || this.cmp_on_id; - const c = this.binary_search_on(array, itm, cmp, true); - if (typeof c === typeof 3) { return c; } + c = this.binary_search_on(array, itm, cmp, true); + if (typeof c === typeof 3) { + return c; + } array.splice(c.idx, 0, itm); return c.idx; - } + }; - remove_from(itm, array, cmp) { + Huviz.prototype.remove_from = function(itm, array, cmp) { + var c; cmp = cmp || array.__current_sort_order || this.cmp_on_id; - const c = this.binary_search_on(array, itm, cmp); - if (c > -1) { array.splice(c, 1); } + c = this.binary_search_on(array, itm, cmp); + if (c > -1) { + array.splice(c, 1); + } return array; - } + }; - fire_newsubject_event(s) { - return window.dispatchEvent( - new CustomEvent('newsubject', { - detail: { - sid: s - }, - // time: new Date() - bubbles: true, - cancelable: true - }) - ); - } + Huviz.prototype.my_graph = { + subjects: {}, + predicates: {}, + objects: {} + }; + + Huviz.prototype.fire_newsubject_event = function(s) { + return window.dispatchEvent(new CustomEvent('newsubject', { + detail: { + sid: s + }, + bubbles: true, + cancelable: true + })); + }; - ensure_predicate_lineage(pid) { - // Ensure that fire_newpredicate_event is run for pid all the way back - // to its earliest (possibly abstract) parent starting with the earliest - const pred_lid = uniquer(pid); - if ((this.my_graph.predicates[pred_lid] == null)) { - let parent_lid, pred_name; + Huviz.prototype.ensure_predicate_lineage = function(pid) { + var parent_lid, pred_lid, pred_name; + pred_lid = uniquer(pid); + if (this.my_graph.predicates[pred_lid] == null) { if (this.ontology.subPropertyOf[pred_lid] != null) { parent_lid = this.ontology.subPropertyOf[pred_lid]; } else { @@ -9881,173 +8453,200 @@ with Shelved, Discarded, Graphed and Hidden.`; } return this.fire_newpredicate_event(pid, pred_lid, parent_lid, pred_name); } - } + }; - fire_newpredicate_event(pred_uri, pred_lid, parent_lid, pred_name) { - return window.dispatchEvent( - new CustomEvent('newpredicate', { - detail: { - pred_uri, - pred_lid, - parent_lid, - pred_name - }, - bubbles: true, - cancelable: true - }) - ); - } + Huviz.prototype.fire_newpredicate_event = function(pred_uri, pred_lid, parent_lid, pred_name) { + return window.dispatchEvent(new CustomEvent('newpredicate', { + detail: { + pred_uri: pred_uri, + pred_lid: pred_lid, + parent_lid: parent_lid, + pred_name: pred_name + }, + bubbles: true, + cancelable: true + })); + }; - auto_discover_header(uri, digestHeaders, sendHeaders) { - // THIS IS A FAILED EXPERIMENT BECAUSE - // It turns out that for security reasons AJAX requests cannot show - // the headers of redirect responses. So, though it is a fine ambition - // to retrieve the X-PrefLabel it cannot be seen because the 303 redirect - // it is attached to is processed automatically by the browser and we - // find ourselves looking at the final response. + Huviz.prototype.auto_discover_header = function(uri, digestHeaders, sendHeaders) { return $.ajax({ type: 'GET', url: uri, - beforeSend(xhr) { - //console.log(xhr) - return Array.from(sendHeaders).map((pair) => - //xhr.setRequestHeader('X-Test-Header', 'test-value') - xhr.setRequestHeader(pair[0], pair[1])); + beforeSend: function(xhr) { + var pair, _i, _len, _results; + _results = []; + for (_i = 0, _len = sendHeaders.length; _i < _len; _i++) { + pair = sendHeaders[_i]; + _results.push(xhr.setRequestHeader(pair[0], pair[1])); + } + return _results; }, - //xhr.setRequestHeader('Accept', "text/n-triples, text/x-turtle, */*") - //headers: - // Accept: "text/n-triples, text/x-turtle, */*" - success: (data, textStatus, request) => { - console.log(textStatus); - console.log(request.getAllResponseHeaders()); - console.table((Array.from(request.getAllResponseHeaders().split("\n")).map((line) => line.split(':')))); - return (() => { - const result = []; - for (let header of Array.from(digestHeaders)) { - const val = request.getResponseHeader(header); + success: (function(_this) { + return function(data, textStatus, request) { + var header, line, val, _i, _len, _results; + console.log(textStatus); + console.log(request.getAllResponseHeaders()); + console.table((function() { + var _i, _len, _ref, _results; + _ref = request.getAllResponseHeaders().split("\n"); + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + line = _ref[_i]; + _results.push(line.split(':')); + } + return _results; + })()); + _results = []; + for (_i = 0, _len = digestHeaders.length; _i < _len; _i++) { + header = digestHeaders[_i]; + val = request.getResponseHeader(header); if (val != null) { - result.push(alert(val)); + _results.push(alert(val)); } else { - result.push(undefined); + _results.push(void 0); } } - return result; - })(); - } + return _results; + }; + })(this) }); - } + }; - getTesterAndMunger(discoArgs) { - const fallbackQuadTester = q => (q != null); - const fallbackQuadMunter = q => [q]; - const quadTester = discoArgs.quadTester || fallbackQuadTester; - const quadMunger = discoArgs.quadMunger || fallbackQuadMunger; - return {quadTester, quadMunger}; - } + Huviz.prototype.getTesterAndMunger = function(discoArgs) { + var fallbackQuadMunter, fallbackQuadTester, quadMunger, quadTester; + fallbackQuadTester = (function(_this) { + return function(q) { + return q != null; + }; + })(this); + fallbackQuadMunter = (function(_this) { + return function(q) { + return [q]; + }; + })(this); + quadTester = discoArgs.quadTester || fallbackQuadTester; + quadMunger = discoArgs.quadMunger || fallbackQuadMunger; + return { + quadTester: quadTester, + quadMunger: quadMunger + }; + }; - discovery_triple_ingestor_N3(data, textStatus, request, discoArgs) { - // Purpose: - // THIS IS NOT YET IN USE. THIS IS FOR WHEN WE SWITCH OVER TO N3 - // - // This is the XHR callback returned by @make_triple_ingestor() - // The assumption is that data will be something N3 can parse. - // Accepts: - // discoArgs: - // quadTester (OPTIONAL) - // returns true if the quad is to be added - // quadMunger (OPTIONAL) - // returns an array of one or more quads inspired by each quad - if (discoArgs == null) { discoArgs = {}; } - const {quadTester, quadMunger} = this.getTesterAndMunger(discoArgs); - const quad_count = 0; - const parser = N3.Parser(); - return parser.parse(data, (err, quad, pref) => { - if (err && (discoArgs.onErr != null)) { - discoArgs.onErr(err); - } - if (quadTester(quad)) { - return Array.from(quadMunger(quad)).map((aQuad) => - this.inject_discovered_quad_for(quad, discoArgs.aUrl)); - } - }); - } + Huviz.prototype.discovery_triple_ingestor_N3 = function(data, textStatus, request, discoArgs) { + var parser, quadMunger, quadTester, quad_count, _ref; + if (discoArgs == null) { + discoArgs = {}; + } + _ref = this.getTesterAndMunger(discoArgs), quadTester = _ref.quadTester, quadMunger = _ref.quadMunger; + quad_count = 0; + parser = N3.Parser(); + return parser.parse(data, (function(_this) { + return function(err, quad, pref) { + var aQuad, _i, _len, _ref1, _results; + if (err && (discoArgs.onErr != null)) { + discoArgs.onErr(err); + } + if (quadTester(quad)) { + _ref1 = quadMunger(quad); + _results = []; + for (_i = 0, _len = _ref1.length; _i < _len; _i++) { + aQuad = _ref1[_i]; + _results.push(_this.inject_discovered_quad_for(quad, discoArgs.aUrl)); + } + return _results; + } + }; + })(this)); + }; - discovery_triple_ingestor_GreenTurtle(data, textStatus, request, discoArgs) { - // Purpose: - // This is the XHR callback returned by @make_triple_ingestor() - // The assumption is that data will be something N3 can parse. - // Accepts: - // discoArgs: - // quadTester (OPTIONAL) - // returns true if the quad is to be added - // quadMunger (OPTIONAL) - // returns an array of one or more quads inspired by each quad - if (discoArgs == null) { discoArgs = {}; } - const { - graphUri - } = discoArgs; - const {quadTester, quadMunger} = this.getTesterAndMunger(discoArgs); - const dataset = new GreenerTurtle().parse(data, "text/turtle"); - for (let subj_uri in dataset.subjects) { - const frame = dataset.subjects[subj_uri]; - for (let pred_id in frame.predicates) { - const pred = frame.predicates[pred_id]; - for (let obj of Array.from(pred.objects)) { - const quad = { + Huviz.prototype.discovery_triple_ingestor_GreenTurtle = function(data, textStatus, request, discoArgs) { + var aQuad, dataset, frame, graphUri, obj, pred, pred_id, quad, quadMunger, quadTester, subj_uri, _i, _j, _len, _len1, _ref, _ref1, _ref2, _ref3, _ref4; + if (discoArgs == null) { + discoArgs = {}; + } + graphUri = discoArgs.graphUri; + _ref = this.getTesterAndMunger(discoArgs), quadTester = _ref.quadTester, quadMunger = _ref.quadMunger; + dataset = new GreenerTurtle().parse(data, "text/turtle"); + _ref1 = dataset.subjects; + for (subj_uri in _ref1) { + frame = _ref1[subj_uri]; + _ref2 = frame.predicates; + for (pred_id in _ref2) { + pred = _ref2[pred_id]; + _ref3 = pred.objects; + for (_i = 0, _len = _ref3.length; _i < _len; _i++) { + obj = _ref3[_i]; + quad = { s: frame.id, p: pred.id, - o: obj, // keys: type,value[,language] + o: obj, g: graphUri }; if (quadTester(quad)) { - for (let aQuad of Array.from(quadMunger(quad))) { + _ref4 = quadMunger(quad); + for (_j = 0, _len1 = _ref4.length; _j < _len1; _j++) { + aQuad = _ref4[_j]; this.inject_discovered_quad_for(aQuad, discoArgs.aUrl); } } } } } - } + }; - make_triple_ingestor(discoArgs) { - return (data, textStatus, request) => { - return this.discovery_triple_ingestor_GreenTurtle(data, textStatus, request, discoArgs); - }; - } + Huviz.prototype.make_triple_ingestor = function(discoArgs) { + return (function(_this) { + return function(data, textStatus, request) { + return _this.discovery_triple_ingestor_GreenTurtle(data, textStatus, request, discoArgs); + }; + })(this); + }; - discover_labels(aUrl) { - const discoArgs = { - aUrl, - quadTester: quad => { - if (quad.s !== aUrl.toString()) { - return false; - } - if (!(Array.from(NAME_SYNS).includes(quad.p))) { - return false; - } - return true; - }, - quadMunger: quad => { - return [quad]; - }, + Huviz.prototype.discover_labels = function(aUrl) { + var discoArgs; + discoArgs = { + aUrl: aUrl, + quadTester: (function(_this) { + return function(quad) { + var _ref; + if (quad.s !== aUrl.toString()) { + return false; + } + if (!(_ref = quad.p, __indexOf.call(NAME_SYNS, _ref) >= 0)) { + return false; + } + return true; + }; + })(this), + quadMunger: (function(_this) { + return function(quad) { + return [quad]; + }; + })(this), graphUri: aUrl.origin }; return this.make_triple_ingestor(discoArgs); - } + }; - ingest_quads_from(uri, success, failure) { + Huviz.prototype.ingest_quads_from = function(uri, success, failure) { return $.ajax({ type: 'GET', url: uri, - success, - failure + success: success, + failure: failure }); - } + }; - adjust_setting(input_or_id, new_value, old_value, skip_custom_handler) { - // NOTE that old_value is only being provided by adjust_setting_if_needed() - let input = null; - let setting_id = null; + Huviz.prototype.discover_geoname_name_msgs_threshold_ms = 5 * 1000; + + Huviz.prototype.discover_geoname_name_instructions = "Be sure to\n 1) create a\n new account\n 2) validate your email\n 3) on\n manage account\n press\n click here to enable\n 4) re-enter your GeoNames Username in HuViz settings to trigger lookup"; + + Huviz.prototype.discover_geoname_name_instructions_md = "## How to get GeoNames lookup working\n\n[GeoNames](http://www.geonames.org) is a very popular service experiencing much load.\nTo protect their servers they require a username to be able to perform lookup.\nThe hourly limit is 1000 and the daily limit is 30000 per username.\n\nYou may use the `huviz` username if you are going to perform just a couple of lookups.\nIf you are going to do lots of GeoNames lookups you should set up your own account.\nHere is how:\n\n1. create a new account if you don't have one\n2. validate your email (if you haven't already)\n3. on the manage account page\n press Click here to enable\n if your account is not already _enabled to use the free web services_\n4. enter your *GeoNames Username* in HuViz `Settings` tab then press the TAB or ENTER key to trigger lookup\n5. if you need to perform more lookups, just adjust the *GeoNames Limit*, then leave that field with TAB, ENTER or a click\n\n(Soon, HuViz will let you save your personal *GeoNames Username* and your *GeoNames Limit* to make this more convenient.)\n"; + + Huviz.prototype.adjust_setting = function(input_or_id, new_value, old_value, skip_custom_handler) { + var input, setting_id, theType; + input = null; + setting_id = null; if (typeof input_or_id === 'string') { input = this.get_setting_input_JQElem(input_or_id); setting_id = input_or_id; @@ -10055,9 +8654,8 @@ with Shelved, Discarded, Graphed and Hidden.`; input = input_or_id; setting_id = input[0].name; } - const theType = input.attr('type'); - if (['checkbox', 'radiobutton'].includes(theType)) { - //new_value = new_value and 'checked' or null + theType = input.attr('type'); + if (theType === 'checkbox' || theType === 'radiobutton') { input.prop('checked', new_value); } else { input.val(new_value); @@ -10067,67 +8665,63 @@ with Shelved, Discarded, Graphed and Hidden.`; } this.change_setting_to_from(setting_id, new_value, old_value, skip_custom_handler); return new_value; - } + }; - get_setting_input_JQElem(inputName) { - return this.topJQElem.find(`[name='${inputName}']`); - } + Huviz.prototype.get_setting_input_JQElem = function(inputName) { + return this.topJQElem.find("[name='" + inputName + "']"); + }; - countdown_setting(inputName) { - const input = this.get_setting_input_JQElem(inputName); + Huviz.prototype.countdown_setting = function(inputName) { + var input, newVal; + input = this.get_setting_input_JQElem(inputName); if (input.val() < 1) { return 0; } - const newVal = input.val() - 1; + newVal = input.val() - 1; return this.adjust_setting(inputName, newVal); - } + }; - preset_discover_geonames_remaining() { - let count = 0; - for (let node of Array.from(this.nameless_set)) { - const url = node.id; + Huviz.prototype.preset_discover_geonames_remaining = function() { + var count, node, url, _i, _len, _ref; + count = 0; + _ref = this.nameless_set; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node = _ref[_i]; + url = node.id; if (url.includes('geonames.org')) { count++; } } return this.adjust_setting('discover_geonames_remaining', count); - } + }; - show_geonames_instructions(params) { - //params = - // msg: "Check your email for confirmation msg" - // Usage: - // show_geonames_instructions({msg:'Check your email for confirmation message.'}) - const args = { + Huviz.prototype.show_geonames_instructions = function(params) { + var args, markdown; + args = { width: this.width * 0.6, height: this.height * 0.6 }; - let markdown = this.discover_geoname_name_instructions_md; + markdown = this.discover_geoname_name_instructions_md; if (params != null) { if (params.msg != null) { - markdown += `\ - -#### Error: -${params.msg}\ -`; + markdown += "\n#### Error:\n" + params.msg + ""; } } return this.make_markdown_dialog(markdown, null, args); - } + }; - discover_geoname_name(aUrl) { - let widget; - const id = aUrl.pathname.replace(/\//g,''); - const soughtId = id; - const idInt = parseInt(id); - const userId = this.discover_geonames_as; - const k2p = this.discover_geoname_key_to_predicate_mapping; - const url = `http://api.geonames.org/hierarchyJSON?geonameId=${id}&username=${userId}`; + Huviz.prototype.discover_geoname_name = function(aUrl) { + var id, idInt, k2p, rem, soughtId, url, userId, widget; + id = aUrl.pathname.replace(/\//g, ''); + soughtId = id; + idInt = parseInt(id); + userId = this.discover_geonames_as; + k2p = this.discover_geoname_key_to_predicate_mapping; + url = "http://api.geonames.org/hierarchyJSON?geonameId=" + id + "&username=" + userId; if (this.discover_geonames_remaining < 1) { - //console.warn("discover_geoname_name() should not be called when remaining is less than 1") return; } - if (widget = this.discover_geonames_as__widget) { + if ((widget = this.discover_geonames_as__widget)) { if (widget.state === 'untried') { this.discover_geonames_as__widget.set_state('trying'); } else if (widget.state === 'looking') { @@ -10135,274 +8729,270 @@ with Shelved, Discarded, Graphed and Hidden.`; console.info('stop looking because remaining is', this.discover_geonames_remaining); return false; } - // We decrement remaining before looking or after successfully trying. - // We do so before looking because we know that the username is good, so this will count. - // We do so after trying because we do not know until afterward that the username was good and whether it would count. - const rem = this.countdown_setting('discover_geonames_remaining'); - //console.info('discover_geoname_name() widget.state =', widget.state, "so decrementing remaining (#{rem}) early") + rem = this.countdown_setting('discover_geonames_remaining'); } else if (widget.state === 'good') { if (this.discover_geonames_remaining < 1) { - //console.info('aborting discover_geoname_name() because remaining =', @discover_geonames_remaining) return false; } this.discover_geonames_as__widget.set_state('looking'); - console.info('looking for',id,'using name',userId); + console.info('looking for', id, 'using name', userId); } else { console.warn("discover_goename_name() should not be called when widget.state =", widget.state); return false; } } - if (this.geonames_name_lookups_performed == null) { this.geonames_name_lookups_performed = 0; } + if (this.geonames_name_lookups_performed == null) { + this.geonames_name_lookups_performed = 0; + } this.geonames_name_lookups_performed += 1; $.ajax({ - url, - error: (xhr, status, error) => { - //console.log(xhr, status, error) - if (error === 'Unauthorized') { - if (this.discover_geonames_as__widget.state !== 'bad') { - this.discover_geonames_as__widget.set_state('bad'); - return this.show_geonames_instructions(); - } - } - }, - success: (json, textStatus, request) => { - let msg; - if (json.status) { - if (this.discover_geoname_name_msgs == null) { this.discover_geoname_name_msgs = {}; } - if (json.status.message) { - msg = `
    ${json.status.message}
    ` + - this.discover_geoname_name_instructions; - if (userId) { - msg = `${userId} ${msg}`; + url: url, + error: (function(_this) { + return function(xhr, status, error) { + if (error === 'Unauthorized') { + if (_this.discover_geonames_as__widget.state !== 'bad') { + _this.discover_geonames_as__widget.set_state('bad'); + return _this.show_geonames_instructions(); } } - if ((!this.discover_geoname_name_msgs[msg]) || - (this.discover_geoname_name_msgs[msg] && - ((Date.now() - this.discover_geoname_name_msgs[msg]) > - this.discover_geoname_name_msgs_threshold_ms))) { - this.discover_geoname_name_msgs[msg] = Date.now(); - this.make_dialog(msg); - } - //@show_state_msg(msg) - return; - } - //subj = aUrl.toString() - if (widget = this.discover_geonames_as__widget) { - const state_at_start = widget.state; - if (['trying', 'looking'].includes(state_at_start)) { - if (widget.state === 'trying') { - // we decrement remaining after successfully trying or before looking - this.countdown_setting('discover_geonames_remaining'); // more remaining - this.discover_geonames_as__widget.set_state('looking'); // yes, fall through to looking + }; + })(this), + success: (function(_this) { + return function(json, textStatus, request) { + var again, containershipQuad, deeperQuad, deeply, depth, geoNamesRoot, geoRec, greedily, key, msg, name, placeQuad, pred, quad, seen_name, soughtGeoname, state_at_start, subj, theType, value, _i, _ref; + if (json.status) { + if (_this.discover_geoname_name_msgs == null) { + _this.discover_geoname_name_msgs = {}; } - if (widget.state === 'looking') { - if (this.discover_geonames_remaining > 0) { - // trigger again because they have been suspended - // use setTimeout to give nodes a chance to update - const again = () => this.discover_names('geonames.org'); - setTimeout(again, 100); - } else { - this.discover_geonames_as__widget.set_state('good'); // no more remaining lookups permitted + if (json.status.message) { + msg = ("
    " + json.status.message + "
    ") + _this.discover_geoname_name_instructions; + if (userId) { + msg = "" + userId + " " + msg; } - } else { // TODO figure out why setting 'good' only when done (and setting 'looking' while 'trying') hangs - console.log('we should never get here where widget.state =',widget.state); } - //@discover_geonames_as__widget.set_state('good') # finally go to good because we are done - } else { - msg = `state_at_start = ${state_at_start} but it should only be looking or trying (nameless: ${this.nameless_set.length})`; + if ((!_this.discover_geoname_name_msgs[msg]) || (_this.discover_geoname_name_msgs[msg] && Date.now() - _this.discover_geoname_name_msgs[msg] > _this.discover_geoname_name_msgs_threshold_ms)) { + _this.discover_geoname_name_msgs[msg] = Date.now(); + _this.make_dialog(msg); + } + return; } - //console.error(msg) - //throw new Error(msg) - } else { - throw new Error("discover_geonames_as__widget is missing"); - } - const geoNamesRoot = aUrl.origin; - let deeperQuad = null; - const greedily = this.discover_geonames_greedily; - const deeply = this.discover_geonames_deeply; - let depth = 0; - for (let i = json.geonames.length - 1; i >= 0; i--) { // from most specific to most general - // Solution! The originally sought geoname (given by aUrl) should have - // its name injected back into the graph using the exact representation - // employed in aUrl (ie with or without 'https', 'www' and trailing slash) - // but all the deeper geoRecs (because they are new to this graph, presumably) - // should be represented canonically (ie without 'https', 'www' or trailing slash). - var quad, subj, value; - const geoRec = json.geonames[i]; - if (!depth) { - if (geoRec.geonameId.toString() !== soughtId) { - console.warn("likely misalignment between representation of soughtId and found", - soughtId, "!=", geoRec.geonameId); + if ((widget = _this.discover_geonames_as__widget)) { + state_at_start = widget.state; + if (state_at_start === 'trying' || state_at_start === 'looking') { + if (widget.state === 'trying') { + _this.countdown_setting('discover_geonames_remaining'); + _this.discover_geonames_as__widget.set_state('looking'); + } + if (widget.state === 'looking') { + if (_this.discover_geonames_remaining > 0) { + again = function() { + return _this.discover_names('geonames.org'); + }; + setTimeout(again, 100); + } else { + _this.discover_geonames_as__widget.set_state('good'); + } + } else { + console.log('we should never get here where widget.state =', widget.state); + } + } else { + msg = "state_at_start = " + state_at_start + " but it should only be looking or trying (nameless: " + _this.nameless_set.length + ")"; } - subj = aUrl.toString(); } else { - subj = geoNamesRoot + '/' + geoRec.geonameId; // + '/' - } - //console.log("discover_geoname_name(#{subj})") - depth++; - const soughtGeoname = (geoRec.geonameId === idInt); - if ((!deeply) && (!soughtGeoname)) { - //console.error("skipping because we are not going deep",geoRec.geonameId, id, geoRec.name) - continue; + throw new Error("discover_geonames_as__widget is missing"); } - //console.table([{id: id, geonameId: geoRec.geonameId, name: geoRec.name}]) - const { - name - } = geoRec || {}; - const placeQuad = { - s: subj, - p: RDF_type, - o: { - value: 'https://schema.org/Place', - type: RDF_object - }, // REVIEW are there others? - g: geoNamesRoot - }; - this.inject_discovered_quad_for(placeQuad, aUrl); - - let seen_name = false; - for (let key in geoRec) { // climb the hierarchy of Places sent by GeoNames - value = geoRec[key]; - if (key === 'name') { - seen_name = true; // so we can break at the end of this loop being done - } else { - if (!greedily) { - continue; + geoNamesRoot = aUrl.origin; + deeperQuad = null; + greedily = _this.discover_geonames_greedily; + deeply = _this.discover_geonames_deeply; + depth = 0; + _ref = json.geonames; + for (_i = _ref.length - 1; _i >= 0; _i += -1) { + geoRec = _ref[_i]; + if (!depth) { + if (geoRec.geonameId.toString() !== soughtId) { + console.warn("likely misalignment between representation of soughtId and found", soughtId, "!=", geoRec.geonameId); } + subj = aUrl.toString(); + } else { + subj = geoNamesRoot + '/' + geoRec.geonameId; } - if (['geonameId'].includes(key)) { - continue; - } - const pred = k2p[key]; - if (!pred) { + depth++; + soughtGeoname = geoRec.geonameId === idInt; + if ((!deeply) && (!soughtGeoname)) { continue; } - let theType = RDF_literal; - - if (typeof value === 'number') { - // REVIEW are these right? - if (Number.isInteger(value)) { - theType = 'xsd:integer'; - } else { - theType = 'xsd:decimal'; - } - value = "" + value; // convert to string for @add_quad() - } else { - theType = RDF_literal; - } - quad = { + name = (geoRec || {}).name; + placeQuad = { s: subj, - p: pred, + p: RDF_type, o: { - value, - type: theType - }, // REVIEW are there others? - g: geoNamesRoot - }; - this.inject_discovered_quad_for(quad, aUrl); - if (!greedily && seen_name) { - break; // out of the greedy consumption of all k/v pairs - } - } - if (!deeply && (depth > 1)) { - break; // out of the deep consumption of all nested contexts - } - if (deeperQuad) { - const containershipQuad = { - s: quad.s, - p: 'http://data.ordnancesurvey.co.uk/ontology/spatialrelations/contains', - o: { - value: deeperQuad.s, + value: 'https://schema.org/Place', type: RDF_object }, g: geoNamesRoot }; - this.inject_discovered_quad_for(containershipQuad, aUrl); + _this.inject_discovered_quad_for(placeQuad, aUrl); + seen_name = false; + for (key in geoRec) { + value = geoRec[key]; + if (key === 'name') { + seen_name = true; + } else { + if (!greedily) { + continue; + } + } + if (key === 'geonameId') { + continue; + } + pred = k2p[key]; + if (!pred) { + continue; + } + theType = RDF_literal; + if (typeof value === 'number') { + if (Number.isInteger(value)) { + theType = 'xsd:integer'; + } else { + theType = 'xsd:decimal'; + } + value = "" + value; + } else { + theType = RDF_literal; + } + quad = { + s: subj, + p: pred, + o: { + value: value, + type: theType + }, + g: geoNamesRoot + }; + _this.inject_discovered_quad_for(quad, aUrl); + if (!greedily && seen_name) { + break; + } + } + if (!deeply && depth > 1) { + break; + } + if (deeperQuad) { + containershipQuad = { + s: quad.s, + p: 'http://data.ordnancesurvey.co.uk/ontology/spatialrelations/contains', + o: { + value: deeperQuad.s, + type: RDF_object + }, + g: geoNamesRoot + }; + _this.inject_discovered_quad_for(containershipQuad, aUrl); + } + deeperQuad = Object.assign({}, quad); } - deeperQuad = Object.assign({}, quad); - } // shallow copy - } - }); // from success - } + }; + })(this) + }); + }; + + + /* + "fcode" : "RGN", + "adminCodes1" : { + "ISO3166_2" : "ENG" + }, + "adminName1" : "England", + "countryName" : "United Kingdom", + "fcl" : "L", + "countryId" : "2635167", + "adminCode1" : "ENG", + "name" : "Yorkshire", + "lat" : "53.95528", + "population" : 0, + "geonameId" : 8581589, + "fclName" : "parks,area, ...", + "countryCode" : "GB", + "fcodeName" : "region", + "toponymName" : "Yorkshire", + "lng" : "-1.16318" + */ + + Huviz.prototype.discover_geoname_key_to_predicate_mapping = { + name: RDFS_label, + population: 'http://dbpedia.org/property/population' + }; - inject_discovered_quad_for(quad, url) { - // Purpose: - // Central place to perform operations on discoveries, such as caching. - const q = this.add_quad(quad); + Huviz.prototype.inject_discovered_quad_for = function(quad, url) { + var q; + q = this.add_quad(quad); this.update_set_counts(); - if (this.found_names == null) { this.found_names = []; } + if (this.found_names == null) { + this.found_names = []; + } return this.found_names.push(quad.o.value); - } + }; - deprefix(uri, prefix, expansion) { - // Return uri replacing expansion with prefix if possible + Huviz.prototype.deprefix = function(uri, prefix, expansion) { return uri.replace(expansion, prefix); - } + }; - make_sparql_name_for_getty(uris, expansion, prefix) { - // This is good stuff which should be made a bit more general - // for applicability beyond getty.edu - // see https://github.com/cwrc/HuViz/issues/180#issuecomment-489557605 - let subj_constraint; - if (prefix == null) { prefix = ':'; } + Huviz.prototype.make_sparql_name_for_getty = function(uris, expansion, prefix) { + var subj_constraint, uri; + if (prefix == null) { + prefix = ':'; + } if (!Array.isArray(uris)) { uris = [uris]; } if (!uris.length) { throw new Error('expecting uris to be an Array of length > 0'); } - if (uris.length === 1) { // so just match that one uri directly - subj_constraint = `BIND (?s AS <${uris[0]}>)`; - } else { // more than 1 so make a FILTER statement for the ?subj match - // Build a constraint for the subject - // FILTER (?subj IN (:300073730, :300153822, :300153825)) - subj_constraint = "FILTER (?s IN (" + - (Array.from(uris).map((uri) => this.deprefix(uri, prefix, expansion))).join(', ') + "))"; - } - return `\ -PREFIX ${prefix} <${expansion}> -SELECT * { - ?subj gvp:prefLabelGVP [xl:literalForm ?label] . - ${subj_constraint} - }`; // """ - } + if (uris.length === 1) { + subj_constraint = "BIND (?s AS <" + uris[0] + ">)"; + } else { + subj_constraint = "FILTER (?s IN (" + ((function() { + var _i, _len, _results; + _results = []; + for (_i = 0, _len = uris.length; _i < _len; _i++) { + uri = uris[_i]; + _results.push(this.deprefix(uri, prefix, expansion)); + } + return _results; + }).call(this)).join(', ') + "))"; + } + return "PREFIX " + prefix + " <" + expansion + ">\nSELECT * {\n ?subj gvp:prefLabelGVP [xl:literalForm ?label] .\n " + subj_constraint + "\n }"; + }; + + Huviz.prototype.make_sparql_name_query = function(uris) { + var subj_constraint, uri; + if (uris.length === 1) { + subj_constraint = "FILTER (?subj in (<" + uris[0] + ">))"; + } else { + subj_constraint = "FILTER (?subj IN (" + ((function() { + var _i, _len, _results; + _results = []; + for (_i = 0, _len = uris.length; _i < _len; _i++) { + uri = uris[_i]; + _results.push(this.deprefix(uri, prefix, expansion)); + } + return _results; + }).call(this)).join(', ') + "))"; + } + return "PREFIX dbr: \nPREFIX rdfs: \n\nCONSTRUCT {\n ?subj ?pred ?obj .\n}\nWHERE {\n ?subj ?pred ?obj .\n FILTER (?pred IN (rdfs:label)) .\n " + subj_constraint + "\n}\nLIMIT 10"; - make_sparql_name_query(uris) { - let subj_constraint; - if (uris.length === 1) { // so just match that one uri directly - //subj_constraint = "BIND (<#{uris[0]}> AS ?subj)" - subj_constraint = `FILTER (?subj in (<${uris[0]}>))`; - } else { // more than 1 so make a FILTER statement for the ?subj match - // Build a constraint for the subject - // FILTER (?subj IN (:300073730, :300153822, :300153825)) - subj_constraint = "FILTER (?subj IN (" + - (Array.from(uris).map((uri) => this.deprefix(uri, prefix, expansion))).join(', ') + "))"; - } - return `\ -PREFIX dbr: -PREFIX rdfs: - -CONSTRUCT { - ?subj ?pred ?obj . -} -WHERE { - ?subj ?pred ?obj . - FILTER (?pred IN (rdfs:label)) . - ${subj_constraint} -} -LIMIT 10\ -`; // """ /* PREFIX dbr: PREFIX rdfs: - + CONSTRUCT {?sub ?pre ?obj} WHERE { ?sub ?pre ?obj . FILTER (?sub IN (dbr:Robert_Tappan_Morris,dbr:Technical_University_of_Berlin)) . FILTER (?pre IN (rdfs:label)) . } - */ + */ /* SELECT ?sub ?obj @@ -10410,148 +9000,125 @@ LIMIT 10\ ?sub rdfs:label|foaf:name ?obj . FILTER (?sub IN ()) } - */ - } + */ + }; - make_sparql_name_handler(uris) { + Huviz.prototype.make_sparql_name_handler = function(uris) { return noop; - } + }; - make_sparql_name_query_and_handler(uri_or_uris) { - let uris; + Huviz.prototype.make_sparql_name_query_and_handler = function(uri_or_uris) { + var handler, query, uris; if (Array.isArray(uri_or_uris)) { uris = uri_or_uris; } else { uris = [uri_or_uris]; } - const query = this.make_sparql_name_query(uris); - const handler = this.make_sparql_name_handler(uris); + query = this.make_sparql_name_query(uris); + handler = this.make_sparql_name_handler(uris); return [query, handler]; - } + }; - auto_discover_name_for(namelessUri) { - let args, aUrl, retval, serverUrl; - if (namelessUri.startsWith('_')) { // skip "blank" nodes + Huviz.prototype.auto_discover_name_for = function(namelessUri) { + var aUrl, args, domainName, downloadUrl, e, hasDomainName, retval, serverUrl, try_even_though_CORS_should_block, _ref, _ref1; + if (namelessUri.startsWith('_')) { return; } try { aUrl = new URL(namelessUri); - } catch (e) { - colorlog(`skipping auto_discover_name_for('${namelessUri}') because`); + } catch (_error) { + e = _error; + colorlog("skipping auto_discover_name_for('" + namelessUri + "') because"); console.log(e); return; } this.highwater_incr('discover_name'); - - const hasDomainName = domainName => aUrl.hostname.endsWith(domainName); - + hasDomainName = function(domainName) { + return aUrl.hostname.endsWith(domainName); + }; if (hasDomainName('cwrc.ca')) { - console.warn(`auto_discover_name_for('${namelessUri}') skipping cwrc.ca`); + console.warn("auto_discover_name_for('" + namelessUri + "') skipping cwrc.ca"); return; args = { - namelessUri, - //predicates: [OSMT_reg_name, OSMT_name] + namelessUri: namelessUri, serverUrl: "http://sparql.cwrc.ca/sparql" }; this.run_sparql_name_query(args); return; } - if (hasDomainName("id.loc.gov")) { - // This is less than ideal because it uses the special knowledge - // that the .skos.nt file is available. Unfortunately the only - // RDF file which is offered via content negotiation is .rdf and - // there is no parser for that in HuViz yet. Besides, they are huge. - retval = this.ingest_quads_from(`${namelessUri}.skos.nt`, - this.discover_labels(namelessUri)); - // This cool method would via a proxy but fails in the browser because - // full header access is blocked by XHR. - // `@auto_discover_header(namelessUri, ['X-PrefLabel'], sendHeaders or [])` + retval = this.ingest_quads_from("" + namelessUri + ".skos.nt", this.discover_labels(namelessUri)); return; } - if (hasDomainName("vocab.getty.edu")) { - let try_even_though_CORS_should_block; - if (try_even_though_CORS_should_block = false) { - // This would work, but CORS blocks this. Preserved in case sufficiently - // robust accounts are set up so the HuViz server could serve as a proxy. + if ((try_even_though_CORS_should_block = false)) { serverUrl = "http://vocab.getty.edu/download/nt"; - const downloadUrl = `${serverUrl}?uri=${encodeURIComponent(namelessUri)}`; + downloadUrl = "" + serverUrl + "?uri=" + (encodeURIComponent(namelessUri)); retval = this.ingest_quads_from(downloadUrl, this.discover_labels(namelessUri)); return; } else { - // Alternative response datatypes are .json, .csv, .tsv and .xml args = { - namelessUri, + namelessUri: namelessUri, serverUrl: "http://vocab.getty.edu/sparql.tsv" }; this.run_sparql_name_query(args); return; } } - if (hasDomainName("openstreetmap.org")) { args = { - namelessUri, + namelessUri: namelessUri, predicates: [OSMT_reg_name, OSMT_name], serverUrl: "https://sophox.org/sparql" }; this.run_sparql_name_query(args); return; } - - // ## Geonames - // - // Geonames has its own API and some complicated use limits so is treated - // very differently. if (hasDomainName("geonames.org")) { - if (['untried','looking','good'].includes(this.discover_geonames_as__widget.state) && - (this.discover_geonames_remaining > 0)) { + if (((_ref = this.discover_geonames_as__widget.state) === 'untried' || _ref === 'looking' || _ref === 'good') && this.discover_geonames_remaining > 0) { this.discover_geoname_name(aUrl); } return; } - - // As a final backstop we use LDF. Why last? To spare the LDF server. - // The endpoint of authority is superior because it ought to be up to date. - for (let domainName in this.domain2ldfServer) { - serverUrl = this.domain2ldfServer[domainName]; + _ref1 = this.domain2ldfServer; + for (domainName in _ref1) { + serverUrl = _ref1[domainName]; args = { - namelessUri, - serverUrl + namelessUri: namelessUri, + serverUrl: serverUrl }; - if (hasDomainName(domainName) || (domainName === '*')) { + if (hasDomainName(domainName) || domainName === '*') { this.run_ldf_name_query(args); return; } } - } + }; - discover_names_including(includes) { - if (this.nameless_set) { // this might be before the set exists + Huviz.prototype.discover_names_including = function(includes) { + if (this.nameless_set) { this.discover_names(includes); } - } + }; - discover_names(includes) { - //console.log('discover_names(',includes,') # of nameless:',@nameless_set.length) - for (let node of Array.from(this.nameless_set)) { - const uri = node.id; + Huviz.prototype.discover_names = function(includes) { + var node, uri, _i, _len, _ref; + _ref = this.nameless_set; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node = _ref[_i]; + uri = node.id; if (!((includes != null) && !uri.includes(includes))) { - // only if includes is specified but not found do we skip auto_discover_name_for this.auto_discover_name_for(uri); } } - } - - // ## SPARQL queries + }; - run_sparql_name_query(args) { - const {namelessUri} = args; - if (args.query == null) { args.query = "# " + - ( args.comment || `run_sparql_name_query(${namelessUri})`) + "\n" + - this.make_name_query(namelessUri, args); } - const defaults = { + Huviz.prototype.run_sparql_name_query = function(args) { + var defaults, namelessUri; + namelessUri = args.namelessUri; + if (args.query == null) { + args.query = "# " + (args.comment || ("run_sparql_name_query(" + namelessUri + ")")) + "\n" + this.make_name_query(namelessUri, args); + } + defaults = { success_handler: this.generic_name_success_handler, result_handler: this.name_result_handler, default_terms: { @@ -10561,99 +9128,86 @@ LIMIT 10\ }; args = this.compose_object_from_defaults_and_incoming(defaults, args); return this.run_managed_query_ajax(args); - } + }; - // Receive a tsv of rows and call the `result_handler` to process each row. - // - // Data might look like: - // ``` - // ?p ?o - // rdfs:label "Uncle Bob" - // rdfs:label "Uncle Sam" - // ``` - // - // Meanwhile `result_handler` expects each row to be JSON like: - // - // ```json - // {'?p': 'rdfs:label', '?o': "Uncle Bob"} - // ``` - tsv_name_success_handler(data, textStatus, jqXHR, queryManager) { - let e, table; - const { - result_handler - } = queryManager.args; + Huviz.prototype.tsv_name_success_handler = function(data, textStatus, jqXHR, queryManager) { + var cols, e, firstLine, line, lines, result_handler, row, rowJson, table, _i, _len; + result_handler = queryManager.args.result_handler; try { - let lines; table = []; - //@make_pre_dialog(data, null, {title:"tsv_name_success_handler"}) try { lines = data.split(/\r?\n/); - } catch (error) { - e = error; - console.info("data:",data); + } catch (_error) { + e = _error; + console.info("data:", data); throw e; } - const firstLine = lines.shift(); - const cols = firstLine.split("\t"); - for (let line of Array.from(lines)) { - if (!line) { continue; } - const row = line.split("\t"); - const rowJson = _.zipObject(cols, row); + firstLine = lines.shift(); + cols = firstLine.split("\t"); + for (_i = 0, _len = lines.length; _i < _len; _i++) { + line = lines[_i]; + if (!line) { + continue; + } + row = line.split("\t"); + rowJson = _.zipObject(cols, row); result_handler(rowJson, queryManager); table.push(rowJson); } queryManager.setResultCount(table.length); - } catch (error1) { - e = error1; + } catch (_error) { + e = _error; this.make_json_dialog(table); queryManager.fatalError(e); } - } + }; - json_name_success_handler(data, textStatus, jqXHR, queryManager) { - let table; - const { - result_handler - } = queryManager.args; + Huviz.prototype.json_name_success_handler = function(data, textStatus, jqXHR, queryManager) { + var e, resultJson, result_handler, table, _i, _len, _ref; + result_handler = queryManager.args.result_handler; try { table = []; - for (let resultJson of Array.from(data.results.bindings)) { - if (!resultJson) { continue; } + _ref = data.results.bindings; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + resultJson = _ref[_i]; + if (!resultJson) { + continue; + } result_handler(resultJson, queryManager); table.push(resultJson); } queryManager.setResultCount(table.length); - } catch (e) { - this.make_json_dialog(table, null, {title: "table of results"}); + } catch (_error) { + e = _error; + this.make_json_dialog(table, null, { + title: "table of results" + }); queryManager.fatalError(e); } - } + }; - display_graph_success_handler(data, textStatus, jqXHR, queryManager) { + Huviz.prototype.display_graph_success_handler = function(data, textStatus, jqXHR, queryManager) { this.disable_dataset_ontology_loader_AUTOMATICALLY(); - // TODO @update_browser_title() - // TODO @update_caption() this.generic_name_success_handler(data, textStatus, jqXHR, queryManager); this.call_on_dataset_loaded(); - } + }; - generic_success_handler(data, textStatus, jqXHR, queryManager) { + Huviz.prototype.generic_success_handler = function(data, textStatus, jqXHR, queryManager) { this.generic_name_success_handler(data, textStatus, jqXHR, queryManager); - } + }; - generic_name_success_handler(data, textStatus, jqXHR, queryManager) { - let resp_type, success_handler; + Huviz.prototype.generic_name_success_handler = function(data, textStatus, jqXHR, queryManager) { + var error, resp_type, success_handler; try { data = JSON.parse(data); - } catch (error) { + } catch (_error) { + error = _error; console.info("generic_success_handler tried and failed to treat data as json"); } - // this should be based on response header or a queryManager console.log("response Content-Type:", jqXHR.getResponseHeader("content-type")); if (data.head != null) { resp_type = 'json'; } else if (data.includes("\t")) { - // TODO base presumption of .tsv on something more definitive than finding one resp_type = 'tsv'; } else { console.warn(data); @@ -10670,92 +9224,83 @@ LIMIT 10\ throw new Error('no name_success_handler available'); } success_handler(data, textStatus, jqXHR, queryManager); - // set to `false` for no limit - } + }; + + Huviz.prototype.domain2ldfServer = { + 'dbpedia.org': "http://fragments.dbpedia.org/2016-04/en", + 'viaf.org': "http://data.linkeddatafragments.org/viaf", + 'getty.edu': "http://data.linkeddatafragments.org/lov", + '*': "http://data.linkeddatafragments.org/lov" + }; + + Huviz.prototype.default_name_query_args = { + predicates: [RDFS_label, FOAF_name, SCHEMA_name], + limit: 20 + }; - // ### make_name_query() - // - // Generate a name lookup query for `uri`. If the optional `args` object - // has an optional `predicates` list then those predicates are specifically - // looked up. The default predicates are provided by `default_name_query_args`. - // - // The default query looks like: - // ```sparql - // SELECT * - // WHERE { - // { - // BIND (foaf:name as ?p) . - // <#{uri}> ?p ?o . - // } UNION { - // BIND (rdfs:label as ?p) . - // <#{uri}> ?p ?o . - // } UNION { - // BIND (schema:name as ?p) . - // <#{uri}> ?p ?o . - // } - // } - // LIMIT 20``` - make_name_query(uri, in_args) { - const args = this.compose_object_from_defaults_and_incoming(this.default_name_query_args, in_args); - const {predicates} = args; - const lines = [ - "SELECT *", - "WHERE {"]; - let pred_num = 0; - for (let pred of Array.from(predicates)) { + Huviz.prototype.make_name_query = function(uri, in_args) { + var args, lines, pred, pred_num, predicates, _i, _len; + args = this.compose_object_from_defaults_and_incoming(this.default_name_query_args, in_args); + predicates = args.predicates; + lines = ["SELECT *", "WHERE {"]; + pred_num = 0; + for (_i = 0, _len = predicates.length; _i < _len; _i++) { + pred = predicates[_i]; if (pred_num) { lines.push(' UNION'); } pred_num++; lines.push(" {"); - lines.push(` BIND (<${pred}> as ?p) .`); - lines.push(` <${uri}> ?p ?o .`); + lines.push(" BIND (<" + pred + "> as ?p) ."); + lines.push(" <" + uri + "> ?p ?o ."); lines.push(" }"); } lines.push("}"); if (args.limit) { - lines.push(`LIMIT ${args.limit}`); + lines.push("LIMIT " + args.limit); } return lines.join("\n"); - } + }; - convert_N3_obj_to_GreenTurtle(n3_obj_term) { - let bare_obj_term, retval; - if (typeof(n3_obj_term) === 'string') { + Huviz.prototype.convert_N3_obj_to_GreenTurtle = function(n3_obj_term) { + var bare_obj_term, e, graph, pred, retval, statement, subj; + if (typeof n3_obj_term === 'string') { bare_obj_term = n3_obj_term; } else { bare_obj_term = n3_obj_term.id; - if (!bare_obj_term.startsWith('"')) { // it must be an uri + if (!bare_obj_term.startsWith('"')) { retval = { type: RDF_object, value: n3_obj_term.id }; return retval; } - // the GreenTurtle parser seems to expect curies as types not full uri - bare_obj_term = bare_obj_term.replace("http://www.w3.org/2001/XMLSchema#","xsd:"); - bare_obj_term = bare_obj_term.replace("^^xsd:string",''); + bare_obj_term = bare_obj_term.replace("http://www.w3.org/2001/XMLSchema#", "xsd:"); + bare_obj_term = bare_obj_term.replace("^^xsd:string", ''); + } + if (this.greenturtleparser == null) { + this.greenturtleparser = new GreenerTurtle(); } - if (this.greenturtleparser == null) { this.greenturtleparser = new GreenerTurtle(); } - const subj = 'http://example.com/subj'; - const pred = 'http://example.com/pred'; - const statement = `<${subj}> <${pred}> ${bare_obj_term} .`; + subj = 'http://example.com/subj'; + pred = 'http://example.com/pred'; + statement = "<" + subj + "> <" + pred + "> " + bare_obj_term + " ."; try { - const graph = this.greenturtleparser.parse(statement, "text/turtle"); + graph = this.greenturtleparser.parse(statement, "text/turtle"); retval = graph.subjects[subj].predicates[pred].objects.slice(-1)[0]; - } catch (e) { - //console.log(n3_obj_term, n3_obj_term.split('')) + } catch (_error) { + e = _error; console.error(e); throw e; retval = { value: strip_surrounding_quotes(n3_obj_term), - type: 'Literal' // TODO make this legit + type: 'Literal' }; } return retval; - } + }; - convert_str_obj_to_GreenTurtle(bare_term) { + Huviz.prototype.convert_str_obj_to_GreenTurtle = function(bare_term) { + var msg; if (bare_term[0] === '<') { return this.convert_N3_obj_to_GreenTurtle(bare_term); } @@ -10763,47 +9308,43 @@ LIMIT 10\ if (bare_term.startsWith('"')) { if (bare_term.includes('@')) { return this.convert_N3_obj_to_GreenTurtle(bare_term); + } else { + } - else {} - // fall through to report error } else { - return this.convert_N3_obj_to_GreenTurtle('"'+bare_term+'"'); + return this.convert_N3_obj_to_GreenTurtle('"' + bare_term + '"'); } } - const msg = `bare_term: {${bare_term}} not parseable by convert_str_term_to_GreenTurtle`; + msg = "bare_term: {" + bare_term + "} not parseable by convert_str_term_to_GreenTurtle"; throw new Error(msg); - } + }; - convert_N3_uri_to_string(n3Uri) { - //console.warn("convert_N3_uri_to_string('#{n3Uri}')") + Huviz.prototype.convert_N3_uri_to_string = function(n3Uri) { return n3Uri; - } + }; - convert_str_uri_to_string(bareUri) { + Huviz.prototype.convert_str_uri_to_string = function(bareUri) { if (bareUri.startsWith('<')) { - bareUri = bareUri.substr(1,bareUri.length-2); + bareUri = bareUri.substr(1, bareUri.length - 2); } - //console.warn("convert_str_uri_to_string('#{bareUri}')") return bareUri; - } + }; - convert_obj_obj_to_GreenTurtle(jsObj) { - // TODO convert the .type to a legit uri + Huviz.prototype.convert_obj_obj_to_GreenTurtle = function(jsObj) { + var lang; if (jsObj.type === 'uri') { jsObj.type = RDF_object; } else if (jsObj.type === 'literal') { - let lang; jsObj.type = RDF_literal; - if (lang = jsObj['xml:lang']) { + if ((lang = jsObj['xml:lang'])) { delete jsObj['xml:lang']; - jsObj.language = lang.toLowerCase(); // REVIEW is lowercasing always right? + jsObj.language = lang.toLowerCase(); } } return jsObj; - } + }; - convert_obj_uri_to_string(jsObj) { - // We are anticipating jsObj to have a .value + Huviz.prototype.convert_obj_uri_to_string = function(jsObj) { if (jsObj.value != null) { return jsObj.value; } @@ -10811,27 +9352,21 @@ LIMIT 10\ return jsObj; } throw new Error('expecting jsObj to have .value or be a literal'); - } - - name_result_handler(result, queryManager) { - let parseObj, parseUri, result_type; - const terms = queryManager.args.query_terms || queryManager.args.default_terms; - const subj_term = result['?s'] || result['s'] || terms.s; - const pred_term = result['?p'] || result['p'] || terms.p; - const obj_term = result['?o'] || result['o'] || terms.o; + }; - // identify the result_type + Huviz.prototype.name_result_handler = function(result, queryManager) { + var error, obj_term, parseObj, parseUri, pred_term, q, result_type, subj_term, terms; + terms = queryManager.args.query_terms || queryManager.args.default_terms; + subj_term = result['?s'] || result['s'] || terms.s; + pred_term = result['?p'] || result['p'] || terms.p; + obj_term = result['?o'] || result['o'] || terms.o; if (queryManager.args.from_N3) { result_type = 'n3'; } else if (obj_term.value != null) { - // TODO this LOOKS like GreenTurtle. Is it a standard? - // It differs in that the .type is ['url','literal'] rather than an uri result_type = 'obj'; } else { result_type = 'str'; } - - // prepare parsers based on the result_type switch (result_type) { case 'n3': parseObj = this.convert_N3_obj_to_GreenTurtle; @@ -10841,7 +9376,7 @@ LIMIT 10\ parseObj = this.convert_obj_obj_to_GreenTurtle; parseUri = this.convert_obj_uri_to_string; break; - case 'str': // TODO what should we call this? + case 'str': parseObj = this.convert_str_obj_to_GreenTurtle; parseUri = this.convert_str_uri_to_string; break; @@ -10850,27 +9385,25 @@ LIMIT 10\ throw new Error('can not determine result_type'); } try { - const q = { + q = { s: parseUri(subj_term), p: parseUri(pred_term), o: parseObj(obj_term), g: terms.g }; this.add_quad(q); - } catch (error1) { - //@make_json_dialog(result, null, {title: error.toString()}) - const error = error1; + } catch (_error) { + error = _error; console.warn(result); console.error(error); } - } + }; - run_ldf_name_query(args) { - const {namelessUri} = args; - args.query = "# " + - ( args.comment || `run_ldf_name_query(${namelessUri})`) + "\n" + - this.make_name_query(namelessUri); - const defaults = { + Huviz.prototype.run_ldf_name_query = function(args) { + var defaults, namelessUri; + namelessUri = args.namelessUri; + args.query = "# " + (args.comment || ("run_ldf_name_query(" + namelessUri + ")")) + "\n" + this.make_name_query(namelessUri); + defaults = { success_handler: this.generic_name_success_handler, result_handler: this.name_result_handler, from_N3: true, @@ -10881,57 +9414,66 @@ LIMIT 10\ }; args = this.compose_object_from_defaults_and_incoming(defaults, args); return this.run_managed_query_ldf(args); - } + }; - run_managed_query_ldf(args) { - const queryManager = this.run_managed_query_abstract(args); - let {success_handler, error_callback, timeout, result_handler, serverUrl, query} = args; - if (serverUrl == null) { serverUrl = "http://fragments.dbpedia.org/2016-04/en"; } // TODO what? - const ldf_worker = new Worker('/comunica-ldf-client/ldf-client-worker.min.js'); + Huviz.prototype.run_managed_query_ldf = function(args) { + var error_callback, ldf_worker, query, queryManager, result_handler, serverUrl, success_handler, timeout; + queryManager = this.run_managed_query_abstract(args); + success_handler = args.success_handler, error_callback = args.error_callback, timeout = args.timeout, result_handler = args.result_handler, serverUrl = args.serverUrl, query = args.query; + if (serverUrl == null) { + serverUrl = "http://fragments.dbpedia.org/2016-04/en"; + } + ldf_worker = new Worker('/comunica-ldf-client/ldf-client-worker.min.js'); ldf_worker.postMessage({ type: 'query', - query, - resultsToTree: false, // TODO experiment with this + query: query, + resultsToTree: false, context: { '@comunica/actor-http-memento:datetime': null, queryFormat: 'sparql', - sources: [{ - type: 'auto', - value: serverUrl - } - ] - }}); - - ldf_worker.onmessage = event => { - queryManager.cancelAnimation(); - const d = event.data; - const {type, result} = d; - switch (type) { - case 'result': - queryManager.incrResultCount(); - return result_handler.call(this, result, queryManager); - case 'error': - return queryManager.fatalError(d); - case 'end': - return queryManager.finishCounting(); - case 'queryInfo': case 'log': - //console.log(type, event) - default: - return console.log("UNHANDLED", event); + sources: [ + { + type: 'auto', + value: serverUrl + } + ] } - }; - + }); + ldf_worker.onmessage = (function(_this) { + return function(event) { + var d, result, type; + queryManager.cancelAnimation(); + d = event.data; + type = d.type, result = d.result; + switch (type) { + case 'result': + queryManager.incrResultCount(); + return result_handler.call(_this, result, queryManager); + case 'error': + return queryManager.fatalError(d); + case 'end': + return queryManager.finishCounting(); + case 'queryInfo': + case 'log': + break; + default: + return console.log("UNHANDLED", event); + } + }; + })(this); return queryManager; - } - - // ## Examples and Tests START + }; - make_wikidata_name_query(uri, langs) { - let prefixes, subj; - if (uri == null) { uri = 'wd:Q160302'; } - if (langs == null) { langs = "en"; } // comma delimited langs expected, eg "en,fr,de" + Huviz.prototype.make_wikidata_name_query = function(uri, langs) { + var prefixes, subj; + if (uri == null) { + uri = 'wd:Q160302'; + } + if (langs == null) { + langs = "en"; + } if (uri.startsWith('http')) { - subj = `<${uri}>`; + subj = "<" + uri + ">"; } else { subj = uri; } @@ -10940,75 +9482,59 @@ LIMIT 10\ } else { prefixes = ""; } - return `\ -${prefixes} -SELECT ?subj ?pred ?subjLabel -WHERE { - BIND (${subj} as ?subj) - BIND (rdfs:label as ?pred) - SERVICE wikibase:label { - bd:serviceParam wikibase:language "${langs}" . - } -}`; // " - } + return "" + prefixes + "\nSELECT ?subj ?pred ?subjLabel\nWHERE {\n BIND (" + subj + " as ?subj)\n BIND (rdfs:label as ?pred)\n SERVICE wikibase:label {\n bd:serviceParam wikibase:language \"" + langs + "\" .\n }\n}"; + }; + + Huviz.prototype.test_json_fetch = function(uri, success, err) { + if (uri == null) { + uri = 'https://www.wikidata.org/entity/Q12345.json'; + } + if (success == null) { + success = (function(_this) { + return function(r) { + return console.log(r, r.json().then(function(json) { + return console.log(JSON.stringify(json)); + })); + }; + })(this); + } + if (err == null) { + err = (function(_this) { + return function(e) { + return console.log('OOF:', e); + }; + })(this); + } + fetch(uri).then(success)["catch"](err); + }; - test_json_fetch(uri, success, err) { - if (uri == null) { uri = 'https://www.wikidata.org/entity/Q12345.json'; } - if (success == null) { success = r => console.log(r, r.json().then(json=> console.log(JSON.stringify(json)))); } - if (err == null) { err = e => console.log('OOF:',e); } - fetch(uri).then(success).catch(err); - } + Huviz.prototype.make_qname = function(uri) { + return uri; + }; - // ## QUAD Ingestion + Huviz.prototype.last_quad = {}; - make_qname(uri) { - // TODO(smurp) dear god! this method name is lying (it is not even trying) - return uri; - } - add_quad(quad, sprql_subj) { //sprq_sbj only used in SPARQL quieries - // FIXME Oh! How this method needs a fine toothed combing!!!! - // * are rdf:Class and owl:Class the same? - // * uniquer is misnamed, it should be called make_domsafe_id or sumut - // * vars like sid, pid, subj_lid should be revisited - // * review subj vs subj_n - // * do not conflate node ids across prefixes eg rdfs:Class vs owl:Class - // * Literal should not be a subclass of Thing. Thing and dataType are sibs - // Terminology: - // A `lid` is a "local id" which is unique and a safe identifier for css selectors. - // This is in opposition to an `id` which is a synonym for uri (ideally). - // There is inconsistency in this usage, which should be cleared up. - // Proposed terms which SHOULD be used are: - // - *_curie eg pred_curie='rdfs:label' - // - *_uri eg subj_uri='http://sparql.cwrc.ca/ontology/cwrc#NaturalPerson' - // - *_lid: a "local id" eg subj_lid='atwoma' - //console.log("HuViz.add_quad()", quad) - // - // Expecting .o to either: - // * represent an uri - // - type: "http://www.w3.org/1999/02/22-rdf-syntax-ns#object" - // - value: the uri - // * represent a literal - // - language: undefined OR a full language url - // - type: an XMLSchema value - // - value: the value in a string - const subj_uri = quad.s; - if ((subj_uri == null)) { + Huviz.prototype.object_value_types = {}; + + Huviz.prototype.unique_pids = {}; + + Huviz.prototype.add_quad = function(quad, sprql_subj) { + var cntx_n, ctxid, edge, isLiteral, is_type, literal_node, make_edge, newsubj, objId, objId_explanation, objKey, objVal, obj_n, pred_n, pred_uri, simpleType, subj, subj_lid, subj_n, subj_uri, use_thumb; + subj_uri = quad.s; + if (subj_uri == null) { throw new Error("quad.s is undefined"); } - const pred_uri = quad.p; - if ((pred_uri == null)) { + pred_uri = quad.p; + if (pred_uri == null) { throw new Error("quad.p is undefined"); } - const ctxid = quad.g || this.get_context(); - const subj_lid = uniquer(subj_uri); // FIXME rename uniquer to make_dom_safe_id + ctxid = quad.g || this.get_context(); + subj_lid = uniquer(subj_uri); this.object_value_types[quad.o.type] = 1; this.unique_pids[pred_uri] = 1; - let newsubj = false; - let subj = null; - //if @p_display then @performance_dashboard('add_quad') - - // REVIEW is @my_graph still needed and being correctly used? - if ((this.my_graph.subjects[subj_uri] == null)) { + newsubj = false; + subj = null; + if (this.my_graph.subjects[subj_uri] == null) { newsubj = true; subj = { id: subj_uri, @@ -11019,40 +9545,34 @@ WHERE { } else { subj = this.my_graph.subjects[subj_uri]; } - this.ensure_predicate_lineage(pred_uri); - let edge = null; - const subj_n = this.get_or_create_node_by_id(subj_uri); - const pred_n = this.get_or_create_predicate_by_id(pred_uri); - const cntx_n = this.get_or_create_context_by_id(ctxid); - if ((quad.p === RDF_subClassOf) && this.show_class_instance_edges) { + edge = null; + subj_n = this.get_or_create_node_by_id(subj_uri); + pred_n = this.get_or_create_predicate_by_id(pred_uri); + cntx_n = this.get_or_create_context_by_id(ctxid); + if (quad.p === RDF_subClassOf && this.show_class_instance_edges) { this.try_to_set_node_type(subj_n, OWL_Class); } - // TODO: use @predicates_to_ignore instead OR rdfs:first and rdfs:rest if (pred_uri.match(/\#(first|rest)$/)) { - console.warn(`add_quad() ignoring quad because pred_uri=${pred_uri}`, quad); + console.warn("add_quad() ignoring quad because pred_uri=" + pred_uri, quad); return; } - // set the predicate on the subject - if ((subj.predicates[pred_uri] == null)) { - subj.predicates[pred_uri] = {objects:[]}; + if (subj.predicates[pred_uri] == null) { + subj.predicates[pred_uri] = { + objects: [] + }; } if (quad.o.type === RDF_object) { - // The object is not a literal, but another resource with an uri - // so we must get (or create) a node to represent it - const obj_n = this.get_or_create_node_by_id(quad.o.value); - if ((quad.o.value === RDF_Class) && this.show_class_instance_edges) { - // This weird operation is to ensure that the Class Class is a Class + obj_n = this.get_or_create_node_by_id(quad.o.value); + if (quad.o.value === RDF_Class && this.show_class_instance_edges) { this.try_to_set_node_type(obj_n, OWL_Class); } - if ((quad.p === RDF_subClassOf) && this.show_class_instance_edges) { + if (quad.p === RDF_subClassOf && this.show_class_instance_edges) { this.try_to_set_node_type(obj_n, OWL_Class); } - // We have a node for the object of the quad and this quad is relational - // so there should be links made between this node and that node - const is_type = is_one_of(pred_uri, TYPE_SYNS); - const use_thumb = is_one_of(pred_uri, THUMB_PREDS) && this.show_thumbs_dont_graph; - const make_edge = this.show_class_instance_edges || (!is_type && !use_thumb); + is_type = is_one_of(pred_uri, TYPE_SYNS); + use_thumb = is_one_of(pred_uri, THUMB_PREDS) && this.show_thumbs_dont_graph; + make_edge = this.show_class_instance_edges || !is_type && !use_thumb; if (is_type) { this.try_to_set_node_type(subj_n, quad.o.value); } @@ -11061,65 +9581,35 @@ WHERE { this.develop(subj_n); } if (make_edge) { - this.develop(subj_n); // both subj_n and obj_n should hatch for edge to make sense - // REVIEW uh, how are we ensuring that the obj_n is hatching? should it? + this.develop(subj_n); edge = this.get_or_create_Edge(subj_n, obj_n, pred_n, cntx_n); this.infer_edge_end_types(edge); edge.register_context(cntx_n); - edge.color = this.gclui.predicate_picker.get_color_forId_byName(pred_n.lid,'showing'); + edge.color = this.gclui.predicate_picker.get_color_forId_byName(pred_n.lid, 'showing'); this.add_edge(edge); this.develop(obj_n); } - } else { // ie the quad.o is a literal + } else { if (is_one_of(pred_uri, NAME_SYNS)) { - this.set_name( - subj_n, - quad.o.value.replace(/^\s+|\s+$/g, ''), - quad.o.language); + this.set_name(subj_n, quad.o.value.replace(/^\s+|\s+$/g, ''), quad.o.language); if (subj_n.embryo) { - this.develop(subj_n); // might be ready now + this.develop(subj_n); } - } else { // the object is a literal other than name + } else { if (this.make_nodes_for_literals) { - let isLiteral, objId; - const objVal = quad.o.value; - const simpleType = getTypeSignature(quad.o.type || '') || 'Literal'; - if ((objVal == null)) { + objVal = quad.o.value; + simpleType = getTypeSignature(quad.o.type || '') || 'Literal'; + if (objVal == null) { throw new Error("missing value for " + JSON.stringify([subj_uri, pred_uri, quad.o])); } - // Does the value have a language or does it contain spaces? - //objValHasSpaces = (objVal.match(/\s/g)||[]).length > 0 if (quad.o.language && this.group_literals_by_subj_and_pred) { - // Perhaps an appropriate id for a literal "node" is - // some sort of amalgam of the subject and predicate ids - // for that object. - // Why? Consider the case of rdfs:comment. - // If there are multiple literal object values on rdfs:comment - // they are presumably different language versions of the same - // text. For them to end up on the same MultiString instance - // they all have to be treated as names for a node with the same - // id -- hence that id must be composed of the subj and pred ids. - // Another perspective on this is that these are different comments - // in different languages, so what suggests that they have anything - // at all to do with one another? - // Further, if (as is the case with these triples) - // Martineau_Harriet hasActivistInvolvementIn "_tariff reform_" - // Martineau_Harriet hasGenderedPoliticalActivity "_tariff reform_" - // they SHOULD share the "_tariff reform_" node. - // - // So, after all this (poorly stated commentary) the uneasy conclusion - // is that if a literal value has a language associated with it then - // all the alternate language literals associated with that same - // subject/predicate combination will be treated as the same literal - // node. - const objKey = `${subj_n.lid} ${pred_uri}`; + objKey = "" + subj_n.lid + " " + pred_uri; objId = synthIdFor(objKey); - const objId_explanation = `synthIdFor('${objKey}') = ${objId}`; - //console.warn(objId_explanation) + objId_explanation = "synthIdFor('" + objKey + "') = " + objId; } else { objId = synthIdFor(objVal); } - const literal_node = this.get_or_create_node_by_id(objId, objVal, (isLiteral = true)); + literal_node = this.get_or_create_node_by_id(objId, objVal, (isLiteral = true)); this.try_to_set_node_type(literal_node, simpleType); literal_node.__dataType = quad.o.type; this.develop(literal_node); @@ -11127,106 +9617,52 @@ WHERE { edge = this.get_or_create_Edge(subj_n, literal_node, pred_n, cntx_n); this.infer_edge_end_types(edge); edge.register_context(cntx_n); - edge.color = this.gclui.predicate_picker.get_color_forId_byName(pred_n.lid,'showing'); + edge.color = this.gclui.predicate_picker.get_color_forId_byName(pred_n.lid, 'showing'); this.add_edge(edge); - literal_node.fully_loaded = true; // for sparql quieries to flag literals as fully_loaded + literal_node.fully_loaded = true; } } } - // if the subject came from SPARQL then to true (i.e. fully loaded) if (this.using_sparql()) { - subj_n.fully_loaded = false; // all nodes default to not being fully_loaded - //if subj_n.id is sprql_subj# if it is the subject node then is fully_loaded - // subj_n.fully_loaded = true - if (subj_n.id === quad.subject) { // if it is the subject node then is fully_loaded + subj_n.fully_loaded = false; + if (subj_n.id === quad.subject) { subj_n.fully_loaded = true; } } - if (subj_n.embryo) { - // It is unprincipled to do this, but some subj_n were escaping development. this.develop(subj_n); } - this.consider_suppressing_edge_and_ends_re_OA(edge); - this.last_quad = quad; this.pfm_count('add_quad'); return edge; - } - - consider_suppressing_edge_and_ends_re_OA(edge) { - // ## Purpose: - // - // Suppress (ie keep from appearing in the graph by policy) nodes and edges - // whose only purpose is to implement annotations. - // - // The exceptions to this are: - // - // * the object of an oa:exact predicate should NOT be suppressed - // * the oa:exact object should be depicted as having an edge of type '_:hasAnnotation' - // * the oa:hasTarget edge should be suppressed but a SYNTHETIC edge should be - // put in its place which links the target of the [oa:hasTarget] edge to the - // target of the [oa:exact] edge with [_:hasAnnotation] - // - // ## REVIEW: - // - // * discover if there are other predicates which should be treated like [oa:exact] - // - // ## Method: - // - // Place a node in the suppressed_set if any one of the following is true: - // * its edges are only in the OA vocab - // * it is in a taxon which is in the OA vocab - // * it only has edges connecting it to nodes which are instances of OA classes - // - // The other aspect of this strategy which is complicated is how to keep - // account of the relations between the nodes and edges in the subgraph - // of an Annotion, noting these considerations: - // * an Annotation may have 1 or more Targets - // * an Annotation may have 0 or more Bodies - // * Bodies and Targets may be connected directly to their Resources OR - // * the may be indirectly connected to Resources via ResourceSelection - // * multiple triples must be captured before a summary Edge can be created - // * some of those triples my participate in multiple summary Edges - // * during digestion some nodes may not have their subgraph membership known - // * some Annotations will not have an easy "summary object" (eg oa:exact value) - // * we will still want to be able to graph such Annotations - // * multiple Bodies for an Annotation should each be "summarized" - // - // Strategies: - // - // 1. build paths - // * Nodes come to us randomly, so whenever one arrives knit it into a - // path and check to see if the newly extended path now satisfies - // conditions such as sufficiency for a) display b) closing - // * challenges: - // - how to express the logic for testing displayability and closability - // - how to maintain the set of fragmentary paths - // * references: - // - is this like Nooron's AutoSem? + }; + Huviz.prototype.consider_suppressing_edge_and_ends_re_OA = function(edge) { + var suppressEdge, _ref; if (!edge || !this.suppress_annotation_edges) { return; } this.suppress_node_re_OA_if_appropriate(edge.source); - // if edge.predicate.id is OA_exact # TODO once ids are urls then this is truer - if (edge.predicate.lid === 'exact') { // TODO ensure ids are urls then do the above... - if (this.hasAnnotation_targets == null) { this.hasAnnotation_targets = []; } - if (!(Array.from(this.hasAnnotation_targets).includes(edge.target))) { + if (edge.predicate.lid === 'exact') { + if (this.hasAnnotation_targets == null) { + this.hasAnnotation_targets = []; + } + if (!(_ref = edge.target, __indexOf.call(this.hasAnnotation_targets, _ref) >= 0)) { this.hasAnnotation_targets.push(edge.target); } - //alert("not suppressing the object of oa:exact: #{edge.target.lid}") - - return; // edge.target should not be suppressed + return; } - const suppressEdge = this.in_OA_cached(edge.predicate); // WIP what???? + suppressEdge = this.in_OA_cached(edge.predicate); this.suppress_node_re_OA_if_appropriate(edge.target); - } + }; - suppress_node_re_OA_if_appropriate(node) { - let should_suppress = false; - for (let taxon of Array.from(node.taxons)) { + Huviz.prototype.suppress_node_re_OA_if_appropriate = function(node) { + var should_suppress, taxon, _i, _len, _ref; + should_suppress = false; + _ref = node.taxons; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + taxon = _ref[_i]; if (this.in_OA_cached(taxon)) { should_suppress = true; continue; @@ -11235,242 +9671,241 @@ WHERE { if (should_suppress) { this.suppress(node); } - } + }; - in_OA_cached(thing) { - if ((thing._is_in_OA == null)) { + Huviz.prototype.in_OA_cached = function(thing) { + if (thing._is_in_OA == null) { thing._is_in_OA = this.in_OA_vocab(thing.id); } return thing._is_in_OA; - } + }; - in_OA_vocab(url) { - // Ideally it would be enough for url.startsWith to be tested for OA membership - // but until @ontology.domain and @ontology.range and such are using URLs as - // ids rather than "lids" (ie 'local' ids) we must also check for bare lids - // such as 'Annotation', 'TextQuoteSelector' and friends. - const match = url.match(OA_terms_regex); + Huviz.prototype.in_OA_vocab = function(url) { + var match; + match = url.match(OA_terms_regex); return url.startsWith(OA_) || match; - } + }; - remove_from_nameless(node) { + Huviz.prototype.remove_from_nameless = function(node) { + var node_removed; if (node.nameless != null) { - if (this.nameless_removals == null) { this.nameless_removals = 0; } + if (this.nameless_removals == null) { + this.nameless_removals = 0; + } this.nameless_removals++; - const node_removed = this.nameless_set.remove(node); + node_removed = this.nameless_set.remove(node); if (node_removed !== node) { - console.log("expecting",node_removed,"to have been",node); + console.log("expecting", node_removed, "to have been", node); } - //if @nameless_set.binary_search(node) > -1 - // console.log("expecting",node,"to no longer be found in",@nameless_set) delete node.nameless_since; } - } - add_to_nameless(node) { + }; + + Huviz.prototype.add_to_nameless = function(node) { + var _base; if (node.isLiteral) { - // Literals cannot have names looked up. return; } node.nameless_since = performance.now(); - if (this.nameless_set.traffic == null) { this.nameless_set.traffic = 0; } + if ((_base = this.nameless_set).traffic == null) { + _base.traffic = 0; + } this.nameless_set.traffic++; this.nameless_set.add(node); - //@nameless_set.push(node) # REVIEW(smurp) why not .add()????? - } + }; - set_name(node, full_name, lang) { - // So if we set the full_name to null that is to mean that we have - // no good idea what the name yet. - const perform_rename = () => { - if (full_name != null) { - if (!node.isLiteral) { - this.remove_from_nameless(node); - } - } else { - if (!node.isLiteral) { - this.add_to_nameless(node); + Huviz.prototype.set_name = function(node, full_name, lang) { + var len, perform_rename; + perform_rename = (function(_this) { + return function() { + if (full_name != null) { + if (!node.isLiteral) { + _this.remove_from_nameless(node); + } + } else { + if (!node.isLiteral) { + _this.add_to_nameless(node); + } + full_name = node.lid || node.id; } - full_name = node.lid || node.id; - } - if (typeof full_name === 'object') { - // MultiString instances have constructor.name == 'String' - // console.log(full_name.constructor.name, full_name) - return node.name = full_name; - } else { - if (node.name) { - return node.name.set_val_lang(full_name, lang); + if (typeof full_name === 'object') { + return node.name = full_name; } else { - return node.name = new MultiString(full_name, lang); + if (node.name) { + return node.name.set_val_lang(full_name, lang); + } else { + return node.name = new MultiString(full_name, lang); + } } - } - }; - if (node.state && (node.state.id === 'shelved')) { - // Alter calls the callback add_name in the midst of an operation - // which is likely to move subj_n from its current position in - // the shelved_set. The shelved_set is the only one which is - // sorted by name and as a consequence is the only one able to - // be confused by the likely shift in alphabetic position of a - // node. For the sake of efficiency we "alter()" the position - // of the node rather than do shelved_set.resort() after the - // renaming. + }; + })(this); + if (node.state && node.state.id === 'shelved') { this.shelved_set.alter(node, perform_rename); this.tick("Tick in set_name"); } else { perform_rename(); } - //node.name ?= full_name # set it if blank - const len = this.truncate_labels_to; - if ((len == null)) { + len = this.truncate_labels_to; + if (len == null) { alert("len not set"); } if (len > 0) { - node.pretty_name = node.name.substr(0, len); // truncate + node.pretty_name = node.name.substr(0, len); } else { node.pretty_name = node.name; } node.scroll_offset = 0; - } + }; + + Huviz.prototype.scroll_spacer = " "; - scroll_pretty_name(node) { - let limit; + Huviz.prototype.scroll_pretty_name = function(node) { + var limit, should_scroll, spacer, wrapped; if (this.truncate_labels_to >= node.name.length) { limit = node.name.length; } else { limit = this.truncate_labels_to; } - const should_scroll = (limit > 0) && (limit < node.name.length); + should_scroll = limit > 0 && limit < node.name.length; if (!should_scroll) { return; } - if (true) { // node.label_truncated_to - const spacer = this.scroll_spacer; + if (true) { + spacer = this.scroll_spacer; if (!node.scroll_offset) { node.scroll_offset = 1; } else { node.scroll_offset += 1; - if (node.scroll_offset > (node.name.length + spacer.length)) { //limit + if (node.scroll_offset > node.name.length + spacer.length) { node.scroll_offset = 0; } } - let wrapped = ""; - while (wrapped.length < (3 * limit)) { - wrapped += node.name + spacer; + wrapped = ""; + while (wrapped.length < 3 * limit) { + wrapped += node.name + spacer; } return node.pretty_name = wrapped.substr(node.scroll_offset, limit); } - } - // if node.pretty_name.length > limit - // alert("TOO BIG") - // if node.pretty_name.length < 1 - // alert("TOO SMALL") - unscroll_pretty_name(node) { + }; + + Huviz.prototype.unscroll_pretty_name = function(node) { return this.set_name(node, node.name); - } + }; - infer_edge_end_types(edge) { - if (edge.source.type == null) { edge.source.type = 'Thing'; } - if (edge.target.type == null) { edge.target.type = 'Thing'; } - // infer type of source based on the range of the predicate - const ranges = this.ontology.range[edge.predicate.lid]; + Huviz.prototype.infer_edge_end_types = function(edge) { + var domain_lid, ranges, _base, _base1; + if ((_base = edge.source).type == null) { + _base.type = 'Thing'; + } + if ((_base1 = edge.target).type == null) { + _base1.type = 'Thing'; + } + ranges = this.ontology.range[edge.predicate.lid]; if (ranges != null) { this.try_to_set_node_type(edge.target, ranges[0]); } - // infer type of source based on the domain of the predicate - const domain_lid = this.ontology.domain[edge.predicate.lid]; + domain_lid = this.ontology.domain[edge.predicate.lid]; if (domain_lid != null) { return this.try_to_set_node_type(edge.source, domain_lid); } - } + }; - make_Edge_id(subj_n, obj_n, pred_n) { - return ([subj_n, pred_n, obj_n].map((a) => a.lid)).join(' '); - } + Huviz.prototype.make_Edge_id = function(subj_n, obj_n, pred_n) { + var a; + return ((function() { + var _i, _len, _ref, _results; + _ref = [subj_n, pred_n, obj_n]; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + a = _ref[_i]; + _results.push(a.lid); + } + return _results; + })()).join(' '); + }; - get_or_create_Edge(subj_n, obj_n, pred_n, cntx_n) { - const edge_id = this.make_Edge_id(subj_n, obj_n, pred_n); - let edge = this.edges_by_id[edge_id]; - if ((edge == null)) { + Huviz.prototype.get_or_create_Edge = function(subj_n, obj_n, pred_n, cntx_n) { + var edge, edge_id; + edge_id = this.make_Edge_id(subj_n, obj_n, pred_n); + edge = this.edges_by_id[edge_id]; + if (edge == null) { this.edge_count++; edge = new Edge(subj_n, obj_n, pred_n, cntx_n); this.edges_by_id[edge_id] = edge; } return edge; - } + }; - add_edge(edge) { + Huviz.prototype.add_edge = function(edge) { if (edge.id.match(/Universal$/)) { console.log("add", edge.id); } - // TODO(smurp) should .links_from and .links_to be SortedSets? Yes. Right? this.add_to(edge, edge.source.links_from); this.add_to(edge, edge.target.links_to); return edge; - } + }; - delete_edge(e) { + Huviz.prototype.delete_edge = function(e) { this.remove_link(e.id); this.remove_from(e, e.source.links_from); this.remove_from(e, e.target.links_to); delete this.edges_by_id[e.id]; return null; - } + }; - try_to_set_node_type(node, type_uri) { - // if not type_uri.includes(':') - // debugger - // throw new Error("try_to_set_node_type() expects an URL, not #{type_uri}") - const type_lid = uniquer(type_uri); // should ensure uniqueness + Huviz.prototype.try_to_set_node_type = function(node, type_uri) { + var prev_type, type_lid; + type_lid = uniquer(type_uri); if (!node._types) { node._types = []; } - if (!(Array.from(node._types).includes(type_lid))) { + if (!(__indexOf.call(node._types, type_lid) >= 0)) { node._types.push(type_lid); } - const prev_type = node.type; + prev_type = node.type; node.type = type_lid; if (prev_type !== type_lid) { - return this.assign_types(node); // if 1 then more data shown + return this.assign_types(node); } - } + }; - get_context() { + Huviz.prototype.report_every = 100; + + Huviz.prototype.get_context = function() { return this.data_uri || this.DEFAULT_CONTEXT; - } + }; - parseAndShowTTLData(data, textStatus, callback) { - // modelled on parseAndShowNQStreamer - //console.log("parseAndShowTTLData",data) - const parse_start_time = new Date(); - const context = this.get_context(); - if ((GreenerTurtle != null) && (this.turtle_parser === 'GreenerTurtle')) { - //console.log("GreenTurtle() started") - //@G = new GreenerTurtle().parse(data, "text/turtle") + Huviz.prototype.parseAndShowTTLData = function(data, textStatus, callback) { + var blurt_msg, context, e, every, frame, msg, obj, parse_start_time, pred, pred_id, quad_count, subj_uri, _i, _len, _ref, _ref1, _ref2; + parse_start_time = new Date(); + context = this.get_context(); + if ((GreenerTurtle != null) && this.turtle_parser === 'GreenerTurtle') { try { this.G = new GreenerTurtle().parse(data, "text/turtle"); - } catch (e) { - const msg = escapeHtml(e.toString()); - const blurt_msg = `

    There has been a problem with the Turtle parser. Check your dataset for errors.

    ${msg}

    `; + } catch (_error) { + e = _error; + msg = escapeHtml(e.toString()); + blurt_msg = "

    There has been a problem with the Turtle parser. Check your dataset for errors.

    " + msg + "

    "; this.blurt(blurt_msg, "error"); return false; } } - let quad_count = 0; - const every = this.report_every; - for (let subj_uri in this.G.subjects) { - //console.log("frame:",frame) - //console.log(frame.predicates) - const frame = this.G.subjects[subj_uri]; - for (let pred_id in frame.predicates) { - const pred = frame.predicates[pred_id]; - for (let obj of Array.from(pred.objects)) { - // this is the right place to convert the ids (URIs) to CURIES - // Or should it be QNames? - // http://www.w3.org/TR/curie/#s_intro + quad_count = 0; + every = this.report_every; + _ref = this.G.subjects; + for (subj_uri in _ref) { + frame = _ref[subj_uri]; + _ref1 = frame.predicates; + for (pred_id in _ref1) { + pred = _ref1[pred_id]; + _ref2 = pred.objects; + for (_i = 0, _len = _ref2.length; _i < _len; _i++) { + obj = _ref2[_i]; if (every === 1) { - this.show_state_msg(`
  • ${frame.id}
  • ${pred.id}
  • ${obj.value}`); + this.show_state_msg("
  • " + frame.id + "
  • " + pred.id + "
  • " + obj.value); console.log("===========================\n #", quad_count, " subj:", frame.id, "\n pred:", pred.id, "\n obj.value:", obj.value); } else { - if ((quad_count % every) === 0) { + if (quad_count % every === 0) { this.show_state_msg("parsed relation: " + quad_count); } } @@ -11478,7 +9913,7 @@ WHERE { this.add_quad({ s: frame.id, p: pred.id, - o: obj, // keys: type,value[,language] + o: obj, g: context }); } @@ -11486,149 +9921,155 @@ WHERE { } this.dump_stats(); return this.after_file_loaded('stream', callback); - } + }; - dump_stats() { + Huviz.prototype.dump_stats = function() { console.log("object_value_types:", this.object_value_types); return console.log("unique_pids:", this.unique_pids); - } - - parseAndShowTurtle(data, textStatus) { - let msg = "data was " + data.length + " bytes"; - const parse_start_time = new Date(); + }; - if ((GreenerTurtle != null) && (this.turtle_parser === 'GreenerTurtle')) { + Huviz.prototype.parseAndShowTurtle = function(data, textStatus) { + var key, msg, parse_end_time, parse_start_time, parse_time, parser, predicates, prop_name, prop_obj, show_end_time, show_start_time, show_time, siz, value, _i, _len, _ref; + msg = "data was " + data.length + " bytes"; + parse_start_time = new Date(); + if ((GreenerTurtle != null) && this.turtle_parser === 'GreenerTurtle') { this.G = new GreenerTurtle().parse(data, "text/turtle"); console.log("GreenTurtle"); - } else if (this.turtle_parser === 'N3') { console.log("N3"); - //N3 = require('N3') console.log("n3", N3); - const predicates = {}; - const parser = N3.Parser(); - parser.parse(data, (err,trip,pref) => { - console.log(trip); - if (pref) { - console.log(pref); - } - if (trip) { - return this.add_quad(trip); - } else { - return console.log(err); - } - }); - - //console.log("my_graph", @my_graph) + predicates = {}; + parser = N3.Parser(); + parser.parse(data, (function(_this) { + return function(err, trip, pref) { + console.log(trip); + if (pref) { + console.log(pref); + } + if (trip) { + return _this.add_quad(trip); + } else { + return console.log(err); + } + }; + })(this)); console.log('==================================='); - for (let prop_name of ['predicates','subjects','objects']) { - var prop_obj = this.my_graph[prop_name]; - console.log(prop_name,((() => { - const result = []; - for (let key in prop_obj) { - const value = prop_obj[key]; - result.push(key); + _ref = ['predicates', 'subjects', 'objects']; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + prop_name = _ref[_i]; + prop_obj = this.my_graph[prop_name]; + console.log(prop_name, ((function() { + var _results; + _results = []; + for (key in prop_obj) { + value = prop_obj[key]; + _results.push(key); } - return result; - })()).length,prop_obj); + return _results; + })()).length, prop_obj); } console.log('==================================='); } - //console.log "Predicates",(key for key,value of my_graph.predicates).length,my_graph.predicates - //console.log "Subjects",my_graph.subjects.length,my_graph.subjects - //console.log "Objects",my_graph.objects.length,my_graph.objects - - const parse_end_time = new Date(); - const parse_time = (parse_end_time - parse_start_time) / 1000; - const siz = this.roughSizeOfObject(this.G); + parse_end_time = new Date(); + parse_time = (parse_end_time - parse_start_time) / 1000; + siz = this.roughSizeOfObject(this.G); msg += " resulting in a graph of " + siz + " bytes"; msg += " which took " + parse_time + " seconds to parse"; - if (this.verbosity >= this.COARSE) { console.log(msg); } - const show_start_time = new Date(); + if (this.verbosity >= this.COARSE) { + console.log(msg); + } + show_start_time = new Date(); this.showGraph(this.G); - const show_end_time = new Date(); - const show_time = (show_end_time - show_start_time) / 1000; + show_end_time = new Date(); + show_time = (show_end_time - show_start_time) / 1000; msg += " and " + show_time + " sec to show"; - if (this.verbosity >= this.COARSE) { console.log(msg); } + if (this.verbosity >= this.COARSE) { + console.log(msg); + } this.text_cursor.set_cursor("default"); return $("#status").text(""); - } + }; - choose_everything() { - const cmd = new gcl.GraphCommand(this, { + Huviz.prototype.choose_everything = function() { + var cmd; + cmd = new gcl.GraphCommand(this, { verbs: ['choose'], classes: ['Thing'], every_class: true - } - ); + }); this.gclc.run(cmd); return this.tick("Tick in choose_everything"); - } + }; + + Huviz.prototype.remove_framing_quotes = function(s) { + return s.replace(/^\"/, "").replace(/\"$/, ""); + }; - remove_framing_quotes(s) { return s.replace(/^\"/,"").replace(/\"$/,""); } - parseAndShowNQStreamer(uri, callback) { - // turning a blob (data) into a stream - // http://stackoverflow.com/questions/4288759/asynchronous-for-cycle-in-javascript - // http://www.dustindiaz.com/async-method-queues/ - const owl_type_map = { - uri: RDF_object, + Huviz.prototype.parseAndShowNQStreamer = function(uri, callback) { + var owl_type_map, quad_count, worker; + owl_type_map = { + uri: RDF_object, literal: RDF_literal }; - const worker = new Worker('/huviz/xhr_readlines_worker.js'); - let quad_count = 0; - worker.addEventListener('message', e => { - let msg = null; - if (e.data.event === 'line') { - quad_count++; - this.show_state_msg("

    Parsing...

    " + uri + "

    "); - //if quad_count % 100 is 0 - //@show_state_msg("parsed relation " + quad_count) - const q = parseQuadLine(e.data.line); - if (q) { - q.s = q.s.raw; - q.p = q.p.raw; - q.g = q.g.raw; - q.o = { - type: owl_type_map[q.o.type], - value: unescape_unicode(this.remove_framing_quotes(q.o.toString())) - }; - this.add_quad(q); + worker = new Worker('/huviz/xhr_readlines_worker.js'); + quad_count = 0; + worker.addEventListener('message', (function(_this) { + return function(e) { + var msg, q; + msg = null; + if (e.data.event === 'line') { + quad_count++; + _this.show_state_msg("

    Parsing...

    " + uri + "

    "); + q = parseQuadLine(e.data.line); + if (q) { + q.s = q.s.raw; + q.p = q.p.raw; + q.g = q.g.raw; + q.o = { + type: owl_type_map[q.o.type], + value: unescape_unicode(_this.remove_framing_quotes(q.o.toString())) + }; + _this.add_quad(q); + } + } else if (e.data.event === 'start') { + msg = "starting to split " + uri; + _this.show_state_msg("

    Starting to split...

    " + uri + "

    "); + _this.node_count = e.data.numLines; + } else if (e.data.event === 'finish') { + msg = "finished_splitting " + uri; + _this.show_state_msg("done loading"); + _this.after_file_loaded(uri, callback); + } else { + msg = "unrecognized NQ event:" + e.data.event; } - } else if (e.data.event === 'start') { - msg = "starting to split " + uri; - this.show_state_msg("

    Starting to split...

    " + uri + "

    "); - this.node_count = e.data.numLines; - } else if (e.data.event === 'finish') { - msg = "finished_splitting " + uri; - this.show_state_msg("done loading"); - this.after_file_loaded(uri, callback); - } else { - msg = "unrecognized NQ event:" + e.data.event; - } - if (msg != null) { - return this.blurt(msg); - } + if (msg != null) { + return _this.blurt(msg); + } + }; + })(this)); + return worker.postMessage({ + uri: uri }); - return worker.postMessage({uri}); - } + }; - parse_and_show_NQ_file(data, callback) { - //TODO There is currently no error catcing on local nq files - const owl_type_map = { - uri: RDF_object, + Huviz.prototype.parse_and_show_NQ_file = function(data, callback) { + var allLines, line, owl_type_map, q, quad_count, _i, _len; + owl_type_map = { + uri: RDF_object, literal: RDF_literal }; - let quad_count = 0; - const allLines = data.split(/\r\n|\n/); - for (let line of Array.from(allLines)) { + quad_count = 0; + allLines = data.split(/\r\n|\n/); + for (_i = 0, _len = allLines.length; _i < _len; _i++) { + line = allLines[_i]; quad_count++; - const q = parseQuadLine(line); + q = parseQuadLine(line); if (q) { q.s = q.s.raw; q.p = q.p.raw; q.g = q.g.raw; q.o = { - type: owl_type_map[q.o.type], + type: owl_type_map[q.o.type], value: unescape_unicode(this.remove_framing_quotes(q.o.toString())) }; this.add_quad(q); @@ -11636,605 +10077,565 @@ WHERE { } this.local_file_data = ""; return this.after_file_loaded('local file', callback); - } + }; - DUMPER(data) { + Huviz.prototype.DUMPER = function(data) { return console.log(data); - } + }; - fetchAndShow(url, callback) { - let msg; + Huviz.prototype.fetchAndShow = function(url, callback) { + var msg, the_parser; this.show_state_msg("fetching " + url); - let the_parser = this.parseAndShowNQ; //++++Why does the parser default to NQ? + the_parser = this.parseAndShowNQ; if (url.match(/.ttl/)) { - the_parser = this.parseAndShowTTLData; // does not stream - } else if (url.match(/.(nq|nt)/)) { // TODO Retire this in favor of parseAndShowFile + the_parser = this.parseAndShowTTLData; + } else if (url.match(/.(nq|nt)/)) { the_parser = this.parseAndShowNQ; } else if (url.match(/.(jsonld|nq|nquads|nt|n3|trig|ttl|rdf|xml)$/)) { the_parser = this.parseAndShowFile; - } else { //File not valid - //abort with message - // NOTE This only catches URLs that do not have a valid file name; - // nothing about actual file format - msg = `Could not load ${url}. The data file format is not supported! ` + - "Only accepts jsonld|nq|nquads|nt|n3|trig|ttl|rdf|xml extensions."; + } else { + msg = ("Could not load " + url + ". The data file format is not supported! ") + "Only accepts jsonld|nq|nquads|nt|n3|trig|ttl|rdf|xml extensions."; this.hide_state_msg(); this.blurt(msg, 'error'); - $('#'+this.get_data_ontology_display_id()).remove(); + $('#' + this.get_data_ontology_display_id()).remove(); this.reset_dataset_ontology_loader(); - //@init_resource_menus() return; } - if (the_parser === this.parseAndShowFile) { this.parseAndShowFile(url, callback); return; } - - // Deal with the case that the file is cached inside the datasetDB as a result - // of having been dragged and droppped from the local disk and added to the datasetDB. - if (url.startsWith('file:///') || (url.indexOf('/') === -1)) { // ie it is a local file - this.get_resource_from_db(url, (err, rsrcRec) => { - if (rsrcRec != null) { - the_parser(rsrcRec.data); - return; // REVIEW ensure that proper try catch is happening - } - this.blurt(err || `'${url} was not found in your DATASET menu. Provide it and reload this page`); - this.reset_dataset_ontology_loader(); - }); + if (url.startsWith('file:///') || url.indexOf('/') === -1) { + this.get_resource_from_db(url, (function(_this) { + return function(err, rsrcRec) { + if (rsrcRec != null) { + the_parser(rsrcRec.data); + return; + } + _this.blurt(err || ("'" + url + " was not found in your DATASET menu. Provide it and reload this page")); + _this.reset_dataset_ontology_loader(); + }; + })(this)); return; } - if (the_parser === this.parseAndShowNQ) { this.parseAndShowNQStreamer(url, callback); return; } - return $.ajax({ - url, - success: (data, textStatus) => { - the_parser(data, textStatus, callback); - //@fire_fileloaded_event(url) ## should call after_file_loaded(url, callback) within the_parser - return this.hide_state_msg(); - }, - error: (jqxhr, textStatus, errorThrown) => { - console.log(url, errorThrown); - if (!errorThrown) { - errorThrown = "Cross-Origin error"; - } - msg = errorThrown + " while fetching dataset " + url; - this.hide_state_msg(); - $('#'+this.get_data_ontology_display_id()).remove(); - this.blurt(msg, 'error'); // trigger this by goofing up one of the URIs in cwrc_data.json - return this.reset_dataset_ontology_loader(); - } + url: url, + success: (function(_this) { + return function(data, textStatus) { + the_parser(data, textStatus, callback); + return _this.hide_state_msg(); + }; + })(this), + error: (function(_this) { + return function(jqxhr, textStatus, errorThrown) { + console.log(url, errorThrown); + if (!errorThrown) { + errorThrown = "Cross-Origin error"; + } + msg = errorThrown + " while fetching dataset " + url; + _this.hide_state_msg(); + $('#' + _this.get_data_ontology_display_id()).remove(); + _this.blurt(msg, 'error'); + return _this.reset_dataset_ontology_loader(); + }; + })(this) }); - } - //TODO Reset titles on page + }; - log_query_with_timeout(qry, timeout, fillColor, bgColor) { - const queryManager = this.log_query(qry); + Huviz.prototype.log_query_with_timeout = function(qry, timeout, fillColor, bgColor) { + var queryManager; + queryManager = this.log_query(qry); queryManager.anim = this.animate_sparql_query(queryManager.preElem, timeout, fillColor, bgColor); return queryManager; - } + }; - log_query(qry) { + Huviz.prototype.log_query = function(qry) { return this.gclui.push_sparqlQuery_onto_log(qry); - } - - run_little_test_query() { - const littleTestQuery = "SELECT * WHERE {?s ?o ?p} LIMIT 1"; + }; + Huviz.prototype.run_little_test_query = function() { + var littleTestQuery; + littleTestQuery = "SELECT * WHERE {?s ?o ?p} LIMIT 1"; return $.ajax({ method: 'GET', url: url + '?query=' + encodeURIComponent(littleTestQuery), headers: { 'Accept': 'application/sparql-results+json' }, - success: (data, textStatus, jqXHR) => { - console.log("This a little repsponse test: " + textStatus); - console.log(jqXHR); - console.log(jqXHR.getAllResponseHeaders(data)); - return console.log(data); - }, - error: (jqxhr, textStatus, errorThrown) => { - console.log(url, errorThrown); - return console.log(jqXHR.getAllResponseHeaders(data)); - } + success: (function(_this) { + return function(data, textStatus, jqXHR) { + console.log("This a little repsponse test: " + textStatus); + console.log(jqXHR); + console.log(jqXHR.getAllResponseHeaders(data)); + return console.log(data); + }; + })(this), + error: (function(_this) { + return function(jqxhr, textStatus, errorThrown) { + console.log(url, errorThrown); + return console.log(jqXHR.getAllResponseHeaders(data)); + }; + })(this) }); - } - - run_managed_query_abstract(args) { - // Reference: https://www.w3.org/TR/sparql11-protocol/ - if (args == null) { args = {}; } - if (args.success_handler == null) { args.success_handler = noop; } - if (args.error_callback == null) { args.error_callback = noop; } - if (args.timeout == null) { args.timeout = this.get_sparql_timeout_msec(); } + }; - const queryManager = this.log_query_with_timeout(args.query, args.timeout); + Huviz.prototype.run_managed_query_abstract = function(args) { + var queryManager; + if (args == null) { + args = {}; + } + if (args.success_handler == null) { + args.success_handler = noop; + } + if (args.error_callback == null) { + args.error_callback = noop; + } + if (args.timeout == null) { + args.timeout = this.get_sparql_timeout_msec(); + } + queryManager = this.log_query_with_timeout(args.query, args.timeout); queryManager.args = args; return queryManager; - } + }; - run_managed_query_ajax(args) { - const {query, serverUrl} = args; - const queryManager = this.run_managed_query_abstract(args); - const {success_handler, error_callback, timeout} = args; - // These POST settings work for: CWRC, WWI open, on DBpedia, and Open U.K. - // but not on Bio Database - const more = "&timeout=" + timeout; - // TODO This should be decrufted - const ajax_settings = { //TODO Currently this only works on CWRC Endpoint + Huviz.prototype.run_managed_query_ajax = function(args) { + var ajax_settings, error_callback, more, query, queryManager, serverUrl, success_handler, timeout; + query = args.query, serverUrl = args.serverUrl; + queryManager = this.run_managed_query_abstract(args); + success_handler = args.success_handler, error_callback = args.error_callback, timeout = args.timeout; + more = "&timeout=" + timeout; + ajax_settings = { 'method': 'GET', 'url': serverUrl + '?query=' + encodeURIComponent(query) + more, - 'headers' : { - // This is only required for CWRC - not accepted by some Endpoints - //'Content-Type': 'application/sparql-query' + 'headers': { 'Accept': 'application/sparql-results+json' } }; - if (serverUrl === "http://sparql.cwrc.ca/sparql") { // Hack to make CWRC setup work properly + if (serverUrl === "http://sparql.cwrc.ca/sparql") { ajax_settings.headers = { - 'Content-Type' : 'application/sparql-query', + 'Content-Type': 'application/sparql-query', 'Accept': 'application/sparql-results+json' }; } if (serverUrl.includes('wikidata')) { - // these don't solve CORS issues but could solve CORB issues ajax_settings.headers.Accept = "text/tab-separated-values"; ajax_settings.headers.Accept = "text/csv"; } - queryManager.xhr = $.ajax({ - timeout, + timeout: timeout, method: ajax_settings.method, url: ajax_settings.url, headers: ajax_settings.headers, - success: (data, textStatus, jqXHR) => { - queryManager.cancelAnimation(); - try { - return success_handler(data, textStatus, jqXHR, queryManager); - } catch (e) { - return queryManager.fatalError(e); - } - }, - error: (jqxhr, textStatus, errorThrown) => { - if (!errorThrown) { - errorThrown = "Cross-Origin error"; - } - const msg = errorThrown + " while fetching " + serverUrl; - $('#'+this.get_data_ontology_display_id()).remove(); - queryManager.fatalError(msg); - if (error_callback != null) { - return error_callback(jqxhr, textStatus, errorThrown, queryManager); - } - } + success: (function(_this) { + return function(data, textStatus, jqXHR) { + var e; + queryManager.cancelAnimation(); + try { + return success_handler(data, textStatus, jqXHR, queryManager); + } catch (_error) { + e = _error; + return queryManager.fatalError(e); + } + }; + })(this), + error: (function(_this) { + return function(jqxhr, textStatus, errorThrown) { + var msg; + if (!errorThrown) { + errorThrown = "Cross-Origin error"; + } + msg = errorThrown + " while fetching " + serverUrl; + $('#' + _this.get_data_ontology_display_id()).remove(); + queryManager.fatalError(msg); + if (error_callback != null) { + return error_callback(jqxhr, textStatus, errorThrown, queryManager); + } + }; + })(this) }); - return queryManager; - } + }; - run_managed_query_worker(qry, serverUrl, args) { + Huviz.prototype.run_managed_query_worker = function(qry, serverUrl, args) { + var queryManager; args.query = qry; args.serverUrl = serverUrl; - const queryManager = this.run_managed_query_abstract(args); + queryManager = this.run_managed_query_abstract(args); return queryManager; - } + }; - sparql_graph_query_and_show__trigger(url) { - const selectId = this.endpoint_loader.select_id; + Huviz.prototype.sparql_graph_query_and_show__trigger = function(url) { + var selectId; + selectId = this.endpoint_loader.select_id; this.sparql_graph_query_and_show(url, selectId); - //console.log @dataset_loader - $(`#${this.dataset_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); - $(`#${this.ontology_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); - return $(`#${this.script_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); - } + $("#" + this.dataset_loader.uniq_id).children('select').prop('disabled', 'disabled'); + $("#" + this.ontology_loader.uniq_id).children('select').prop('disabled', 'disabled'); + return $("#" + this.script_loader.uniq_id).children('select').prop('disabled', 'disabled'); + }; - sparql_graph_query_and_show(url, id, callback) { - const qry = `\ -# sparql_graph_query_and_show() -PREFIX rdfs: -SELECT ?g ?label -WHERE { - GRAPH ?g { } . - OPTIONAL {?g rdfs:label ?label} -} -ORDER BY ?g\ -`; - //alert("sparql_graph_query_and_show() id: #{id}") - // these are shared between success and error handlers - const spinner = $(`#sparqlGraphSpinner-${id}`); - spinner.css('display','block'); - const graphSelector = `#sparqlGraphOptions-${id}`; + Huviz.prototype.sparql_graph_query_and_show = function(url, id, callback) { + var args, graphSelector, handle_graphsNotFound, make_error_callback, make_success_handler, qry, spinner; + qry = "# sparql_graph_query_and_show()\nPREFIX rdfs: \nSELECT ?g ?label\nWHERE {\n GRAPH ?g { } .\n OPTIONAL {?g rdfs:label ?label}\n}\nORDER BY ?g"; + spinner = $("#sparqlGraphSpinner-" + id); + spinner.css('display', 'block'); + graphSelector = "#sparqlGraphOptions-" + id; $(graphSelector).parent().css('display', 'none'); this.sparqlQryInput_hide(); - // LOAD button should be disabled while the search for graphs is happening this.disable_go_button(); - const handle_graphsNotFound = () => { - $(graphSelector).parent().css('display', 'none'); - this.reset_endpoint_form(true); - return this.enable_go_button(); - }; - - const make_success_handler = () => { - return (data, textStatus, jqXHR, queryManager) => { - let json_data; - const json_check = typeof data; - if (json_check === 'string') { - json_data = JSON.parse(data); - } else { - json_data = data; - } - - const results = json_data.results.bindings; - queryManager.setResultCount(results.length); - - const graphsNotFound = jQuery.isEmptyObject(results[0]); - if (graphsNotFound) { - handle_graphsNotFound(); - return; - } - let graph_options = ``; - for (let graph of Array.from(results)) { - var label; - if (graph.label != null) { - label = ` (${graph.label.value})`; + handle_graphsNotFound = (function(_this) { + return function() { + $(graphSelector).parent().css('display', 'none'); + _this.reset_endpoint_form(true); + return _this.enable_go_button(); + }; + })(this); + make_success_handler = (function(_this) { + return function() { + return function(data, textStatus, jqXHR, queryManager) { + var graph, graph_options, graphsNotFound, json_check, json_data, label, results, _i, _len; + json_check = typeof data; + if (json_check === 'string') { + json_data = JSON.parse(data); } else { - label = ''; + json_data = data; } - graph_options = graph_options + ``; - } - $(`#sparqlGraphOptions-${id}`).html(graph_options); - $(graphSelector).parent().css('display', 'block'); - this.reset_endpoint_form(true); - return this.disable_go_button(); // disable until a graph or term is picked + results = json_data.results.bindings; + queryManager.setResultCount(results.length); + graphsNotFound = jQuery.isEmptyObject(results[0]); + if (graphsNotFound) { + handle_graphsNotFound(); + return; + } + graph_options = ""; + for (_i = 0, _len = results.length; _i < _len; _i++) { + graph = results[_i]; + if (graph.label != null) { + label = " (" + graph.label.value + ")"; + } else { + label = ''; + } + graph_options = graph_options + (""); + } + $("#sparqlGraphOptions-" + id).html(graph_options); + $(graphSelector).parent().css('display', 'block'); + _this.reset_endpoint_form(true); + return _this.disable_go_button(); + }; }; - }; - - const make_error_callback = () => { - return (jqXHR, textStatus, errorThrown) => { - $(graphSelector).parent().css('display', 'none'); - spinner.css('visibility','hidden'); - //@reset_dataset_ontology_loader() - handle_graphsNotFound(); - return this.reset_endpoint_form(true); + })(this); + make_error_callback = (function(_this) { + return function() { + return function(jqXHR, textStatus, errorThrown) { + $(graphSelector).parent().css('display', 'none'); + spinner.css('visibility', 'hidden'); + handle_graphsNotFound(); + return _this.reset_endpoint_form(true); + }; }; - }; - - const args = { + })(this); + args = { success_handler: make_success_handler(), error_callback: make_error_callback() }; args.query = qry; args.serverUrl = url; return this.sparql_graph_query_and_show_queryManager = this.run_managed_query_ajax(args); - } + }; - sparqlQryInput_hide() { - return this.sparqlQryInput_JQElem.hide(); //css('display', 'none') - } - sparqlQryInput_show() { + Huviz.prototype.sparqlQryInput_hide = function() { + return this.sparqlQryInput_JQElem.hide(); + }; + + Huviz.prototype.sparqlQryInput_show = function() { this.sparqlQryInput_JQElem.show(); - return this.sparqlQryInput_JQElem.css({'color': 'inherit'} ); - } + return this.sparqlQryInput_JQElem.css({ + 'color': 'inherit' + }); + }; - load_endpoint_data_and_show(subject, callback) { + Huviz.prototype.load_endpoint_data_and_show = function(subject, callback) { + var args, fromGraph, make_success_handler, node_limit, qry, url; this.sparql_node_list = []; this.pfm_count('sparql'); - //if @p_display then @performance_dashboard('sparql_request') - const node_limit = this.endpoint_limit_JQElem.val(); - const url = this.endpoint_loader.value; + node_limit = this.endpoint_limit_JQElem.val(); + url = this.endpoint_loader.value; this.endpoint_loader.outstanding_requests = 0; - let fromGraph = ''; + fromGraph = ''; if (this.endpoint_loader.endpoint_graph) { - fromGraph=` FROM <${this.endpoint_loader.endpoint_graph}> `; - } - const qry = `\ -# load_endpoint_data_and_show('${subject}') -SELECT * ${fromGraph} -WHERE { - {<${subject}> ?p ?o} - UNION - {{<${subject}> ?p ?o} . - {?o ?p2 ?o2}} - UNION - {{?s3 ?p3 <${subject}>} . - {?s3 ?p4 ?o4 }} -} -LIMIT ${node_limit}\ -`; - - const make_success_handler = () => { - return (data, textStatus, jqXHR, queryManager) => { - let json_data; - const json_check = typeof data; - if (json_check === 'string') { - json_data = JSON.parse(data); - } else { - json_data = data; - } - queryManager.setResultCount(json_data.length); - this.add_nodes_from_SPARQL(json_data, subject, queryManager); - const endpoint = this.endpoint_loader.value; - this.dataset_loader.disable(); - this.ontology_loader.disable(); - this.replace_loader_display_for_endpoint(endpoint, this.endpoint_loader.endpoint_graph); - this.disable_go_button(); - this.big_go_button.hide(); - return this.after_file_loaded('sparql', callback); + fromGraph = " FROM <" + this.endpoint_loader.endpoint_graph + "> "; + } + qry = "# load_endpoint_data_and_show('" + subject + "')\nSELECT * " + fromGraph + "\nWHERE {\n {<" + subject + "> ?p ?o}\n UNION\n {{<" + subject + "> ?p ?o} .\n {?o ?p2 ?o2}}\n UNION\n {{?s3 ?p3 <" + subject + ">} .\n {?s3 ?p4 ?o4 }}\n}\nLIMIT " + node_limit; + make_success_handler = (function(_this) { + return function() { + return function(data, textStatus, jqXHR, queryManager) { + var endpoint, json_check, json_data; + json_check = typeof data; + if (json_check === 'string') { + json_data = JSON.parse(data); + } else { + json_data = data; + } + queryManager.setResultCount(json_data.length); + _this.add_nodes_from_SPARQL(json_data, subject, queryManager); + endpoint = _this.endpoint_loader.value; + _this.dataset_loader.disable(); + _this.ontology_loader.disable(); + _this.replace_loader_display_for_endpoint(endpoint, _this.endpoint_loader.endpoint_graph); + _this.disable_go_button(); + _this.big_go_button.hide(); + return _this.after_file_loaded('sparql', callback); + }; }; - }; - - const args = { + })(this); + args = { query: qry, serverUrl: url, success_handler: make_success_handler() }; return this.run_managed_query_ajax(args); - } - + }; - add_nodes_from_SPARQL(json_data, subject, queryManager) { - const data = ''; - const context = this.get_context(); - const plainLiteral = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; - //console.log(json_data) + Huviz.prototype.add_nodes_from_SPARQL = function(json_data, subject, queryManager) { + var a_node, context, data, i, language, node, node_list_empty, node_not_in_list, obj_type, obj_val, plainLiteral, pred, q, results, snode, subj, _i, _j, _k, _len, _len1, _len2, _ref, _ref1, _results; + data = ''; + context = this.get_context(); + plainLiteral = "http://www.w3.org/1999/02/22-rdf-syntax-ns#PlainLiteral"; console.log("Adding node (i.e. fully exploring): " + subject); - const results = json_data.results.bindings; + results = json_data.results.bindings; if (queryManager != null) { queryManager.setResultCount(results.length); } - return (() => { - const result = []; - for (let node of Array.from(results)) { - var node_not_in_list, obj_val, pred, subj; - let language = ''; - let obj_type = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; - if (node.s) { - subj = node.s.value; - pred = node.p.value; - obj_val = subject; - } else if (node.o2) { - subj = node.o.value; - pred = node.p2.value; - obj_val = node.o2.value; - if ((node.o2.type === 'literal') || (node.o.type === 'typed-literal')) { - if (node.o2.datatype) { - obj_type = node.o2.datatype; - } else { - obj_type = plainLiteral; - } - if (node.o2["xml:lang"]) { - language = node.o2['xml:lang']; - } + _results = []; + for (_i = 0, _len = results.length; _i < _len; _i++) { + node = results[_i]; + language = ''; + obj_type = "http://www.w3.org/1999/02/22-rdf-syntax-ns#object"; + if (node.s) { + subj = node.s.value; + pred = node.p.value; + obj_val = subject; + } else if (node.o2) { + subj = node.o.value; + pred = node.p2.value; + obj_val = node.o2.value; + if (node.o2.type === 'literal' || node.o.type === 'typed-literal') { + if (node.o2.datatype) { + obj_type = node.o2.datatype; + } else { + obj_type = plainLiteral; } - //console.log "-------- Sub-node -----" + subj + " " + pred + " " + obj_val + " " + obj_type - } else if (node.s3) { - subj = node.s3.value; - pred = node.p4.value; - obj_val = node.o4.value; - if ((node.o4.type === 'literal') || (node.o4.type === 'typed-literal')) { - if (node.o4.datatype) { - obj_type = node.o4.datatype; - } else { - obj_type = plainLiteral; - } - if (node.o4["xml:lang"]) { - language = node.o4['xml:lang']; - } + if (node.o2["xml:lang"]) { + language = node.o2['xml:lang']; } - } else { - subj = subject; - pred = node.p.value; - obj_val = node.o.value; - if ((node.o.type === 'literal') || (node.o.type === 'typed-literal')) { - if (node.o.datatype) { - obj_type = node.o.datatype; - } else { - obj_type = plainLiteral; - } - if (node.o["xml:lang"]) { - language = node.o['xml:lang']; - } + } + } else if (node.s3) { + subj = node.s3.value; + pred = node.p4.value; + obj_val = node.o4.value; + if (node.o4.type === 'literal' || node.o4.type === 'typed-literal') { + if (node.o4.datatype) { + obj_type = node.o4.datatype; + } else { + obj_type = plainLiteral; + } + if (node.o4["xml:lang"]) { + language = node.o4['xml:lang']; } } - const q = { - g: context, - s: subj, - p: pred, - o: { - type: obj_type, - value: obj_val + } else { + subj = subject; + pred = node.p.value; + obj_val = node.o.value; + if (node.o.type === 'literal' || node.o.type === 'typed-literal') { + if (node.o.datatype) { + obj_type = node.o.datatype; + } else { + obj_type = plainLiteral; + } + if (node.o["xml:lang"]) { + language = node.o['xml:lang']; } - }; - if (language) { - q.o.language = language; } - - //console.log(q) - //IF this is a new quad, then add it. Otherwise no. - const node_list_empty = this.sparql_node_list.length; - if (node_list_empty === 0) { // Add first node (because list is empty) - this.sparql_node_list.push(q); - node_not_in_list = true; - } else { - // Check if node is in list - sparql_node_list is used to keep track - // of nodes that have already been loaded by a query so that they - // will not be added again through add_quad. - for (let snode of Array.from(this.sparql_node_list)) { - //TODO - This filtering statement doesn't seem tight (Will not catch nodes that HuViz creates - that's okay I think) - if ((q.s === snode.s) && (q.p === snode.p) && (q.o.value === snode.o.value) && (q.o.type === snode.o.type) && (q.o.language === snode.o.language)) { - node_not_in_list = false; - //console.log("Found it in list so will not send to add_quad") - if ((snode.s === subject) || (snode.o.value === subject)) {//IF node is subject node IS already in list BUT fullly_loaded is false then set to true - for (let i = 0; i < this.all_set.length; i++) { - const a_node = this.all_set[i]; - if (a_node.id === subject) { - this.all_set[i].fully_loaded = true; - } + } + q = { + g: context, + s: subj, + p: pred, + o: { + type: obj_type, + value: obj_val + } + }; + if (language) { + q.o.language = language; + } + node_list_empty = this.sparql_node_list.length; + if (node_list_empty === 0) { + this.sparql_node_list.push(q); + node_not_in_list = true; + } else { + _ref = this.sparql_node_list; + for (_j = 0, _len1 = _ref.length; _j < _len1; _j++) { + snode = _ref[_j]; + if (q.s === snode.s && q.p === snode.p && q.o.value === snode.o.value && q.o.type === snode.o.type && q.o.language === snode.o.language) { + node_not_in_list = false; + if (snode.s === subject || snode.o.value === subject) { + _ref1 = this.all_set; + for (i = _k = 0, _len2 = _ref1.length; _k < _len2; i = ++_k) { + a_node = _ref1[i]; + if (a_node.id === subject) { + this.all_set[i].fully_loaded = true; } } - //console.log("Found node for #{subject} so making it fully_loaded") - //else if snode.o.value is subject - //for a_node, i in @all_set - //console.log("compare: " + a_node.id + " subject: " + subject) - //if a_node.id is subject - //@all_set[i].fully_loaded = true - //console.log "Found object node for #{subject} which should be fully_loaded" - break; - } else { - node_not_in_list = true; } + break; + } else { + node_not_in_list = true; } } - //If node is not in list then add - if (node_not_in_list) { - this.sparql_node_list.push(q); - node_not_in_list = false; - result.push(this.add_quad(q, subject)); - } else { - result.push(undefined); - } } - return result; - })(); - } - //@dump_stats() + if (node_not_in_list) { + this.sparql_node_list.push(q); + node_not_in_list = false; + _results.push(this.add_quad(q, subject)); + } else { + _results.push(void 0); + } + } + return _results; + }; - add_nodes_from_SPARQL_Worker(queryTarget, callback) { - let previous_nodes; + Huviz.prototype.add_nodes_from_SPARQL_Worker = function(queryTarget, callback) { + var graph, local_node_added, previous_nodes, queryManager, queryManagerArgs, query_limit, timeout, url, worker; console.log("Make request for new query and load nodes"); - - const timeout = this.get_sparql_timeout_msec(); - const queryManagerArgs = {timeout}; - let queryManager = null; // so it can be seen across calls to the message listener - + timeout = this.get_sparql_timeout_msec(); + queryManagerArgs = { + timeout: timeout + }; + queryManager = null; this.pfm_count('sparql'); - const url = this.endpoint_loader.value; - if (this.sparql_node_list) { previous_nodes = this.sparql_node_list; } else { previous_nodes = []; } - const graph = this.endpoint_loader.endpoint_graph; - let local_node_added = 0; - const query_limit = 1000; //@endpoint_limit_JQElem.val() - const worker = new Worker('/huviz/sparql_ajax_query.js'); - worker.addEventListener('message', e => { - //console.log e.data - if (e.data.method_name === 'log_query') { - queryManagerArgs.query = "#SPARQL_Worker\n"+e.data.qry; - queryManagerArgs.serverUrl = url; - queryManager = this.run_managed_query_abstract(queryManagerArgs); - //queryManager = @log_query_with_timeout(, timeout) - return; - } else if (e.data.method_name !== 'accept_results') { - const error = new Error("expecting either data.method = 'log_query' or 'accept_results'"); - queryManager.fatalError(error); - throw error; - } - const add_fully_loaded = e.data.fully_loaded_index; - for (let quad of Array.from(e.data.results)) { - //console.log quad - this.add_quad(quad); - this.sparql_node_list.push(quad); // Add the new quads to the official list of added quads - local_node_added++; - } - queryManager.setResultCount(local_node_added); - queryManager.cancelAnimation(); - if (local_node_added) { - queryManager.setSuccessColor(); - } else { - queryManager.setNoneColor(); - } - // Verify through the loaded nodes that they are all properly marked as fully_loaded - for (let i = 0; i < this.all_set.length; i++) { - const a_node = this.all_set[i]; - if (a_node.id === queryTarget) { - this.all_set[i].fully_loaded = true; + url = this.endpoint_loader.value; + if (this.sparql_node_list) { + previous_nodes = this.sparql_node_list; + } else { + previous_nodes = []; + } + graph = this.endpoint_loader.endpoint_graph; + local_node_added = 0; + query_limit = 1000; + worker = new Worker('/huviz/sparql_ajax_query.js'); + worker.addEventListener('message', (function(_this) { + return function(e) { + var a_node, add_fully_loaded, error, i, quad, _i, _j, _len, _len1, _ref, _ref1; + if (e.data.method_name === 'log_query') { + queryManagerArgs.query = "#SPARQL_Worker\n" + e.data.qry; + queryManagerArgs.serverUrl = url; + queryManager = _this.run_managed_query_abstract(queryManagerArgs); + return; + } else if (e.data.method_name !== 'accept_results') { + error = new Error("expecting either data.method = 'log_query' or 'accept_results'"); + queryManager.fatalError(error); + throw error; } - } - this.endpoint_loader.outstanding_requests = this.endpoint_loader.outstanding_requests - 1; - //console.log "Resort the shelf" - this.shelved_set.resort(); - this.tick("Tick in add_nodes_from_SPARQL_worker"); - this.update_all_counts(); - if (callback != null) { - return callback(); - } - }); + add_fully_loaded = e.data.fully_loaded_index; + _ref = e.data.results; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + quad = _ref[_i]; + _this.add_quad(quad); + _this.sparql_node_list.push(quad); + local_node_added++; + } + queryManager.setResultCount(local_node_added); + queryManager.cancelAnimation(); + if (local_node_added) { + queryManager.setSuccessColor(); + } else { + queryManager.setNoneColor(); + } + _ref1 = _this.all_set; + for (i = _j = 0, _len1 = _ref1.length; _j < _len1; i = ++_j) { + a_node = _ref1[i]; + if (a_node.id === queryTarget) { + _this.all_set[i].fully_loaded = true; + } + } + _this.endpoint_loader.outstanding_requests = _this.endpoint_loader.outstanding_requests - 1; + _this.shelved_set.resort(); + _this.tick("Tick in add_nodes_from_SPARQL_worker"); + _this.update_all_counts(); + if (callback != null) { + return callback(); + } + }; + })(this)); return worker.postMessage({ target: queryTarget, - url, - graph, + url: url, + graph: graph, limit: query_limit, - timeout, - previous_nodes}); - } + timeout: timeout, + previous_nodes: previous_nodes + }); + }; - using_sparql() { - // force the return of a boolan with "not not" - return !!((this.endpoint_loader != null) && this.endpoint_loader.value); // This is part of a sparql set - } + Huviz.prototype.using_sparql = function() { + return !!((this.endpoint_loader != null) && this.endpoint_loader.value); + }; - outstanding_sparql_requests_are_capped() { + Huviz.prototype.outstanding_sparql_requests_are_capped = function() { return !(this.endpoint_loader.outstanding_requests < this.max_outstanding_sparql_requests); - } + }; - get_neighbors_via_sparql(chosen, callback) { + Huviz.prototype.get_neighbors_via_sparql = function(chosen, callback) { + var maxReq, msg; if (!chosen.fully_loaded) { - // If there are more than certain number of requests, stop the process - const maxReq = this.max_outstanding_sparql_requests; + maxReq = this.max_outstanding_sparql_requests; if (!this.outstanding_sparql_requests_are_capped()) { this.endpoint_loader.outstanding_requests++; this.add_nodes_from_SPARQL_Worker(chosen.id, callback); console.log("outstanding_requests: " + this.endpoint_loader.outstanding_requests); } else { - const msg = `SPARQL requests capped at ${maxReq}`; - //@blurt(msg, 'alert') + msg = "SPARQL requests capped at " + maxReq; console.info(msg); } } - // if $("#blurtbox").html() - // #console.log "Don't add error message " + message - // console.log "Request counter (over): " + @endpoint_loader.outstanding_requests - // else - // #console.log "Error message " + message - // msg = "There are more than 300 requests in the que. Restricting process. " + message - // @blurt(msg, 'alert') - // message = true - // console.log "Request counter: " + @endpoint_loader.outstanding_requests - } + }; - // Deal with buggy situations where flashing the links on and off - // fixes data structures. Not currently needed. - show_and_hide_links_from_node(d) { + Huviz.prototype.show_and_hide_links_from_node = function(d) { this.show_links_from_node(d); return this.hide_links_from_node(d); - } + }; - get_container_width(pad) { + Huviz.prototype.get_container_width = function(pad) { + var tabs_width, w_width; pad = pad || hpad; - const w_width = (this.container.clientWidth || window.innerWidth || document.documentElement.clientWidth || document.clientWidth) - pad; - let tabs_width = 0; - if (this.tabsJQElem && (this.tabsJQElem.length > 0)) { + w_width = (this.container.clientWidth || window.innerWidth || document.documentElement.clientWidth || document.clientWidth) - pad; + tabs_width = 0; + if (this.tabsJQElem && this.tabsJQElem.length > 0) { tabs_width = this.tabsJQElem.width(); } return this.width = w_width - tabs_width; - } + }; - // Should be refactored to be get_container_height - get_container_height(pad) { + Huviz.prototype.get_container_height = function(pad) { pad = pad || hpad; this.height = (this.container.clientHeight || window.innerHeight || document.documentElement.clientHeight || document.clientHeight) - pad; if (this.args.stay_square) { this.height = this.width; } return this.height; - } + }; - update_graph_radius() { + Huviz.prototype.update_graph_radius = function() { this.graph_region_radius = Math.floor(Math.min(this.width / 2, this.height / 2)); return this.graph_radius = this.graph_region_radius * this.shelf_radius; - } + }; - update_graph_center() { + Huviz.prototype.update_graph_center = function() { this.cy = this.height / 2; if (this.off_center) { this.cx = this.width - this.graph_region_radius; @@ -12243,83 +10644,89 @@ LIMIT ${node_limit}\ } this.my = this.cy * 2; return this.mx = this.cx * 2; - } + }; - update_lariat_zone() { + Huviz.prototype.update_lariat_zone = function() { return this.lariat_center = [this.cx, this.cy]; - } + }; - update_discard_zone() { + Huviz.prototype.update_discard_zone = function() { this.discard_ratio = .1; this.discard_radius = this.graph_radius * this.discard_ratio; - return this.discard_center = [ - this.width - (this.discard_radius * 3), - this.height - (this.discard_radius * 3) - ]; - } + return this.discard_center = [this.width - this.discard_radius * 3, this.height - this.discard_radius * 3]; + }; - set_search_regex(text) { + Huviz.prototype.set_search_regex = function(text) { return this.search_regex = new RegExp(text || "^$", "ig"); - } + }; - update_searchterm() { - const text = $(this).text(); + Huviz.prototype.update_searchterm = function() { + var text; + text = $(this).text(); this.set_search_regex(text); return this.restart(); - } + }; - dump_locations(srch, verbose, func) { + Huviz.prototype.dump_locations = function(srch, verbose, func) { + var pattern; verbose = verbose || false; - const pattern = new RegExp(srch, "ig"); - return nodes.forEach((node, i) => { - if (!node.name.match(pattern)) { - if (verbose) { console.log(pattern, "does not match!", node.name); } - return; - } - if (func) { console.log(func.call(node)); } - if (!func || verbose) { return this.dump_details(node); } - }); - } + pattern = new RegExp(srch, "ig"); + return nodes.forEach((function(_this) { + return function(node, i) { + if (!node.name.match(pattern)) { + if (verbose) { + console.log(pattern, "does not match!", node.name); + } + return; + } + if (func) { + console.log(func.call(node)); + } + if (!func || verbose) { + return _this.dump_details(node); + } + }; + })(this)); + }; - get_node_by_id(node_id, throw_on_fail) { + Huviz.prototype.get_node_by_id = function(node_id, throw_on_fail) { + var obj; throw_on_fail = throw_on_fail || false; - const obj = this.nodes.get_by('id',node_id); + obj = this.nodes.get_by('id', node_id); if ((obj == null) && throw_on_fail) { throw new Error("node with id <" + node_id + "> not found"); } return obj; - } + }; - update_showing_links(n) { - // TODO understand why this is like {Taxon,Predicate}.update_state - // Is this even needed anymore? - const old_status = n.showing_links; + Huviz.prototype.update_showing_links = function(n) { + var old_status; + old_status = n.showing_links; if (n.links_shown.length === 0) { n.showing_links = "none"; } else { - if ((n.links_from.length + n.links_to.length) > n.links_shown.length) { + if (n.links_from.length + n.links_to.length > n.links_shown.length) { n.showing_links = "some"; } else { n.showing_links = "all"; } } if (old_status === n.showing_links) { - return null; // no change, so null + return null; } - // We return true to mean that edges where shown, so - return (old_status === "none") || (n.showing_links === "all"); - } + return old_status === "none" || n.showing_links === "all"; + }; - should_show_link(edge) { - // Edges should not be shown if either source or target are discarded or embryonic. - const ss = edge.source.state; - const ts = edge.target.state; - const d = this.discarded_set; - const e = this.embryonic_set; - return !((ss === d) || (ts === d) || (ss === e) || (ts === e)); - } + Huviz.prototype.should_show_link = function(edge) { + var d, e, ss, ts; + ss = edge.source.state; + ts = edge.target.state; + d = this.discarded_set; + e = this.embryonic_set; + return !(ss === d || ts === d || ss === e || ts === e); + }; - add_link(e) { + Huviz.prototype.add_link = function(e) { this.add_to(e, e.source.links_from); this.add_to(e, e.target.links_to); if (this.should_show_link(e)) { @@ -12328,12 +10735,13 @@ LIMIT ${node_limit}\ this.update_showing_links(e.source); this.update_showing_links(e.target); return this.update_state(e.target); - } + }; - remove_link(edge_id) { - const e = this.links_set.get_by('id', edge_id); - if ((e == null)) { - console.log(`remove_link(${edge_id}) not found!`); + Huviz.prototype.remove_link = function(edge_id) { + var e; + e = this.links_set.get_by('id', edge_id); + if (e == null) { + console.log("remove_link(" + edge_id + ") not found!"); return; } this.remove_from(e, e.source.links_shown); @@ -12344,11 +10752,10 @@ LIMIT ${node_limit}\ this.update_showing_links(e.target); this.update_state(e.target); return this.update_state(e.source); - } + }; - // FIXME it looks like incl_discards is not needed and could be removed - show_link(edge, incl_discards) { - if ((!incl_discards) && ((edge.target.state === this.discarded_set) || (edge.source.state === this.discarded_set))) { + Huviz.prototype.show_link = function(edge, incl_discards) { + if ((!incl_discards) && (edge.target.state === this.discarded_set || edge.source.state === this.discarded_set)) { return; } this.add_to(edge, edge.source.links_shown); @@ -12357,27 +10764,24 @@ LIMIT ${node_limit}\ edge.show(); this.update_state(edge.source); return this.update_state(edge.target); - } - //@gclui.add_shown(edge.predicate.lid,edge) + }; - unshow_link(edge) { - this.remove_from(edge,edge.source.links_shown); - this.remove_from(edge,edge.target.links_shown); + Huviz.prototype.unshow_link = function(edge) { + this.remove_from(edge, edge.source.links_shown); + this.remove_from(edge, edge.target.links_shown); this.links_set.remove(edge); - //console.log("unshowing links from: " + edge.id) - edge.unshow(); // FIXME make unshow call @update_state WHICH ONE? :) + edge.unshow(); this.update_state(edge.source); return this.update_state(edge.target); - } - //@gclui.remove_shown(edge.predicate.lid,edge) + }; - show_links_to_node(n, incl_discards) { + Huviz.prototype.show_links_to_node = function(n, incl_discards) { incl_discards = incl_discards || false; - //if not n.links_to_found - // @find_links_to_node n,incl_discards - n.links_to.forEach((e, i) => { - return this.show_link(e, incl_discards); - }); + n.links_to.forEach((function(_this) { + return function(e, i) { + return _this.show_link(e, incl_discards); + }; + })(this)); this.update_showing_links(n); this.update_state(n); this.force.links(this.links_set); @@ -12385,144 +10789,152 @@ LIMIT ${node_limit}\ console.log("Tick in @force.links(@links_set) show_links_to_node"); } return this.restart(); - } + }; - update_state(node) { - if ((node.state === this.graphed_set) && (node.links_shown.length === 0)) { + Huviz.prototype.update_state = function(node) { + if (node.state === this.graphed_set && node.links_shown.length === 0) { this.shelved_set.acquire(node); this.unpin(node); } - //console.debug("update_state() had to @shelved_set.acquire(#{node.name})",node) - if ((node.state !== this.graphed_set) && (node.links_shown.length > 0)) { - //console.debug("update_state() had to @graphed_set.acquire(#{node.name})",node) + if (node.state !== this.graphed_set && node.links_shown.length > 0) { return this.graphed_set.acquire(node); } - } + }; - hide_links_to_node(n) { - n.links_to.forEach((e, i) => { - this.remove_from(e, n.links_shown); - this.remove_from(e, e.source.links_shown); - e.unshow(); - this.links_set.remove(e); - this.remove_ghosts(e); - this.update_state(e.source); - this.update_showing_links(e.source); - return this.update_showing_links(e.target); - }); + Huviz.prototype.hide_links_to_node = function(n) { + n.links_to.forEach((function(_this) { + return function(e, i) { + _this.remove_from(e, n.links_shown); + _this.remove_from(e, e.source.links_shown); + e.unshow(); + _this.links_set.remove(e); + _this.remove_ghosts(e); + _this.update_state(e.source); + _this.update_showing_links(e.source); + return _this.update_showing_links(e.target); + }; + })(this)); this.update_state(n); this.force.links(this.links_set); if (!this.args.skip_log_tick) { console.log("Tick in @force.links() hide_links_to_node"); } return this.restart(); - } + }; - show_links_from_node(n, incl_discards) { + Huviz.prototype.show_links_from_node = function(n, incl_discards) { incl_discards = incl_discards || false; - //if not n.links_from_found - // @find_links_from_node n - n.links_from.forEach((e, i) => { - return this.show_link(e, incl_discards); - }); + n.links_from.forEach((function(_this) { + return function(e, i) { + return _this.show_link(e, incl_discards); + }; + })(this)); this.update_state(n); this.force.links(this.links_set); if (!this.args.skip_log_tick) { console.log("Tick in @force.links() show_links_from_node"); } return this.restart(); - } - - hide_links_from_node(n) { - n.links_from.forEach((e, i) => { - this.remove_from(e, n.links_shown); - this.remove_from(e, e.target.links_shown); - e.unshow(); - this.links_set.remove(e); - this.remove_ghosts(e); - this.update_state(e.target); - this.update_showing_links(e.source); - return this.update_showing_links(e.target); - }); + }; + Huviz.prototype.hide_links_from_node = function(n) { + n.links_from.forEach((function(_this) { + return function(e, i) { + _this.remove_from(e, n.links_shown); + _this.remove_from(e, e.target.links_shown); + e.unshow(); + _this.links_set.remove(e); + _this.remove_ghosts(e); + _this.update_state(e.target); + _this.update_showing_links(e.source); + return _this.update_showing_links(e.target); + }; + })(this)); this.force.links(this.links_set); if (!this.args.skip_log_tick) { console.log("Tick in @force.links hide_links_from_node"); } return this.restart(); - } + }; - attach_predicate_to_its_parent(a_pred) { - const parent_id = this.ontology.subPropertyOf[a_pred.lid] || 'anything'; + Huviz.prototype.attach_predicate_to_its_parent = function(a_pred) { + var parent_id, parent_pred; + parent_id = this.ontology.subPropertyOf[a_pred.lid] || 'anything'; if (parent_id != null) { - const parent_pred = this.get_or_create_predicate_by_id(parent_id); + parent_pred = this.get_or_create_predicate_by_id(parent_id); a_pred.register_superclass(parent_pred); } - } + }; - get_or_create_predicate_by_id(sid) { - const obj_id = this.make_qname(sid); - let obj_n = this.predicate_set.get_by('id',obj_id); - if ((obj_n == null)) { + Huviz.prototype.get_or_create_predicate_by_id = function(sid) { + var obj_id, obj_n; + obj_id = this.make_qname(sid); + obj_n = this.predicate_set.get_by('id', obj_id); + if (obj_n == null) { obj_n = new Predicate(obj_id); this.predicate_set.add(obj_n); this.attach_predicate_to_its_parent(obj_n); } return obj_n; - } + }; - clean_up_dirty_predicates() { - const pred = this.predicate_set.get_by('id', 'anything'); + Huviz.prototype.clean_up_dirty_predicates = function() { + var pred; + pred = this.predicate_set.get_by('id', 'anything'); if (pred != null) { return pred.clean_up_dirt(); } - } + }; - clean_up_dirty_taxons() { + Huviz.prototype.clean_up_dirty_taxons = function() { if (this.taxonomy.Thing != null) { return this.taxonomy.Thing.clean_up_dirt(); } - } + }; - clean_up_all_dirt_once() { - if (this.clean_up_all_dirt_onceRunner == null) { this.clean_up_all_dirt_onceRunner = new OnceRunner(0, 'clean_up_all_dirt_once'); } + Huviz.prototype.clean_up_all_dirt_once = function() { + if (this.clean_up_all_dirt_onceRunner == null) { + this.clean_up_all_dirt_onceRunner = new OnceRunner(0, 'clean_up_all_dirt_once'); + } return this.clean_up_all_dirt_onceRunner.setTimeout(this.clean_up_all_dirt, 300); - } + }; - clean_up_all_dirt() { - //console.warn("clean_up_all_dirt()") + Huviz.prototype.clean_up_all_dirt = function() { this.clean_up_dirty_taxons(); this.clean_up_dirty_predicates(); - //@regenerate_english() - //setTimeout(@clean_up_dirty_predictes, 500) - //setTimeout(@clean_up_dirty_predictes, 3000) - } + }; - prove_OnceRunner(timeout) { - if (this.prove_OnceRunner_inst == null) { this.prove_OnceRunner_inst = new OnceRunner(30); } - const yahoo = () => alert('yahoo!'); + Huviz.prototype.prove_OnceRunner = function(timeout) { + var yahoo; + if (this.prove_OnceRunner_inst == null) { + this.prove_OnceRunner_inst = new OnceRunner(30); + } + yahoo = function() { + return alert('yahoo!'); + }; return this.prove_OnceRunner_inst.setTimeout(yahoo, timeout); - } + }; - get_or_create_context_by_id(sid) { - const obj_id = this.make_qname(sid); - let obj_n = this.context_set.get_by('id',obj_id); - if ((obj_n == null)) { - obj_n = {id:obj_id}; + Huviz.prototype.get_or_create_context_by_id = function(sid) { + var obj_id, obj_n; + obj_id = this.make_qname(sid); + obj_n = this.context_set.get_by('id', obj_id); + if (obj_n == null) { + obj_n = { + id: obj_id + }; this.context_set.add(obj_n); } return obj_n; - } + }; - get_or_create_node_by_id(uri, name, isLiteral) { - // FIXME OMG must standardize on .lid as the short local id, ie internal id - //node_id = @make_qname(uri) # REVIEW: what about uri: ":" ie the current graph - let node = this.nodes.get_by('id', uri); - if ((node == null)) { + Huviz.prototype.get_or_create_node_by_id = function(uri, name, isLiteral) { + var node; + node = this.nodes.get_by('id', uri); + if (node == null) { node = this.embryonic_set.get_by('id', uri); } - if ((node == null)) { - // at this point the node is embryonic, all we know is its uri! + if (node == null) { node = new Node(uri); if (this.use_lid_as_node_name && (node.name == null) && (name == null)) { name = node.lid; @@ -12530,52 +10942,46 @@ LIMIT ${node_limit}\ if (isLiteral != null) { node.isLiteral = isLiteral; } - if ((node.id == null)) { - alert(`new Node('${uri}') has no id`); + if (node.id == null) { + alert("new Node('" + uri + "') has no id"); } - //@nodes.add(node) this.embryonic_set.add(node); } - if (node.type == null) { node.type = "Thing"; } - if (node.lid == null) { node.lid = uniquer(node.id); } - if ((node.name == null)) { - // FIXME dereferencing of @ontology.label should be by curie, not lid - // if name is empty string, that is acceptable - // if no name is provided, we use the label from the ontology if available - if ((name == null)) { - // Leave defaulting to the use of node.lid to @set_name() itself. - // If we do that here then nothing is recognized as being nameless. + if (node.type == null) { + node.type = "Thing"; + } + if (node.lid == null) { + node.lid = uniquer(node.id); + } + if (node.name == null) { + if (name == null) { name = this.ontology.label[node.lid] || null; } this.set_name(node, name); } return node; - } + }; - develop(node) { - // If the node is embryonic and is ready to hatch, then hatch it. - // In other words if the node is now complete enough to do interesting - // things with, then let it join the company of other complete nodes. + Huviz.prototype.develop = function(node) { if ((node.embryo != null) && this.is_ready(node)) { this.hatch(node); return true; } return false; - } + }; - hatch(node) { - // Take a node from being 'embryonic' to being a fully graphable node - //console.log(node.id+" "+node.name+" is being hatched!") - node.lid = uniquer(node.id); // FIXME ensure uniqueness + Huviz.prototype.hatch = function(node) { + var new_set, start_point; + node.lid = uniquer(node.id); this.embryonic_set.remove(node); - const new_set = this.get_default_set_by_type(node); + new_set = this.get_default_set_by_type(node); if (new_set != null) { new_set.acquire(node); } - this.assign_types(node,"hatch"); - const start_point = [this.cx, this.cy]; + this.assign_types(node, "hatch"); + start_point = [this.cx, this.cy]; node.point(start_point); - node.prev_point([start_point[0]*1.01,start_point[1]*1.01]); + node.prev_point([start_point[0] * 1.01, start_point[1] * 1.01]); this.add_node_ghosts(node); this.update_showing_links(node); this.nodes.add(node); @@ -12583,105 +10989,118 @@ LIMIT ${node_limit}\ this.tick("Tick in hatch"); this.pfm_count('hatch'); return node; - } + }; - get_or_create_transient_node(subjNode, point) { - let isLiteral, name; - const transient_id = '_:_transient'; - let nom = "↪"; + Huviz.prototype.get_or_create_transient_node = function(subjNode, point) { + var isLiteral, name, nom, transient_id, transient_node; + transient_id = '_:_transient'; + nom = "↪"; nom = " "; - const transient_node = this.get_or_create_node_by_id(transient_id, (name = nom), (isLiteral = false)); - this.move_node_to_point(transient_node, {x: subjNode.x, y: subjNode.y}); + transient_node = this.get_or_create_node_by_id(transient_id, (name = nom), (isLiteral = false)); + this.move_node_to_point(transient_node, { + x: subjNode.x, + y: subjNode.y + }); transient_node.radius = 0; transient_node.charge = 20; return transient_node; - } + }; - // REVIEW the need for this method. Called by showGraph but is it called? - make_nodes(g, limit) { + Huviz.prototype.make_nodes = function(g, limit) { + var count, subj, subj_uri, subject, _ref, _results; limit = limit || 0; - let count = 0; - return (() => { - const result = []; - for (let subj_uri in g.subjects) { //my_graph.subjects - //console.log(subj, g.subjects[subj]) if @verbosity >= @DEBUG - //console.log subj_uri - //continue unless subj.match(ids_to_show) - const subj = g.subjects[subj_uri]; - const subject = subj; //g.subjects[subj] - this.get_or_make_node(subject, [ - this.width / 2, - this.height / 2 - ], false); - count++; - if (limit && (count >= limit)) { break; } else { - result.push(undefined); - } + count = 0; + _ref = g.subjects; + _results = []; + for (subj_uri in _ref) { + subj = _ref[subj_uri]; + subject = subj; + this.get_or_make_node(subject, [this.width / 2, this.height / 2], false); + count++; + if (limit && count >= limit) { + break; + } else { + _results.push(void 0); } - return result; - })(); - } + } + return _results; + }; - make_links(g, limit) { + Huviz.prototype.make_links = function(g, limit) { limit = limit || 0; - this.nodes.some((node, i) => { - const subj = node.s; - this.show_links_from_node(this.nodes[i]); - if ((limit > 0) && (this.links_set.length >= limit)) { return true; } - }); + this.nodes.some((function(_this) { + return function(node, i) { + var subj; + subj = node.s; + _this.show_links_from_node(_this.nodes[i]); + if ((limit > 0) && (_this.links_set.length >= limit)) { + return true; + } + }; + })(this)); return this.restart(); - } - - hide_node_links(node) { - node.links_shown.forEach((e, i) => { - this.links_set.remove(e); - if (e.target === node) { - this.remove_from(e, e.source.links_shown); - this.update_state(e.source); - e.unshow(); - this.update_showing_links(e.source); - } else { - this.remove_from(e, e.target.links_shown); - this.update_state(e.target); - e.unshow(); - this.update_showing_links(e.target); - } - return this.remove_ghosts(e); - }); + }; + Huviz.prototype.hide_node_links = function(node) { + node.links_shown.forEach((function(_this) { + return function(e, i) { + _this.links_set.remove(e); + if (e.target === node) { + _this.remove_from(e, e.source.links_shown); + _this.update_state(e.source); + e.unshow(); + _this.update_showing_links(e.source); + } else { + _this.remove_from(e, e.target.links_shown); + _this.update_state(e.target); + e.unshow(); + _this.update_showing_links(e.target); + } + return _this.remove_ghosts(e); + }; + })(this)); node.links_shown = []; this.update_state(node); return this.update_showing_links(node); - } + }; - hide_found_links() { - this.nodes.forEach((node, i) => { - if (node.name.match(search_regex)) { - return this.hide_node_links(node); - } - }); + Huviz.prototype.hide_found_links = function() { + this.nodes.forEach((function(_this) { + return function(node, i) { + if (node.name.match(search_regex)) { + return _this.hide_node_links(node); + } + }; + })(this)); return this.restart(); - } + }; - discard_found_nodes() { - this.nodes.forEach((node, i) => { - if (node.name.match(search_regex)) { return this.discard(node); } - }); + Huviz.prototype.discard_found_nodes = function() { + this.nodes.forEach((function(_this) { + return function(node, i) { + if (node.name.match(search_regex)) { + return _this.discard(node); + } + }; + })(this)); return this.restart(); - } + }; - show_node_links(node) { + Huviz.prototype.show_node_links = function(node) { this.show_links_from_node(node); this.show_links_to_node(node); return this.update_showing_links(node); - } + }; - toggle_display_tech(ctrl, tech) { - let val = undefined; + Huviz.prototype.toggle_display_tech = function(ctrl, tech) { + var val; + val = void 0; tech = ctrl.parentNode.id; if (tech === "use_canvas") { this.use_canvas = !this.use_canvas; - if (!this.use_canvas) { this.clear_canvas(); } + if (!this.use_canvas) { + this.clear_canvas(); + } val = this.use_canvas; } if (tech === "use_svg") { @@ -12695,108 +11114,96 @@ LIMIT ${node_limit}\ ctrl.checked = val; this.tick("Tick in toggle_display_tech"); return true; - } + }; - label(branded) { + Huviz.prototype.label = function(branded) { this.labelled_set.add(branded); - } + }; - unlabel(anonymized) { + Huviz.prototype.unlabel = function(anonymized) { this.labelled_set.remove(anonymized); - } + }; - get_point_from_polar_coords(polar) { - const {range, degrees} = polar; - const radians = (2 * Math.PI * (degrees - 90)) / 360; - return [this.cx + (range * Math.cos(radians) * this.graph_region_radius), - this.cy + (range * Math.sin(radians) * this.graph_region_radius)]; - } + Huviz.prototype.get_point_from_polar_coords = function(polar) { + var degrees, radians, range; + range = polar.range, degrees = polar.degrees; + radians = 2 * Math.PI * (degrees - 90) / 360; + return [this.cx + range * Math.cos(radians) * this.graph_region_radius, this.cy + range * Math.sin(radians) * this.graph_region_radius]; + }; - pin(node, cmd) { + Huviz.prototype.pin = function(node, cmd) { + var pin_point; if (node.state === this.graphed_set) { if ((cmd != null) && cmd.polar_coords) { - const pin_point = this.get_point_from_polar_coords(cmd.polar_coords); + pin_point = this.get_point_from_polar_coords(cmd.polar_coords); node.prev_point(pin_point); } this.pinned_set.add(node); return true; } return false; - } + }; - unpin(node) { - // delete node.pinned_only_while_chosen # do it here in case of direct unpinning + Huviz.prototype.unpin = function(node) { if (node.fixed) { this.pinned_set.remove(node); return true; } return false; - } + }; - pin_at_center(node) { - const cmd = { + Huviz.prototype.pin_at_center = function(node) { + var cmd; + cmd = { polar_coords: { range: 0, degrees: 0 } }; return this.pin(node, cmd); - } + }; - unlink(unlinkee) { - // FIXME discover whether unlink is still needed + Huviz.prototype.unlink = function(unlinkee) { this.hide_links_from_node(unlinkee); this.hide_links_to_node(unlinkee); this.shelved_set.acquire(unlinkee); this.update_showing_links(unlinkee); return this.update_state(unlinkee); - } + }; - // - // The DISCARDED are those nodes which the user has - // explicitly asked to not have drawn into the graph. - // The user expresses this by dropping them in the - // discard_dropzone. - // - discard(goner) { + Huviz.prototype.discard = function(goner) { + var shown; this.unpin(goner); this.unlink(goner); this.discarded_set.acquire(goner); - const shown = this.update_showing_links(goner); + shown = this.update_showing_links(goner); this.unselect(goner); - //@update_state(goner) return goner; - } + }; - undiscard(prodigal) { // TODO(smurp) rename command to 'retrieve' ???? - // see test 'retrieving should only affect nodes which are discarded' + Huviz.prototype.undiscard = function(prodigal) { if (this.discarded_set.has(prodigal)) { this.shelved_set.acquire(prodigal); this.update_showing_links(prodigal); this.update_state(prodigal); } return prodigal; - } + }; - // - // The CHOSEN are those nodes which the user has - // explicitly asked to have the links shown for. - // This is different from those nodes which find themselves - // linked into the graph because another node has been chosen. - // - shelve(goner) { + Huviz.prototype.shelve = function(goner) { + var shownness; this.unpin(goner); this.chosen_set.remove(goner); this.hide_node_links(goner); this.shelved_set.acquire(goner); - const shownness = this.update_showing_links(goner); + shownness = this.update_showing_links(goner); if (goner.links_shown.length > 0) { console.log("shelving failed for", goner); } return goner; - } + }; - suppress(suppressee) { + Huviz.prototype.suppress = function(suppressee) { this.unpin(suppressee); this.chosen_set.remove(suppressee); this.hide_node_links(suppressee); @@ -12804,49 +11211,38 @@ LIMIT ${node_limit}\ this.update_showing_links(suppressee); this.suppressed_set.acquire(suppressee); return suppressee; - } + }; - choose(chosen, callback_after_choosing) { - // If this chosen node is part of a SPARQL query set and not fully loaded then - // fully load it and try this method again, via callback. - if (this.using_sparql() && - !chosen.fully_loaded && - !this.outstanding_sparql_requests_are_capped()) { - const callback_after_getting_neighbors = () => this.choose(chosen, callback_after_choosing); + Huviz.prototype.choose = function(chosen, callback_after_choosing) { + var callback_after_getting_neighbors, shownness; + if (this.using_sparql() && !chosen.fully_loaded && !this.outstanding_sparql_requests_are_capped()) { + callback_after_getting_neighbors = (function(_this) { + return function() { + return _this.choose(chosen, callback_after_choosing); + }; + })(this); this.get_neighbors_via_sparql(chosen, callback_after_getting_neighbors); return; } - - // There is a flag .chosen in addition to the state 'linked' - // because linked means it is in the graph - this.chosen_set.add(chosen); // adding the flag .chosen does not affect the .state - this.nowChosen_set.add(chosen); // adding the flag .nowChosen does not affect the .state - // do it early so add_link shows them otherwise choosing from discards just puts them on the shelf - this.graphed_set.acquire(chosen); // .acquire means DO change the .state to graphed vs shelved etc - + this.chosen_set.add(chosen); + this.nowChosen_set.add(chosen); + this.graphed_set.acquire(chosen); this.show_links_from_node(chosen); this.show_links_to_node(chosen); this.update_state(chosen); - const shownness = this.update_showing_links(chosen); + shownness = this.update_showing_links(chosen); if (callback_after_choosing != null) { callback_after_choosing(); } return chosen; - } + }; - unchoose(unchosen) { - // To unchoose a node is to remove the chosen flag and unshow the edges - // to any nodes which are not themselves chosen. If that means that - // this 'unchosen' node is now no longer graphed, so be it. - // - // remove the node from the chosen set - // loop thru all links_shown - // if neither end of the link is chosen then - // unshow the link - // @unpin unchosen # TODO figure out why this does not cleanse pin + Huviz.prototype.unchoose = function(unchosen) { + var link, _i, _ref; this.chosen_set.remove(unchosen); - for (let i = unchosen.links_shown.length - 1; i >= 0; i--) { - const link = unchosen.links_shown[i]; + _ref = unchosen.links_shown; + for (_i = _ref.length - 1; _i >= 0; _i += -1) { + link = _ref[_i]; if (link != null) { if (!((link.target.chosen != null) || (link.source.chosen != null))) { this.unshow_link(link); @@ -12856,142 +11252,132 @@ LIMIT ${node_limit}\ } } return this.update_state(unchosen); - } + }; - wander__atFirst() { - // Purpose: - // At first, before the verb Wander is executed on any node, we must - // build a SortedSet of the nodes which were wasChosen to compare - // with the SortedSet of nodes which are intendedToBeGraphed as a - // result of the Wander command which is being executed. This method - // is called once, BEFORE iterating through the nodes being wander-ed. + Huviz.prototype.wander__atFirst = function() { + var node, _i, _len, _ref, _results; if (!this.wasChosen_set.clear()) { throw new Error("expecting wasChosen to be empty"); } - return Array.from(this.chosen_set).map((node) => - this.wasChosen_set.add(node)); - } + _ref = this.chosen_set; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node = _ref[_i]; + _results.push(this.wasChosen_set.add(node)); + } + return _results; + }; - wander__atLast() { - // Purpose: - // At last, after all appropriate nodes have been pulled into the graph - // by the Wander verb, it is time to remove wasChosen nodes which - // are not nowChosen. In other words, ungraph those nodes which - // are no longer held in the graph by any recently wandered-to nodes. - // This method is called once, AFTER wander has been called on each node. - const wasRollCall = this.wasChosen_set.roll_call(); - const nowRollCall = this.nowChosen_set.roll_call(); - const removed = this.wasChosen_set.filter(node => { - return !this.nowChosen_set.includes(node); - }); - for (let node of Array.from(removed)) { + Huviz.prototype.wander__atLast = function() { + var node, nowRollCall, removed, wasRollCall, _i, _len; + wasRollCall = this.wasChosen_set.roll_call(); + nowRollCall = this.nowChosen_set.roll_call(); + removed = this.wasChosen_set.filter((function(_this) { + return function(node) { + return !_this.nowChosen_set.includes(node); + }; + })(this)); + for (_i = 0, _len = removed.length; _i < _len; _i++) { + node = removed[_i]; this.unchoose(node); this.wasChosen_set.remove(node); } if (!this.nowChosen_set.clear()) { throw new Error("the nowChosen_set should be empty after clear()"); } - } + }; - wander(chosen) { - // Wander is just the same as Choose (AKA Activate) except afterward it deactivates the - // nodes which were in the chosen_set before but are not in the set being wandered. - // This is accomplished by wander__build_callback() - // See @wander__atFirst and @wander__atLast which are run before and after this one. + Huviz.prototype.wander = function(chosen) { return this.choose(chosen); - } + }; - unwalk(node) { + Huviz.prototype.unwalk = function(node) { this.walked_set.remove(node); delete node.walkedIdx0; - } + }; - walkBackTo(existingStep) { - // note that if existingStep is null (ie a non-node) we will walk back all - const removed = []; - for (let i = this.walked_set.length - 1; i >= 0; i--) { - const pathNode = this.walked_set[i]; + Huviz.prototype.walkBackTo = function(existingStep) { + var pathNode, removed, _i, _ref; + removed = []; + _ref = this.walked_set; + for (_i = _ref.length - 1; _i >= 0; _i += -1) { + pathNode = _ref[_i]; if (pathNode === existingStep) { break; } - // remove these intervening nodes this.unchoose(pathNode); this.shave(pathNode); this.unwalk(pathNode); removed.push(pathNode); } return removed; - } + }; - walkBackAll() { + Huviz.prototype.walkBackAll = function() { return this.walkBackTo(null); - } + }; - walk(nextStep) { - let tooHairy = null; + Huviz.prototype.walk = function(nextStep) { + var do_after_chosen, lastWalked, tooHairy; + tooHairy = null; if (nextStep.walked) { - // 1) if this node already in @walked_set then remove inwtervening nodes - // ie it is already in the path so walk back to it - this.walkBackTo(nextStep); // stop displaying those old links + this.walkBackTo(nextStep); this.choose(nextStep); return; } - - if (this.walked_set.length) { // is there already a walk path in progress? - const lastWalked = this.walked_set.slice(-1)[0]; // find the last node - if (this.nodesAreAdjacent(nextStep, lastWalked)) { // is nextStep linked to lastWalked? - // 2) handle the case of this being the next in a long chain of adjacent nodes - tooHairy = lastWalked; // Shave this guy later. If we do it now, nextStep gets ungraphed! + if (this.walked_set.length) { + lastWalked = this.walked_set.slice(-1)[0]; + if (this.nodesAreAdjacent(nextStep, lastWalked)) { + tooHairy = lastWalked; } else { - // 3) start a new path because nextStep is not connected with the @walked_set - this.walkBackAll(); // clean up the old path completely + this.walkBackAll(); } } - - const do_after_chosen = () => { - if (tooHairy) { // as promised we now deal with the previous terminal node - return this.shave(tooHairy); // ungraph the non-path nodes which were held in the graph by tooHairy - } - }; - - // this should happen to every node added to @walked_set - nextStep.walkedIdx0 = this.walked_set.length; // tell it what position it will have in the path - if (!nextStep.walked) { // It might already be in the path, if not... - this.walked_set.add(nextStep); // add it + do_after_chosen = (function(_this) { + return function() { + if (tooHairy) { + return _this.shave(tooHairy); + } + }; + })(this); + nextStep.walkedIdx0 = this.walked_set.length; + if (!nextStep.walked) { + this.walked_set.add(nextStep); } - this.choose(nextStep, do_after_chosen); // finally, choose nextStep to make it hairy - - // so the javascript is not cluttered with confusing nonsense - } + this.choose(nextStep, do_after_chosen); + }; - nodesAreAdjacent(n1, n2) { - // figure out which node is least connected so we do the least work checking links - let busyNode, link, lonelyNode; + Huviz.prototype.nodesAreAdjacent = function(n1, n2) { + var busyNode, link, lonelyNode, _i, _j, _len, _len1, _ref, _ref1, _ref2, _ref3; if ((n1.links_from.length + n1.links_to.length) > (n2.links_from.length + n2.links_to.length)) { - [lonelyNode, busyNode] = Array.from([n2, n1]); + _ref = [n2, n1], lonelyNode = _ref[0], busyNode = _ref[1]; } else { - [lonelyNode, busyNode] = Array.from([n1, n2]); + _ref1 = [n1, n2], lonelyNode = _ref1[0], busyNode = _ref1[1]; } - // iterate through the outgoing links of the lonlier node, breaking on adjacency - for (link of Array.from(lonelyNode.links_from)) { + _ref2 = lonelyNode.links_from; + for (_i = 0, _len = _ref2.length; _i < _len; _i++) { + link = _ref2[_i]; if (link.target === busyNode) { return true; } } - // iterate through the incoming links of the lonlier node, breaking on adjacency - for (link of Array.from(lonelyNode.links_to)) { + _ref3 = lonelyNode.links_to; + for (_j = 0, _len1 = _ref3.length; _j < _len1; _j++) { + link = _ref3[_j]; if (link.source === busyNode) { return true; } } return false; - } + }; - shave(tooHairy) { - for (let i = tooHairy.links_shown.length - 1; i >= 0; i--) { - const link = tooHairy.links_shown[i]; + Huviz.prototype.shave = function(tooHairy) { + var link, _i, _ref; + _ref = tooHairy.links_shown; + for (_i = _ref.length - 1; _i >= 0; _i += -1) { + link = _ref[_i]; if (link != null) { - if (((link.target.walked == null)) || ((link.source.walked == null))) { + if ((link.target.walked == null) || (link.source.walked == null)) { this.unshow_link(link); } if (!this.edgeIsOnWalkedPath(link)) { @@ -13001,28 +11387,30 @@ LIMIT ${node_limit}\ console.log("there is a null in the .links_shown of", unchosen); } } - return this.update_state(tooHairy); // update the pickers concerning these changes REVIEW needed? - } + return this.update_state(tooHairy); + }; - edgeIsOnWalkedPath(edge) { + Huviz.prototype.edgeIsOnWalkedPath = function(edge) { return this.nodesAreAdjacentOnWalkedPath(edge.target, edge.source); - } + }; - nodesAreAdjacentOnWalkedPath(n1, n2) { - const n1idx0 = n1.walkedIdx0; - const n2idx0 = n2.walkedIdx0; + Huviz.prototype.nodesAreAdjacentOnWalkedPath = function(n1, n2) { + var larger, n1idx0, n2idx0, smaller; + n1idx0 = n1.walkedIdx0; + n2idx0 = n2.walkedIdx0; if ((n1idx0 != null) && (n2idx0 != null)) { - const larger = Math.max(n1idx0, n2idx0); - const smaller = Math.min(n1idx0, n2idx0); - if ((larger - smaller) === 1) { + larger = Math.max(n1idx0, n2idx0); + smaller = Math.min(n1idx0, n2idx0); + if (larger - smaller === 1) { return true; } } return false; - } + }; - distinguish(node) { - const emeritus = this.distinguished_node; + Huviz.prototype.distinguish = function(node) { + var emeritus; + emeritus = this.distinguished_node; if (this.emeritus != null) { delete emeritus._is_distinguished; } @@ -13031,10 +11419,10 @@ LIMIT ${node_limit}\ } this.distinguished_node = node; return emeritus; - } + }; - hide(goner) { - let shownness; + Huviz.prototype.hide = function(goner) { + var shownness; this.unpin(goner); this.chosen_set.remove(goner); this.hidden_set.acquire(goner); @@ -13043,36 +11431,34 @@ LIMIT ${node_limit}\ this.hide_node_links(goner); this.update_state(goner); return shownness = this.update_showing_links(goner); - } + }; - // The verbs SELECT and UNSELECT perhaps don't need to be exposed on the UI - // but they perform the function of manipulating the @selected_set - select(node) { - if ((node.selected == null)) { + Huviz.prototype.select = function(node) { + var msg; + if (node.selected == null) { this.selected_set.add(node); if (node.select != null) { node.select(); return this.recolor_node(node); } else { - const msg = `${node.__proto__.constructor.name} ${node.id} lacks .select()`; + msg = "" + node.__proto__.constructor.name + " " + node.id + " lacks .select()"; throw msg; - return console.error(msg,node); + return console.error(msg, node); } } - } + }; - unselect(node) { + Huviz.prototype.unselect = function(node) { if (node.selected != null) { this.selected_set.remove(node); node.unselect(); this.recolor_node(node); } - } + }; - // These are the EDITING VERBS: connect, spawn, specialize and annotate - connect(node) { + Huviz.prototype.connect = function(node) { if (node !== this.focused_node) { - console.info(`connect('${node.lid}') SKIPPING because it is not the focused node`); + console.info("connect('" + node.lid + "') SKIPPING because it is not the focused node"); return; } this.editui.set_state('seeking_object'); @@ -13081,12 +11467,14 @@ LIMIT ${node_limit}\ this.editui.set_object_node(this.transient_node); this.dragging = this.transient_node; return console.log(this.transient_node.state.id); - } - //alert("connect('#{node.lid}')") + }; - set_unique_color(uniqcolor, set, node) { - if (set.uniqcolor == null) { set.uniqcolor = {}; } - const old_node = set.uniqcolor[uniqcolor]; + Huviz.prototype.set_unique_color = function(uniqcolor, set, node) { + var old_node; + if (set.uniqcolor == null) { + set.uniqcolor = {}; + } + old_node = set.uniqcolor[uniqcolor]; if (old_node) { old_node.color = old_node.uniqucolor_orig; delete old_node.uniqcolor_orig; @@ -13094,11 +11482,11 @@ LIMIT ${node_limit}\ set.uniqcolor[uniqcolor] = node; node.uniqcolor_orig = node.color; node.color = uniqcolor; - } + }; - animate_hunt(array, sought_node, mid_node, prior_node, pos) { - //sought_node.color = 'red' - const pred_uri = 'hunt:trail'; + Huviz.prototype.animate_hunt = function(array, sought_node, mid_node, prior_node, pos) { + var cmd, cmdArgs, edge, pred_uri, trail_pred; + pred_uri = 'hunt:trail'; if (mid_node) { mid_node.color = 'black'; mid_node.radius = 100; @@ -13106,69 +11494,77 @@ LIMIT ${node_limit}\ } if (prior_node) { this.ensure_predicate_lineage(pred_uri); - const trail_pred = this.get_or_create_predicate_by_id(pred_uri); - const edge = this.get_or_create_Edge(mid_node, prior_node, trail_pred, 'http://universal.org'); + trail_pred = this.get_or_create_predicate_by_id(pred_uri); + edge = this.get_or_create_Edge(mid_node, prior_node, trail_pred, 'http://universal.org'); edge.label = JSON.stringify(pos); this.infer_edge_end_types(edge); edge.color = this.gclui.predicate_picker.get_color_forId_byName(trail_pred.lid, 'showing'); this.add_edge(edge); } - //@show_link(edge) if (pos.done) { - const cmdArgs = { + cmdArgs = { verbs: ['show'], regarding: [pred_uri], sets: [this.shelved_set.id] }; - const cmd = new gcl.GraphCommand(this, cmdArgs); + cmd = new gcl.GraphCommand(this, cmdArgs); this.run_command(cmd); return this.clean_up_all_dirt_once(); } - } + }; - hunt(node) { - // Hunt is just a test verb to animate SortedSet.binary_search() for debugging + Huviz.prototype.hunt = function(node) { this.animate_hunt(this.shelved_set, node, null, null, {}); return this.shelved_set.binary_search(node, false, this.animate_hunt); - } + }; - recolor_node(n, default_color) { - if (default_color == null) { default_color = 'black'; } - if (n._types == null) { n._types = []; } - if (this.color_nodes_as_pies && (n._types.length > 1)) { + Huviz.prototype.recolor_node = function(n, default_color) { + var color, taxon_id, _i, _len, _ref, _results; + if (default_color == null) { + default_color = 'black'; + } + if (n._types == null) { + n._types = []; + } + if (this.color_nodes_as_pies && n._types.length > 1) { n._colors = []; - return (() => { - const result = []; - for (let taxon_id of Array.from(n._types)) { - if (typeof(taxon_id) === 'string') { - const color = this.get_color_for_node_type(n, taxon_id) || default_color; - result.push(n._colors.push(color)); - } else { - result.push(undefined); - } + _ref = n._types; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + taxon_id = _ref[_i]; + if (typeof taxon_id === 'string') { + color = this.get_color_for_node_type(n, taxon_id) || default_color; + _results.push(n._colors.push(color)); + } else { + _results.push(void 0); } - return result; - })(); - //n._colors = ['red','orange','yellow','green','blue','purple'] + } + return _results; } else { return n.color = this.get_color_for_node_type(n, n.type); } - } + }; - get_color_for_node_type(node, type) { - const state = ((node.selected != null) && "emphasizing") || "showing"; + Huviz.prototype.get_color_for_node_type = function(node, type) { + var state; + state = (node.selected != null) && "emphasizing" || "showing"; return this.gclui.taxon_picker.get_color_forId_byName(type, state); - } + }; - recolor_nodes() { - // The nodes needing recoloring are all but the embryonic. + Huviz.prototype.recolor_nodes = function() { + var node, _i, _len, _ref, _results; if (this.nodes) { - return Array.from(this.nodes).map((node) => - this.recolor_node(node)); + _ref = this.nodes; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + node = _ref[_i]; + _results.push(this.recolor_node(node)); + } + return _results; } - } + }; - toggle_selected(node) { + Huviz.prototype.toggle_selected = function(node) { if (node.selected != null) { this.unselect(node); } else { @@ -13177,89 +11573,90 @@ LIMIT ${node_limit}\ this.update_all_counts(); this.regenerate_english(); return this.tick("Tick in toggle_selected"); - } + }; - // ======== SNIPPET (INFO BOX) UI ========================================== - get_snippet_url(snippet_id) { + Huviz.prototype.get_snippet_url = function(snippet_id) { if (snippet_id.match(/http\:/)) { return snippet_id; } else { - return `${window.location.origin}${this.get_snippetServer_path(snippet_id)}`; + return "" + window.location.origin + (this.get_snippetServer_path(snippet_id)); } - } + }; - get_snippetServer_path(snippet_id) { - // this relates to index.coffee and the urls for the - let which; - if (this.data_uri != null ? this.data_uri.match('poetesses') : undefined) { - console.info(this.data_uri,this.data_uri.match('poetesses')); + Huviz.prototype.get_snippetServer_path = function(snippet_id) { + var which, _ref; + if ((_ref = this.data_uri) != null ? _ref.match('poetesses') : void 0) { + console.info(this.data_uri, this.data_uri.match('poetesses')); which = "poetesses"; } else { which = "orlando"; } - return `/snippet/${which}/${snippet_id}/`; - } + return "/snippet/" + which + "/" + snippet_id + "/"; + }; - make_edge_inspector_id(edge) { - const id = edge.id.replace(new RegExp(' ','g'), '_'); - //console.log("make_edge_inspector_id()", edge, '==>', id) + Huviz.prototype.make_edge_inspector_id = function(edge) { + var id; + id = edge.id.replace(new RegExp(' ', 'g'), '_'); return id; - } + }; - get_snippet_js_key(snippet_id) { - // This is in case snippet_ids can not be trusted as javascript - // property ids because they might have leading '-' or something. + Huviz.prototype.get_snippet_js_key = function(snippet_id) { return "K_" + snippet_id; - } + }; - get_snippet(snippet_id, callback) { - console.warn(`get_snippet('${snippet_id}') should no longer be called`); - const snippet_js_key = this.get_snippet_js_key(snippet_id); - const snippet_text = this.snippet_db[snippet_js_key]; - const url = this.get_snippet_url(snippet_id); + Huviz.prototype.get_snippet = function(snippet_id, callback) { + var snippet_js_key, snippet_text, url; + console.warn("get_snippet('" + snippet_id + "') should no longer be called"); + snippet_js_key = this.get_snippet_js_key(snippet_id); + snippet_text = this.snippet_db[snippet_js_key]; + url = this.get_snippet_url(snippet_id); if (snippet_text) { - callback(null, {response:snippet_text, already_has_snippet_id:true}); + callback(null, { + response: snippet_text, + already_has_snippet_id: true + }); } else { - //url = "http://localhost:9999/snippet/poetesses/b--balfcl--0--P--3/" - //console.warn(url) d3.xhr(url, callback); } return "got it"; - } + }; - clear_snippets(evt) { + Huviz.prototype.clear_snippets = function(evt) { if ((evt != null) && (evt.target != null) && !$(evt.target).hasClass('close_all_snippets_button')) { return false; } this.currently_printed_snippets = {}; this.snippet_positions_filled = {}; $('.snippet_dialog_box').remove(); - } + }; - init_snippet_box() { + Huviz.prototype.init_snippet_box = function() { if (d3.select('#snippet_box')[0].length > 0) { this.snippet_box = d3.select('#snippet_box'); return console.log("init_snippet_box"); } - } - remove_snippet(snippet_id) { - const key = this.get_snippet_js_key(snippet_id); + }; + + Huviz.prototype.remove_snippet = function(snippet_id) { + var key, slctr; + key = this.get_snippet_js_key(snippet_id); delete this.currently_printed_snippets[key]; if (this.snippet_box) { - const slctr = '#'+id_escape(snippet_id); + slctr = '#' + id_escape(snippet_id); console.log(slctr); return this.snippet_box.select(slctr).remove(); } - } - push_snippet(obj, msg) { + }; + + Huviz.prototype.push_snippet = function(obj, msg) { + var bomb_parent, close_all_button, dialog_args, dlg, elem, my_position, snip_div; console.log("push_snippet"); if (this.snippet_box) { - const snip_div = this.snippet_box.append('div').attr('class','snippet'); + snip_div = this.snippet_box.append('div').attr('class', 'snippet'); snip_div.html(msg); $(snip_div[0][0]).addClass("snippet_dialog_box"); - const my_position = this.get_next_snippet_position(obj.snippet_js_key); - const dialog_args = { - //maxHeight: @snippet_size + my_position = this.get_next_snippet_position(obj.snippet_js_key); + dialog_args = { minWidth: 400, title: obj.dialog_title, position: { @@ -13267,62 +11664,66 @@ LIMIT ${node_limit}\ at: "left top", of: window }, - close: (event, ui) => { - event.stopPropagation(); - delete this.snippet_positions_filled[my_position]; - delete this.currently_printed_snippets[event.target.id]; - } + close: (function(_this) { + return function(event, ui) { + event.stopPropagation(); + delete _this.snippet_positions_filled[my_position]; + delete _this.currently_printed_snippets[event.target.id]; + }; + })(this) }; - - const dlg = $(snip_div).dialog(dialog_args); - const elem = dlg[0][0]; - elem.setAttribute("id",obj.snippet_js_key); - const bomb_parent = $(elem).parent(). - select(".ui-dialog-titlebar").children().first(); - const close_all_button = bomb_parent. - append(''); - //append('') - //append('') + dlg = $(snip_div).dialog(dialog_args); + elem = dlg[0][0]; + elem.setAttribute("id", obj.snippet_js_key); + bomb_parent = $(elem).parent().select(".ui-dialog-titlebar").children().first(); + close_all_button = bomb_parent.append(''); close_all_button.on('click', this.clear_snippets); - return; } - } - snippet_position_str_to_obj(str) { - // convert "left+123 top+456" to {left: 123, top: 456} - const [left, top] = Array.from(str.replace(new RegExp('([a-z]*)\\+','g'),'').split(' ').map(c => parseInt(c))); - return {left, top}; - } - get_next_snippet_position_obj(id) { + }; + + Huviz.prototype.snippet_positions_filled = {}; + + Huviz.prototype.snippet_position_str_to_obj = function(str) { + var left, top, _ref; + _ref = str.replace(new RegExp('([a-z]*)\\+', 'g'), '').split(' ').map(function(c) { + return parseInt(c); + }), left = _ref[0], top = _ref[1]; + return { + left: left, + top: top + }; + }; + + Huviz.prototype.get_next_snippet_position_obj = function(id) { return this.snippet_position_str_to_obj(this.get_next_snippet_position(id)); - } - get_next_snippet_position(id) { - // Fill the left edge, then the top edge, then diagonally from top-left - if (id == null) { id = true; } - const { - height - } = this; - const { - width - } = this; - let left_full = false; - let top_full = false; - let hinc = 0; - let vinc = this.snippet_size; - let hoff = 0; - let voff = 0; - let retval = `left+${hoff} top+${voff}`; + }; + + Huviz.prototype.get_next_snippet_position = function(id) { + var height, hinc, hoff, left_full, retval, top_full, vinc, voff, width; + if (id == null) { + id = true; + } + height = this.height; + width = this.width; + left_full = false; + top_full = false; + hinc = 0; + vinc = this.snippet_size; + hoff = 0; + voff = 0; + retval = "left+" + hoff + " top+" + voff; while (this.snippet_positions_filled[retval] != null) { hoff = hinc + hoff; voff = vinc + voff; - retval = `left+${hoff} top+${voff}`; - if (!left_full && ((voff + vinc + vinc) > height)) { + retval = "left+" + hoff + " top+" + voff; + if (!left_full && voff + vinc + vinc > height) { left_full = true; hinc = this.snippet_size; hoff = 0; voff = 0; vinc = 0; } - if (!top_full && ((hoff + hinc + hinc + hinc) > width)) { + if (!top_full && hoff + hinc + hinc + hinc > width) { top_full = true; hinc = 30; vinc = 30; @@ -13332,17 +11733,15 @@ LIMIT ${node_limit}\ } this.snippet_positions_filled[retval] = id; return retval; - } - - // ========================================================================= + }; - remove_tags(xml) { + Huviz.prototype.remove_tags = function(xml) { return xml.replace(XML_TAG_REGEX, " ").replace(MANY_SPACES_REGEX, " "); - } + }; - // peek selects a node so that subsequent mouse motions select not nodes but edges of this node - peek(node) { - let was_already_peeking = false; + Huviz.prototype.peek = function(node) { + var was_already_peeking; + was_already_peeking = false; if (this.peeking_node != null) { if (this.peeking_node === node) { was_already_peeking = true; @@ -13354,55 +11753,66 @@ LIMIT ${node_limit}\ this.peeking_node = node; return this.peeking_node.color = PEEKING_COLOR; } - } + }; - unflag_all_edges(node) { - return Array.from(node.links_shown).map((edge) => - (edge.focused = false)); - } + Huviz.prototype.unflag_all_edges = function(node) { + var edge, _i, _len, _ref, _results; + _ref = node.links_shown; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + edge = _ref[_i]; + _results.push(edge.focused = false); + } + return _results; + }; - hilight_dialog(dialog_elem) { - if (typeof(dialog_elem) === 'string') { - throw new Error('hilight_dialog() expects an Elem, not '+dialog_elem); + Huviz.prototype.hilight_dialog = function(dialog_elem) { + var dialog_id; + if (typeof dialog_elem === 'string') { + throw new Error('hilight_dialog() expects an Elem, not ' + dialog_elem); } else { - const dialog_id = dialog_elem.getAttribute('id'); + dialog_id = dialog_elem.getAttribute('id'); } - $(dialog_elem).parent().append(dialog_elem); // bring to top + $(dialog_elem).parent().append(dialog_elem); $(dialog_elem).effect('shake'); - } + }; - print_edge(edge) { - // @clear_snippets() - let context_no = 0; - return (() => { - const result = []; - for (let context of Array.from(edge.contexts)) { - var edge_inspector_id = this.make_edge_inspector_id(edge, context); - //snippet_js_key = @get_snippet_js_key(context.id) - context_no++; - if (this.currently_printed_snippets[edge_inspector_id] != null) { - this.hilight_dialog(edge._inspector || edge_inspector_id); - continue; - } - console.log("inspect edge:", edge); - var me = this; - const make_callback = (context_no, edge, context) => { - return (err,data) => { - data = data || {response: ""}; - let snippet_text = data.response; + Huviz.prototype.print_edge = function(edge) { + var cb, context, context_no, edge_inspector_id, make_callback, me, _i, _len, _ref, _results; + context_no = 0; + _ref = edge.contexts; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + context = _ref[_i]; + edge_inspector_id = this.make_edge_inspector_id(edge, context); + context_no++; + if (this.currently_printed_snippets[edge_inspector_id] != null) { + this.hilight_dialog(edge._inspector || edge_inspector_id); + continue; + } + console.log("inspect edge:", edge); + me = this; + make_callback = (function(_this) { + return function(context_no, edge, context) { + return function(err, data) { + var quad, snippet_id, snippet_js_key, snippet_text; + data = data || { + response: "" + }; + snippet_text = data.response; if (!data.already_has_snippet_id) { snippet_text = me.remove_tags(snippet_text); - snippet_text += '
    '+context.id+""; + snippet_text += '
    ' + context.id + ""; } - const snippet_id = context.id; - const snippet_js_key = me.get_snippet_js_key(snippet_id); - if ((me.currently_printed_snippets[edge_inspector_id] == null)) { + snippet_id = context.id; + snippet_js_key = me.get_snippet_js_key(snippet_id); + if (me.currently_printed_snippets[edge_inspector_id] == null) { me.currently_printed_snippets[edge_inspector_id] = []; } me.currently_printed_snippets[edge_inspector_id].push(edge); me.snippet_db[edge_inspector_id] = snippet_text; me.printed_edge = edge; - const quad = { + quad = { subj_uri: edge.source.id, pred_uri: edge.predicate.id, graph_uri: edge.graph.id @@ -13413,57 +11823,67 @@ LIMIT ${node_limit}\ quad.obj_uri = edge.target.id; } return me.push_snippet({ - edge_inspector_id, - edge, + edge_inspector_id: edge_inspector_id, + edge: edge, pred_id: edge.predicate.lid, pred_name: edge.predicate.name, context_id: context.id, - quad, + quad: quad, dialog_title: edge.source.name, - snippet_text, + snippet_text: snippet_text, no: context_no, - snippet_js_key + snippet_js_key: snippet_js_key }); }; }; - const cb = make_callback(context_no, edge, context); - result.push(cb()); - } - return result; - })(); // To get the old snippet fetcher working again, do the following instead: - } - //@get_snippet(context.id, cb) + })(this); + cb = make_callback(context_no, edge, context); + _results.push(cb()); + } + return _results; + }; - // The Verbs PRINT and REDACT show and hide snippets respectively - print(node) { + Huviz.prototype.print = function(node) { + var edge, _i, _len, _ref; this.clear_snippets(); - for (let edge of Array.from(node.links_shown)) { + _ref = node.links_shown; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + edge = _ref[_i]; this.print_edge(edge); } - } + }; - redact(node) { - return node.links_shown.forEach((edge,i) => { - return this.remove_snippet(edge.id); - }); - } + Huviz.prototype.redact = function(node) { + return node.links_shown.forEach((function(_this) { + return function(edge, i) { + return _this.remove_snippet(edge.id); + }; + })(this)); + }; - draw_edge_regarding(node, predicate_lid) { - let dirty = false; - const doit = (edge,i,frOrTo) => { - if (edge.predicate.lid === predicate_lid) { - if ((edge.shown == null)) { - this.show_link(edge); - return dirty = true; + Huviz.prototype.draw_edge_regarding = function(node, predicate_lid) { + var dirty, doit; + dirty = false; + doit = (function(_this) { + return function(edge, i, frOrTo) { + if (edge.predicate.lid === predicate_lid) { + if (edge.shown == null) { + _this.show_link(edge); + return dirty = true; + } } - } - }; - node.links_from.forEach((edge,i) => { - return doit(edge,i,'from'); - }); - node.links_to.forEach((edge,i) => { - return doit(edge,i,'to'); - }); + }; + })(this); + node.links_from.forEach((function(_this) { + return function(edge, i) { + return doit(edge, i, 'from'); + }; + })(this)); + node.links_to.forEach((function(_this) { + return function(edge, i) { + return doit(edge, i, 'to'); + }; + })(this)); if (dirty) { this.update_state(node); this.update_showing_links(node); @@ -13472,169 +11892,189 @@ LIMIT ${node_limit}\ console.log("Tick in @force.alpha draw_edge_regarding"); } } - } + }; - undraw_edge_regarding(node, predicate_lid) { - let dirty = false; - const doit = (edge,i,frOrTo) => { - if (edge.predicate.lid === predicate_lid) { - dirty = true; - return this.unshow_link(edge); - } - }; - node.links_from.forEach((edge,i) => { - return doit(edge,i,'from'); - }); - node.links_to.forEach((edge,i) => { - return doit(edge,i,'to'); - }); - // FIXME(shawn) Looping through links_shown should suffice, try it again - //node.links_shown.forEach (edge,i) => - // doit(edge,'shown') + Huviz.prototype.undraw_edge_regarding = function(node, predicate_lid) { + var dirty, doit; + dirty = false; + doit = (function(_this) { + return function(edge, i, frOrTo) { + if (edge.predicate.lid === predicate_lid) { + dirty = true; + return _this.unshow_link(edge); + } + }; + })(this); + node.links_from.forEach((function(_this) { + return function(edge, i) { + return doit(edge, i, 'from'); + }; + })(this)); + node.links_to.forEach((function(_this) { + return function(edge, i) { + return doit(edge, i, 'to'); + }; + })(this)); if (dirty) { this.update_state(node); this.update_showing_links(node); this.force.alpha(0.1); } - } + }; - update_history() { + Huviz.prototype.update_history = function() { + var n_chosen, the_state, the_title, the_url; if (window.history.pushState) { - const the_state = {}; + the_state = {}; hash = ""; if (chosen_set.length) { the_state.chosen_node_ids = []; hash += "#"; hash += "chosen="; - const n_chosen = chosen_set.length; - this.chosen_set.forEach((chosen, i) => { - hash += chosen.id; - the_state.chosen_node_ids.push(chosen.id); - if (n_chosen > (i + 1)) { return hash += ","; } - }); + n_chosen = chosen_set.length; + this.chosen_set.forEach((function(_this) { + return function(chosen, i) { + hash += chosen.id; + the_state.chosen_node_ids.push(chosen.id); + if (n_chosen > i + 1) { + return hash += ","; + } + }; + })(this)); } - - const the_url = location.href.replace(location.hash, "") + hash; - const the_title = document.title; + the_url = location.href.replace(location.hash, "") + hash; + the_title = document.title; return window.history.pushState(the_state, the_title, the_state); } - } + }; - // TODO: remove this method - restore_graph_state(state) { - //console.log('state:',state); - if (!state) { return; } + Huviz.prototype.restore_graph_state = function(state) { + if (!state) { + return; + } if (state.chosen_node_ids) { this.reset_graph(); - return state.chosen_node_ids.forEach(chosen_id => { - const chosen = get_or_make_node(chosen_id); - if (chosen) { return this.choose(chosen); } - }); + return state.chosen_node_ids.forEach((function(_this) { + return function(chosen_id) { + var chosen; + chosen = get_or_make_node(chosen_id); + if (chosen) { + return _this.choose(chosen); + } + }; + })(this)); } - } + }; - fire_showgraph_event() { - return window.dispatchEvent( - new CustomEvent('showgraph', { - detail: { - message: "graph shown", - time: new Date() - }, - bubbles: true, - cancelable: true - }) - ); - } + Huviz.prototype.fire_showgraph_event = function() { + return window.dispatchEvent(new CustomEvent('showgraph', { + detail: { + message: "graph shown", + time: new Date() + }, + bubbles: true, + cancelable: true + })); + }; - showGraph(g) { + Huviz.prototype.showGraph = function(g) { alert("showGraph called"); this.make_nodes(g); - if (window.CustomEvent != null) { this.fire_showgraph_event(); } + if (window.CustomEvent != null) { + this.fire_showgraph_event(); + } return this.restart(); - } + }; - show_the_edges() {} - //edge_controller.show_tree_in.call(arguments) + Huviz.prototype.show_the_edges = function() {}; - register_gclc_prefixes() { + Huviz.prototype.register_gclc_prefixes = function() { + var abbr, prefix, _ref, _results; this.gclc.prefixes = {}; - return (() => { - const result = []; - for (let abbr in this.G.prefixes) { - const prefix = this.G.prefixes[abbr]; - result.push(this.gclc.prefixes[abbr] = prefix); - } - return result; - })(); - } - + _ref = this.G.prefixes; + _results = []; + for (abbr in _ref) { + prefix = _ref[abbr]; + _results.push(this.gclc.prefixes[abbr] = prefix); + } + return _results; + }; - // https://developer.mozilla.org/en-US/docs/Web/API/IndexedDB_API/Using_IndexedDB - init_datasetDB() { - const { - indexedDB - } = window; // || window.mozIndexedDB || window.webkitIndexedDB || window.msIndexedDB || null + Huviz.prototype.init_datasetDB = function() { + var indexedDB, request; + indexedDB = window.indexedDB; if (!indexedDB) { console.log("indexedDB not available"); } if (!this.datasetDB && indexedDB) { this.dbName = 'datasetDB'; this.dbVersion = 2; - const request = indexedDB.open(this.dbName, this.dbVersion); - request.onsuccess = evt => { - this.datasetDB = request.result; - this.datasetDB.onerror = err => { - return alert(`Database error: ${e.target.errorCode}`); + request = indexedDB.open(this.dbName, this.dbVersion); + request.onsuccess = (function(_this) { + return function(evt) { + _this.datasetDB = request.result; + _this.datasetDB.onerror = function(err) { + return alert("Database error: " + e.target.errorCode); + }; + return _this.populate_menus_from_IndexedDB('onsuccess'); }; - //alert "onsuccess" - return this.populate_menus_from_IndexedDB('onsuccess'); - }; - request.onerror = err => { - return alert(`unable to init ${this.dbName}`); - }; - return request.onupgradeneeded = event => { - const db = event.target.result; - const objectStore = db.createObjectStore("datasets", {keyPath: 'uri'}); - return objectStore.transaction.oncomplete = evt => { - this.datasetDB = db; - // alert "onupgradeneeded" - return this.populate_menus_from_IndexedDB('onupgradeneeded'); + })(this); + request.onerror = (function(_this) { + return function(err) { + return alert("unable to init " + _this.dbName); }; - }; + })(this); + return request.onupgradeneeded = (function(_this) { + return function(event) { + var db, objectStore; + db = event.target.result; + objectStore = db.createObjectStore("datasets", { + keyPath: 'uri' + }); + return objectStore.transaction.oncomplete = function(evt) { + _this.datasetDB = db; + return _this.populate_menus_from_IndexedDB('onupgradeneeded'); + }; + }; + })(this); } - } + }; - ensure_datasets(preload_group, store_in_db) { - // note "fat arrow" so this can be an AJAX callback (see preload_datasets) - const defaults = preload_group.defaults || {}; - //console.log(preload_group) # THIS IS THE ITEMS IN A FILE (i.e. cwrc.json, generes.json) - return (() => { - const result = []; - for (let ds_rec of Array.from(preload_group.datasets)) { - // If this preload_group has defaults apply them to the ds_rec - // if it is missing that value. - // We do not want to do `ds_rec.__proto__ = defaults` - // because then defaults are not ownProperty - for (let k in defaults) { - if (ds_rec[k] == null) { ds_rec[k] = defaults[k]; } + Huviz.prototype.ensure_datasets = function(preload_group, store_in_db) { + var defaults, ds_rec, k, _i, _len, _ref, _results; + defaults = preload_group.defaults || {}; + _ref = preload_group.datasets; + _results = []; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + ds_rec = _ref[_i]; + for (k in defaults) { + if (ds_rec[k] == null) { + ds_rec[k] = defaults[k]; } - result.push(this.ensure_dataset(ds_rec, store_in_db)); } - return result; - })(); - } + _results.push(this.ensure_dataset(ds_rec, store_in_db)); + } + return _results; + }; - ensure_dataset(rsrcRec, store_in_db) { - // ensure the dataset is in the database and the correct - const { - uri - } = rsrcRec; - if (rsrcRec.time == null) { rsrcRec.time = new Date().toString(); } - if (rsrcRec.title == null) { rsrcRec.title = uri; } - if (rsrcRec.isUri == null) { rsrcRec.isUri = !!uri.match(/^(http|ftp)/); } - // if it has a time then a user added it therefore canDelete - if (rsrcRec.canDelete == null) { rsrcRec.canDelete = !(rsrcRec.time == null); } - if (rsrcRec.label == null) { rsrcRec.label = uri.split('/').reverse()[0]; } + Huviz.prototype.ensure_dataset = function(rsrcRec, store_in_db) { + var uri; + uri = rsrcRec.uri; + if (rsrcRec.time == null) { + rsrcRec.time = new Date().toString(); + } + if (rsrcRec.title == null) { + rsrcRec.title = uri; + } + if (rsrcRec.isUri == null) { + rsrcRec.isUri = !!uri.match(/^(http|ftp)/); + } + if (rsrcRec.canDelete == null) { + rsrcRec.canDelete = !(rsrcRec.time == null); + } + if (rsrcRec.label == null) { + rsrcRec.label = uri.split('/').reverse()[0]; + } if (rsrcRec.isOntology) { if (this.ontology_loader) { this.ontology_loader.add_resource(rsrcRec, store_in_db); @@ -13646,196 +12086,209 @@ LIMIT ${node_limit}\ if (rsrcRec.isEndpoint && this.endpoint_loader) { return this.endpoint_loader.add_resource(rsrcRec, store_in_db); } - } - - add_resource_to_db(rsrcRec, callback) { - const trx = this.datasetDB.transaction('datasets', "readwrite"); - trx.oncomplete = e => { - return console.log(`${rsrcRec.uri} added!`); - }; - trx.onerror = e => { - console.log(e); - return alert(`add_resource(${rsrcRec.uri}) error!!!`); - }; - const store = trx.objectStore('datasets'); - const req = store.put(rsrcRec); - return req.onsuccess = e => { - if (rsrcRec.isEndpoint) { - this.sparql_graph_query_and_show__trigger(e.srcElement.result); - } - if (rsrcRec.uri !== e.target.result) { - console.debug(`rsrcRec.uri (${rsrcRec.uri}) is expected to equal`, e.target.result); - } - return callback(rsrcRec); - }; - } + }; - remove_dataset_from_db(dataset_uri, callback) { - const trx = this.datasetDB.transaction('datasets', "readwrite"); - trx.oncomplete = e => { - return console.log(`${dataset_uri} deleted`); - }; - trx.onerror = e => { - console.log(e); - return alert(`remove_dataset_from_db(${dataset_uri}) error!!!`); - }; - const store = trx.objectStore('datasets'); - const req = store.delete(dataset_uri); - req.onsuccess = e => { - if (callback != null) { - return callback(dataset_uri); - } - }; - return req.onerror = e => { - return console.debug(e); - }; - } + Huviz.prototype.add_resource_to_db = function(rsrcRec, callback) { + var req, store, trx; + trx = this.datasetDB.transaction('datasets', "readwrite"); + trx.oncomplete = (function(_this) { + return function(e) { + return console.log("" + rsrcRec.uri + " added!"); + }; + })(this); + trx.onerror = (function(_this) { + return function(e) { + console.log(e); + return alert("add_resource(" + rsrcRec.uri + ") error!!!"); + }; + })(this); + store = trx.objectStore('datasets'); + req = store.put(rsrcRec); + return req.onsuccess = (function(_this) { + return function(e) { + if (rsrcRec.isEndpoint) { + _this.sparql_graph_query_and_show__trigger(e.srcElement.result); + } + if (rsrcRec.uri !== e.target.result) { + console.debug("rsrcRec.uri (" + rsrcRec.uri + ") is expected to equal", e.target.result); + } + return callback(rsrcRec); + }; + })(this); + }; - get_resource_from_db(rsrcUri, callback) { - const trx = this.datasetDB.transaction('datasets', "readwrite"); - trx.oncomplete = evt => { - return console.log(`get_resource_from_db('${rsrcUri}') complete, either by success or error`); - }; - trx.onerror = err => { - console.log(err); - if (callback != null) { - return callback(err, null); - } else { - alert(`get_resource_from_db(${rsrcUri}) error!!!`); - throw err; - } - }; - const store = trx.objectStore('datasets'); - const req = store.get(rsrcUri); - req.onsuccess = event => { - if (callback != null) { - return callback(null, event.target.result); - } - }; - req.onerror = err => { - console.debug(`get_resource_from_db('${rsrcUri}') onerror ==>`,err); - if (callback) { - return callback(err, null); - } else { - throw err; - } - }; - } + Huviz.prototype.remove_dataset_from_db = function(dataset_uri, callback) { + var req, store, trx; + trx = this.datasetDB.transaction('datasets', "readwrite"); + trx.oncomplete = (function(_this) { + return function(e) { + return console.log("" + dataset_uri + " deleted"); + }; + })(this); + trx.onerror = (function(_this) { + return function(e) { + console.log(e); + return alert("remove_dataset_from_db(" + dataset_uri + ") error!!!"); + }; + })(this); + store = trx.objectStore('datasets'); + req = store["delete"](dataset_uri); + req.onsuccess = (function(_this) { + return function(e) { + if (callback != null) { + return callback(dataset_uri); + } + }; + })(this); + return req.onerror = (function(_this) { + return function(e) { + return console.debug(e); + }; + })(this); + }; - populate_menus_from_IndexedDB(why) { - // https://developer.mozilla.org/en-US/docs/Web/API/IndexedDB_API/Using_IndexedDB#Using_a_cursor - console.log(`populate_menus_from_IndexedDB(${why})`); - const datasetDB_objectStore = this.datasetDB.transaction('datasets').objectStore('datasets'); - let count = 0; - const make_onsuccess_handler = why => { - const recs = []; - return event => { - const cursor = event.target.result; - if (cursor) { - count++; - const rec = cursor.value; - recs.push(rec); - const legacyDataset = (!rec.isOntology && !rec.rsrcType); - const legacyOntology = (!!rec.isOntology); - if (['dataset', 'ontology'].includes(rec.rsrcType) || legacyDataset || legacyOntology) { - // both datasets and ontologies appear in the dataset menu, for visualization - this.dataset_loader.add_resource_option(rec); - } - if ((rec.rsrcType === 'ontology') || legacyOntology) { - // only datasets are added to the dataset menu - this.ontology_loader.add_resource_option(rec); - } - if (rec.rsrcType === 'script') { - this.script_loader.add_resource_option(rec); - } - if (rec.rsrcType === 'endpoint') { - this.endpoint_loader.add_resource_option(rec); - } - return cursor.continue(); - } else { // when there are no (or NO MORE) entries, ie FINALLY - //console.table(recs) - // Reset the value of each loader to blank so - // they show 'Pick or Provide...' not the last added entry. - this.dataset_loader.val(''); - this.ontology_loader.val(''); - this.endpoint_loader.val(''); - this.script_loader.val(''); - this.update_dataset_ontology_loader(); - console.groupEnd(); // closing group called "populate_menus_from_IndexedDB(why)" - return document.dispatchEvent( // TODO use 'huvis_controls' rather than document - new Event('dataset_ontology_loader_ready')); + Huviz.prototype.get_resource_from_db = function(rsrcUri, callback) { + var req, store, trx; + trx = this.datasetDB.transaction('datasets', "readwrite"); + trx.oncomplete = (function(_this) { + return function(evt) { + return console.log("get_resource_from_db('" + rsrcUri + "') complete, either by success or error"); + }; + })(this); + trx.onerror = (function(_this) { + return function(err) { + console.log(err); + if (callback != null) { + return callback(err, null); + } else { + alert("get_resource_from_db(" + rsrcUri + ") error!!!"); + throw err; } }; - }; - //alert "#{count} entries saved #{why}" + })(this); + store = trx.objectStore('datasets'); + req = store.get(rsrcUri); + req.onsuccess = (function(_this) { + return function(event) { + if (callback != null) { + return callback(null, event.target.result); + } + }; + })(this); + req.onerror = (function(_this) { + return function(err) { + console.debug("get_resource_from_db('" + rsrcUri + "') onerror ==>", err); + if (callback) { + return callback(err, null); + } else { + throw err; + } + }; + })(this); + }; + Huviz.prototype.populate_menus_from_IndexedDB = function(why) { + var count, datasetDB_objectStore, make_onsuccess_handler; + console.log("populate_menus_from_IndexedDB(" + why + ")"); + datasetDB_objectStore = this.datasetDB.transaction('datasets').objectStore('datasets'); + count = 0; + make_onsuccess_handler = (function(_this) { + return function(why) { + var recs; + recs = []; + return function(event) { + var cursor, legacyDataset, legacyOntology, rec, _ref; + cursor = event.target.result; + if (cursor) { + count++; + rec = cursor.value; + recs.push(rec); + legacyDataset = !rec.isOntology && !rec.rsrcType; + legacyOntology = !!rec.isOntology; + if (((_ref = rec.rsrcType) === 'dataset' || _ref === 'ontology') || legacyDataset || legacyOntology) { + _this.dataset_loader.add_resource_option(rec); + } + if (rec.rsrcType === 'ontology' || legacyOntology) { + _this.ontology_loader.add_resource_option(rec); + } + if (rec.rsrcType === 'script') { + _this.script_loader.add_resource_option(rec); + } + if (rec.rsrcType === 'endpoint') { + _this.endpoint_loader.add_resource_option(rec); + } + return cursor["continue"](); + } else { + _this.dataset_loader.val(''); + _this.ontology_loader.val(''); + _this.endpoint_loader.val(''); + _this.script_loader.val(''); + _this.update_dataset_ontology_loader(); + console.groupEnd(); + return document.dispatchEvent(new Event('dataset_ontology_loader_ready')); + } + }; + }; + })(this); if (this.dataset_loader != null) { return datasetDB_objectStore.openCursor().onsuccess = make_onsuccess_handler(why); } - } + }; - preload_datasets() { - // If present args.preload is expected to be a list or urls or objects. - // Whether literal object or JSON urls the object structure is expected to be: - // { 'datasets': [ - // { - // 'uri': "/data/byroau.nq", // url of dataset .ttl or .nq - // 'label': "Augusta Ada Brown", // label of OPTION in SELECT - // 'isOntology': false, // optional, if true it goes in Onto menu - // 'opt_group': "Individuals", // user-defined label for menu subsection - // 'canDelete': false, // meaningful only for recs in datasetsDB - // 'ontologyUri': '/data/orlando.ttl' // url of ontology - // } - // ], - // 'defaults': {} # optional, may contain default values for the keys above - // } + Huviz.prototype.preload_datasets = function() { + var preload_group_or_uri, _i, _len, _ref; console.groupCollapsed("preload_datasets"); - // Adds preload options to datasetDB table console.log(this.args.preload); if (this.args.preload) { - for (var preload_group_or_uri of Array.from(this.args.preload)) { - if (typeof(preload_group_or_uri) === 'string') { // the URL of a preload_group JSON - //$.getJSON(preload_group_or_uri, null, @ensure_datasets_from_XHR) + _ref = this.args.preload; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + preload_group_or_uri = _ref[_i]; + if (typeof preload_group_or_uri === 'string') { $.ajax({ async: false, url: preload_group_or_uri, - success: (data, textStatus) => { - return this.ensure_datasets_from_XHR(data); - }, - error(jqxhr, textStatus, errorThrown) { - return console.error(preload_group_or_uri + " " +textStatus+" "+errorThrown.toString()); + success: (function(_this) { + return function(data, textStatus) { + return _this.ensure_datasets_from_XHR(data); + }; + })(this), + error: function(jqxhr, textStatus, errorThrown) { + return console.error(preload_group_or_uri + " " + textStatus + " " + errorThrown.toString()); } }); - } else if (typeof(preload_group_or_uri) === 'object') { // a preload_group object + } else if (typeof preload_group_or_uri === 'object') { this.ensure_datasets(preload_group_or_uri); } else { console.error("bad member of @args.preload:", preload_group_or_uri); } } } - return console.groupEnd(); // closing group called "preload_datasets" - } + return console.groupEnd(); + }; - preload_endpoints() { + Huviz.prototype.preload_endpoints = function() { + var preload_group_or_uri, _i, _len, _ref; console.log(this.args.preload_endpoints); console.groupCollapsed("preload_endpoints"); - //### if (this.args.preload_endpoints) { - for (var preload_group_or_uri of Array.from(this.args.preload_endpoints)) { + _ref = this.args.preload_endpoints; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + preload_group_or_uri = _ref[_i]; console.log(preload_group_or_uri); - if (typeof(preload_group_or_uri) === 'string') { // the URL of a preload_group JSON - //$.getJSON(preload_group_or_uri, null, @ensure_datasets_from_XHR) + if (typeof preload_group_or_uri === 'string') { $.ajax({ async: false, url: preload_group_or_uri, - success: (data, textStatus) => { - return this.ensure_datasets_from_XHR(data); - }, - error(jqxhr, textStatus, errorThrown) { - return console.error(preload_group_or_uri + " " +textStatus+" "+errorThrown.toString()); + success: (function(_this) { + return function(data, textStatus) { + return _this.ensure_datasets_from_XHR(data); + }; + })(this), + error: function(jqxhr, textStatus, errorThrown) { + return console.error(preload_group_or_uri + " " + textStatus + " " + errorThrown.toString()); } }); - } else if (typeof(preload_group_or_uri) === 'object') { // a preload_group object + } else if (typeof preload_group_or_uri === 'object') { this.ensure_datasets(preload_group_or_uri); } else { console.error("bad member of @args.preload:", preload_group_or_uri); @@ -13843,68 +12296,67 @@ LIMIT ${node_limit}\ } } return console.groupEnd(); - } - //### + }; - ensure_datasets_from_XHR(preload_group) { - this.ensure_datasets(preload_group, false); // false means DO NOT store_in_db - } + Huviz.prototype.ensure_datasets_from_XHR = function(preload_group) { + this.ensure_datasets(preload_group, false); + }; - get_menu_by_rsrcType(rsrcType) { - return this[rsrcType+'_loader']; // eg rsrcType='script' ==> @script_loader - } + Huviz.prototype.get_menu_by_rsrcType = function(rsrcType) { + return this[rsrcType + '_loader']; + }; - get_or_create_sel_for_picker(specificSel) { - // if specificSel is defined, return it, otherwise return the selector of a thin - let sel = specificSel; - if ((sel == null)) { - if ((this.pickersSel == null)) { - let huvis_controls_sel; - const pickersId = this.unique_id('pickers_'); + Huviz.prototype.get_or_create_sel_for_picker = function(specificSel) { + var huvis_controls_sel, pickersId, sel; + sel = specificSel; + if (sel == null) { + if (this.pickersSel == null) { + pickersId = this.unique_id('pickers_'); this.pickersSel = '#' + pickersId; - if (huvis_controls_sel = this.oldToUniqueTabSel['huvis_controls']) { - if (this.huvis_controls_elem == null) { this.huvis_controls_elem = document.querySelector(huvis_controls_sel); } + if ((huvis_controls_sel = this.oldToUniqueTabSel['huvis_controls'])) { + if (this.huvis_controls_elem == null) { + this.huvis_controls_elem = document.querySelector(huvis_controls_sel); + } if (this.huvis_controls_elem) { - this.huvis_controls_elem.insertAdjacentHTML('beforeend', `
    `); + this.huvis_controls_elem.insertAdjacentHTML('beforeend', "
    "); } } } sel = this.pickersSel; } return sel; - } + }; - init_resource_menus() { - // REVIEW See views/huviz.html.eco to set dataset_loader__append_to_sel and similar - let sel; + Huviz.prototype.init_resource_menus = function() { + var dataset_selector, endpoint_selector, ontology_selector, script_selector, sel; if (!this.dataset_loader && this.args.make_pickers) { sel = this.get_or_create_sel_for_picker(this.args.dataset_loader__append_to_sel); - this.dataset_loader = new PickOrProvide(this, sel, - 'Dataset', 'DataPP', false, false, - {rsrcType: 'dataset'}); + this.dataset_loader = new PickOrProvide(this, sel, 'Dataset', 'DataPP', false, false, { + rsrcType: 'dataset' + }); } if (!this.ontology_loader && this.args.make_pickers) { sel = this.get_or_create_sel_for_picker(this.args.ontology_loader__append_to_sel); - this.ontology_loader = new PickOrProvide(this, sel, - 'Ontology', 'OntoPP', true, false, - {rsrcType: 'ontology'}); + this.ontology_loader = new PickOrProvide(this, sel, 'Ontology', 'OntoPP', true, false, { + rsrcType: 'ontology' + }); } if (!this.script_loader && this.args.make_pickers) { sel = this.get_or_create_sel_for_picker(this.args.script_loader__append_to_sel); - this.script_loader = new PickOrProvideScript(this, sel, - 'Script', 'ScriptPP', false, false, - {dndLoaderClass: DragAndDropLoaderOfScripts, rsrcType: 'script'}); + this.script_loader = new PickOrProvideScript(this, sel, 'Script', 'ScriptPP', false, false, { + dndLoaderClass: DragAndDropLoaderOfScripts, + rsrcType: 'script' + }); } if (!this.endpoint_loader && this.args.make_pickers) { sel = this.get_or_create_sel_for_picker(this.args.endpoint_loader__append_to_sel); - this.endpoint_loader = new PickOrProvide(this, sel, - 'Sparql', 'EndpointPP', false, true, - {rsrcType: 'endpoint'}); + this.endpoint_loader = new PickOrProvide(this, sel, 'Sparql', 'EndpointPP', false, true, { + rsrcType: 'endpoint' + }); } - //@endpoint_loader.outstanding_requests = 0 if (this.endpoint_loader && !this.big_go_button) { this.build_sparql_form(); - const endpoint_selector = `#${this.endpoint_loader.select_id}`; + endpoint_selector = "#" + this.endpoint_loader.select_id; $(endpoint_selector).change(this.update_endpoint_form); } if (this.ontology_loader && !this.big_go_button) { @@ -13915,52 +12367,44 @@ LIMIT ${node_limit}\ this.big_go_button.click(this.big_go_button_onclick); this.disable_go_button(); } - if (this.ontology_loader || this.dataset_loader || (this.script_loader && !this.big_go_button)) { - const ontology_selector = `#${this.ontology_loader.select_id}`; + if (this.ontology_loader || this.dataset_loader || this.script_loader && !this.big_go_button) { + ontology_selector = "#" + this.ontology_loader.select_id; $(ontology_selector).change(this.update_dataset_forms); - const dataset_selector = `#${this.dataset_loader.select_id}`; + dataset_selector = "#" + this.dataset_loader.select_id; $(dataset_selector).change(this.update_dataset_forms); - const script_selector = `#${this.script_loader.select_id}`; + script_selector = "#" + this.script_loader.select_id; $(script_selector).change(this.update_dataset_forms); } - this.init_datasetDB(); this.preload_datasets(); - - //@preload_endpoints() - // TODO remove this nullification of @last_val by fixing logic in select_option() - // clear the last_val so select_option works the first time if (this.ontology_loader.last_val) { return this.ontology_loader.last_val = null; } - } + }; - big_go_button_onclick(event) { + Huviz.prototype.big_go_button_onclick = function(event) { if (this.using_sparql()) { return this.big_go_button_onclick_sparql(event); } this.visualize_dataset_using_ontology(); - } + }; - big_go_button_onclick_sparql(event) { - let endpoint_label_uri, graphUri; + Huviz.prototype.big_go_button_onclick_sparql = function(event) { + var endpoint_label_uri, foundUri, graphUri, spoQuery; if (this.allGraphsChosen()) { - let foundUri; - if (foundUri = this.endpoint_labels_JQElem.val()) { + if ((foundUri = this.endpoint_labels_JQElem.val())) { this.visualize_dataset_using_ontology(); return; } colorlog("IGNORING. The LOAD button should not even be clickable right now"); return; } - if (endpoint_label_uri = this.endpoint_labels_JQElem.val()) { + if ((endpoint_label_uri = this.endpoint_labels_JQElem.val())) { this.visualize_dataset_using_ontology(); return; } - if (graphUri = this.sparqlGraphSelector_JQElem.val()) { - // TODO remove the requirement for a graphUri to be specified before the spoQuery is enabled. - let spoQuery; - if (spoQuery = this.spo_query_JQElem.val()) { + if ((graphUri = this.sparqlGraphSelector_JQElem.val())) { + if ((spoQuery = this.spo_query_JQElem.val())) { this.displayTheSpoQuery(spoQuery, graphUri); return; } @@ -13968,29 +12412,27 @@ LIMIT ${node_limit}\ return; } colorlog("IGNORING. Neither graph nor endpoint_label is chosen."); - } + }; - displayTheChosenGraph(graphUri) { - //alert("stub for displayTheChosenGraph('#{graphUri}')") - let limit; - const args = { + Huviz.prototype.displayTheChosenGraph = function(graphUri) { + var args, limit; + args = { success_handler: this.display_graph_success_handler, result_handler: this.name_result_handler, query_terms: { g: graphUri } }; - // respect the limit provided by the user - if (limit = this.endpoint_limit_JQElem.val()) { + if ((limit = this.endpoint_limit_JQElem.val())) { args.limit = limit; } args.query = this.make_generic_query(args); this.run_generic_query(args); - } + }; - displayTheSpoQuery(spoQuery, graphUri) { - let limit; - const args = { + Huviz.prototype.displayTheSpoQuery = function(spoQuery, graphUri) { + var args, limit; + args = { success_handler: this.display_graph_success_handler, result_handler: this.name_result_handler, query: spoQuery, @@ -13998,52 +12440,45 @@ LIMIT ${node_limit}\ g: graphUri } }; - if (limit = this.endpoint_limit_JQElem.val()) { + if ((limit = this.endpoint_limit_JQElem.val())) { args.limit = limit; } this.run_generic_query(args); - } + }; - // ## make_generic_query() - // - // The default query looks like: - // ```sparql - // SELECT * - // FROM # only present if query_terms.g provided - // WHERE { - // ?p ?o . - // } - // LIMIT 20 # the value of args.limit, if present - // ``` - make_generic_query(in_args) { - const args = this.compose_object_from_defaults_and_incoming(this.default_name_query_args, in_args); - const terms = args.query_terms || {}; - const lines = ["SELECT *"]; + Huviz.prototype.make_generic_query = function(in_args) { + var args, lines, pattern, term, terms, val, _i, _len, _ref; + args = this.compose_object_from_defaults_and_incoming(this.default_name_query_args, in_args); + terms = args.query_terms || {}; + lines = ["SELECT *"]; if (terms.g != null) { - lines.push(`FROM <${terms.g}>`); + lines.push("FROM <" + terms.g + ">"); } lines.push("WHERE {"); - let pattern = " "; - for (let term of Array.from('spo'.split(''))) { - const val = terms[term]; + pattern = " "; + _ref = 'spo'.split(''); + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + term = _ref[_i]; + val = terms[term]; if (val != null) { - pattern += `<${val}> `; + pattern += "<" + val + "> "; } else { - pattern += `?${term} `; + pattern += "?" + term + " "; } } pattern += "."; lines.push(pattern); lines.push("}"); if (args.limit) { - lines.push(`LIMIT ${args.limit}`); + lines.push("LIMIT " + args.limit); } return lines.join("\n"); - } + }; - run_generic_query(args) { - const serverSpec = this.get_server_for_dataset(args.query_terms.g); - const {serverType, serverUrl} = serverSpec; + Huviz.prototype.run_generic_query = function(args) { + var serverSpec, serverType, serverUrl; + serverSpec = this.get_server_for_dataset(args.query_terms.g); + serverType = serverSpec.serverType, serverUrl = serverSpec.serverUrl; args.serverUrl = serverUrl; args.serverType = serverType; switch (serverType) { @@ -14054,81 +12489,80 @@ LIMIT ${node_limit}\ this.run_managed_query_ajax(args); break; default: - throw new Error(`don't know how to handle serverType: '${serverType}'`); + throw new Error("don't know how to handle serverType: '" + serverType + "'"); } - } + }; + + Huviz.prototype.domain2sparqlEndpoint = { + 'cwrc.ca': 'http://sparql.cwrc.ca/sparql', + 'getty.edu': 'http://vocab.getty.edu/sparql.tsv', + 'openstreetmap.org': 'https://sophox.org/sparql' + }; - get_server_for_dataset(datasetUri) { - let serverType, serverUrl; - const aUrl = new URL(datasetUri); - const {domain} = aUrl; - // Deal with the situation where the datasetUri sought is served - // by the server the user has chosen. - if (this.using_sparql() && (this.sparqlGraphSelector_JQElem.val() === datasetUri)) { + Huviz.prototype.get_server_for_dataset = function(datasetUri) { + var aUrl, domain, serverType, serverUrl; + aUrl = new URL(datasetUri); + domain = aUrl.domain; + if (this.using_sparql() && this.sparqlGraphSelector_JQElem.val() === datasetUri) { serverType = 'sparql'; serverUrl = this.endpoint_loader.value; - // Otherwise, consult built-in hard-coded mappings from datasets to - // the servers they are available at. First we look for matches - // based on the domain sought. - } else if (serverUrl = this.domain2sparqlEndpoint[domain]) { + } else if ((serverUrl = this.domain2sparqlEndpoint[domain])) { serverType = 'sparql'; - } else if (serverUrl = this.domain2sparqlEndpoint[domain]) { + } else if ((serverUrl = this.domain2sparqlEndpoint[domain])) { serverType = 'ldf'; - // Then try to find wildcard servers '*', if available. - // Give precedence to sparql over ldf. - } else if (serverUrl = this.domain2sparqlEndpoint['*']) { + } else if ((serverUrl = this.domain2sparqlEndpoint['*'])) { serverType = 'sparql'; - } else if (serverUrl = this.domain2ldfServer['*']) { + } else if ((serverUrl = this.domain2ldfServer['*'])) { serverType = 'ldf'; } else { - throw new Error(`a server could not be found for ${datasetUri}`); + throw new Error("a server could not be found for " + datasetUri); } - return {serverType, serverUrl}; - } + return { + serverType: serverType, + serverUrl: serverUrl + }; + }; - update_dataset_forms(e) { - const ont_val = $(`#${this.ontology_loader.select_id}`).val(); - const dat_val = $(`#${this.dataset_loader.select_id}`).val(); - const scr_val = $(`#${this.script_loader.select_id}`).val(); - if ((ont_val === '') && (dat_val === '') && (scr_val === '')) { - return $(`#${this.endpoint_loader.uniq_id}`).children('select').prop('disabled', false); + Huviz.prototype.update_dataset_forms = function(e) { + var dat_val, ont_val, scr_val; + ont_val = $("#" + this.ontology_loader.select_id).val(); + dat_val = $("#" + this.dataset_loader.select_id).val(); + scr_val = $("#" + this.script_loader.select_id).val(); + if (ont_val === '' && dat_val === '' && scr_val === '') { + return $("#" + this.endpoint_loader.uniq_id).children('select').prop('disabled', false); } else { - return $(`#${this.endpoint_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); + return $("#" + this.endpoint_loader.uniq_id).children('select').prop('disabled', 'disabled'); } - } + }; - update_graph_form(e) { + Huviz.prototype.update_graph_form = function(e) { console.log(e.currentTarget.value); return this.endpoint_loader.endpoint_graph = e.currentTarget.value; - } + }; - visualize_dataset_using_ontology(ignoreEvent, dataset, ontologies) { - let data; + Huviz.prototype.visualize_dataset_using_ontology = function(ignoreEvent, dataset, ontologies) { + var alreadyCommands, data, endpoint_label_uri, onto, scriptUri; colorlog('visualize_dataset_using_ontology()', dataset, ontologies); this.close_blurt_box(); - const endpoint_label_uri = this.endpoint_labels_JQElem.val(); + endpoint_label_uri = this.endpoint_labels_JQElem.val(); if (endpoint_label_uri) { data = dataset || this.endpoint_loader; this.load_endpoint_data_and_show(endpoint_label_uri); - // TODO ensure disable_dataset_ontology_loader() is only called once console.warn("disable_dataset_ontology_loader() SHOULD BE CALLED ONLY ONCE"); this.disable_dataset_ontology_loader_AUTOMATICALLY(); this.update_browser_title(data); this.update_caption(data.value, data.endpoint_graph); return; } - // Either dataset and ontologies are passed in by HuViz.load_with() from a command - // or this method is called with neither in which case get values from the loaders - let alreadyCommands = ((this.gclui.command_list != null) && this.gclui.command_list.length); + alreadyCommands = (this.gclui.command_list != null) && this.gclui.command_list.length; alreadyCommands = this.gclui.future_cmdArgs.length > 0; if (this.script_loader.value && !alreadyCommands) { - const scriptUri = this.script_loader.value; + scriptUri = this.script_loader.value; this.get_resource_from_db(scriptUri, this.load_script_from_db); return; } - const onto = (ontologies && ontologies[0]) || this.ontology_loader; + onto = ontologies && ontologies[0] || this.ontology_loader; data = dataset || this.dataset_loader; - // at this point data and onto are both objects with a .value key, containing url or fname if (!(onto.value && data.value)) { console.debug(data, onto); this.update_dataset_forms(); @@ -14137,117 +12571,122 @@ LIMIT ${node_limit}\ this.load_data_with_onto(data, onto, this.after_visualize_dataset_using_ontology); this.update_browser_title(data); this.update_caption(data.value, onto.value); - } + }; - after_visualize_dataset_using_ontology() { + Huviz.prototype.after_visualize_dataset_using_ontology = function() { return this.preset_discover_geonames_remaining(); - } + }; - load_script_from_db(err, rsrcRec) { + Huviz.prototype.load_script_from_db = function(err, rsrcRec) { if (err != null) { return this.blurt(err, 'error'); } else { return this.load_script_from_JSON(this.parse_script_file(rsrcRec.data, rsrcRec.uri)); } - } + }; - init_gclc() { + Huviz.prototype.init_gclc = function() { + var pid, _i, _len, _ref; this.gclc = new GraphCommandLanguageCtrl(this); this.init_resource_menus(); - if ((this.gclui == null)) { - // @oldToUniqueTabSel['huvis_controls'] ??? - this.gclui = new CommandController(this,d3.select(this.args.gclui_sel)[0][0],this.hierarchy); + if (this.gclui == null) { + this.gclui = new CommandController(this, d3.select(this.args.gclui_sel)[0][0], this.hierarchy); } window.addEventListener('showgraph', this.register_gclc_prefixes); window.addEventListener('newpredicate', this.gclui.handle_newpredicate); if (!this.show_class_instance_edges) { - TYPE_SYNS.forEach((pred_id,i) => { - return this.gclui.ignore_predicate(pred_id); - }); + TYPE_SYNS.forEach((function(_this) { + return function(pred_id, i) { + return _this.gclui.ignore_predicate(pred_id); + }; + })(this)); } - NAME_SYNS.forEach((pred_id,i) => { - return this.gclui.ignore_predicate(pred_id); - }); - for (let pid of Array.from(this.predicates_to_ignore)) { + NAME_SYNS.forEach((function(_this) { + return function(pred_id, i) { + return _this.gclui.ignore_predicate(pred_id); + }; + })(this)); + _ref = this.predicates_to_ignore; + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + pid = _ref[_i]; this.gclui.ignore_predicate(pid); } - } + }; - disable_dataset_ontology_loader_AUTOMATICALLY() { - // TODO to be AUTOMATIC(!!) handle dataset, ontology and script too - // TODO this should add graph, item and limit only if needed - const endpoint = { + Huviz.prototype.disable_dataset_ontology_loader_AUTOMATICALLY = function() { + var endpoint; + endpoint = { value: this.endpoint_loader.value, - label: this.endpoint_loader.value, // TODO get pretty label (or not?) + label: this.endpoint_loader.value, limit: this.endpoint_limit_JQElem.val(), graph: { value: this.sparqlGraphSelector_JQElem.val(), label: this.sparqlGraphSelector_JQElem.val() - }, // TODO get pretty label (or not?) + }, item: { value: this.endpoint_labels_JQElem.val(), label: this.endpoint_labels_JQElem.val() - } // TODO get pretty label (or not?) + } }; this.disable_dataset_ontology_loader(null, null, endpoint); - } + }; - disable_dataset_ontology_loader(data, onto, endpoint) { + Huviz.prototype.disable_dataset_ontology_loader = function(data, onto, endpoint) { this.replace_loader_display(data, onto, endpoint); this.disable_go_button(); this.dataset_loader.disable(); this.ontology_loader.disable(); this.big_go_button.hide(); - } + }; - reset_dataset_ontology_loader() { - $('#'+this.get_data_ontology_display_id()).remove(); - //Enable dataset loader and reset to default setting + Huviz.prototype.reset_dataset_ontology_loader = function() { + $('#' + this.get_data_ontology_display_id()).remove(); this.dataset_loader.enable(); this.ontology_loader.enable(); this.big_go_button.show(); - $(`#${this.dataset_loader.select_id} option[label='Pick or Provide...']`) - .prop('selected', true); - this.gclui_JQElem.removeAttr("style","display:none"); - } + $("#" + this.dataset_loader.select_id + " option[label='Pick or Provide...']").prop('selected', true); + this.gclui_JQElem.removeAttr("style", "display:none"); + }; - update_dataset_ontology_loader(args) { - if (!((this.dataset_loader != null) && (this.ontology_loader != null) && - (this.endpoint_loader != null) && (this.script_loader != null))) { + Huviz.prototype.update_dataset_ontology_loader = function(args) { + var ugb; + if (!((this.dataset_loader != null) && (this.ontology_loader != null) && (this.endpoint_loader != null) && (this.script_loader != null))) { console.log("still building loaders..."); return; } this.set_ontology_from_dataset_if_possible(args); - const ugb = () => { - return this.update_go_button(); // TODO confirm that this should be disable_go_button - }; + ugb = (function(_this) { + return function() { + return _this.update_go_button(); + }; + })(this); return setTimeout(ugb, 200); - } + }; - update_endpoint_form(e) { - //check if there are any endpoint selections available - const graphSelector = `#sparqlGraphOptions-${e.currentTarget.id}`; + Huviz.prototype.update_endpoint_form = function(e) { + var graphSelector; + graphSelector = "#sparqlGraphOptions-" + e.currentTarget.id; $(graphSelector).change(this.update_graph_form); if (e.currentTarget.value === '') { - $(`#${this.dataset_loader.uniq_id}`).children('select').prop('disabled', false); - $(`#${this.ontology_loader.uniq_id}`).children('select').prop('disabled', false); - $(`#${this.script_loader.uniq_id}`).children('select').prop('disabled', false); + $("#" + this.dataset_loader.uniq_id).children('select').prop('disabled', false); + $("#" + this.ontology_loader.uniq_id).children('select').prop('disabled', false); + $("#" + this.script_loader.uniq_id).children('select').prop('disabled', false); $(graphSelector).parent().css('display', 'none'); return this.reset_endpoint_form(false); } else if (e.currentTarget.value === 'provide') { return console.log("update_endpoint_form ... select PROVIDE"); } else { this.sparql_graph_query_and_show(e.currentTarget.value, e.currentTarget.id); - //console.log(@dataset_loader) - $(`#${this.dataset_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); - $(`#${this.ontology_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); - return $(`#${this.script_loader.uniq_id}`).children('select').prop('disabled', 'disabled'); + $("#" + this.dataset_loader.uniq_id).children('select').prop('disabled', 'disabled'); + $("#" + this.ontology_loader.uniq_id).children('select').prop('disabled', 'disabled'); + return $("#" + this.script_loader.uniq_id).children('select').prop('disabled', 'disabled'); } - } + }; - reset_endpoint_form(show) { - const spinner = $(`#sparqlGraphSpinner-${this.endpoint_loader.select_id}`); - spinner.css('display','none'); + Huviz.prototype.reset_endpoint_form = function(show) { + var spinner; + spinner = $("#sparqlGraphSpinner-" + this.endpoint_loader.select_id); + spinner.css('display', 'none'); this.endpoint_labels_JQElem.prop('disabled', false).val(""); this.endpoint_limit_JQElem.prop('disabled', false).val(this.sparql_query_default_limit); if (show) { @@ -14255,400 +12694,355 @@ LIMIT ${node_limit}\ } else { return this.sparqlQryInput_hide(); } - } + }; - disable_go_button() { - let disable; + Huviz.prototype.disable_go_button = function() { + var disable; this.update_go_button((disable = true)); - } + }; - enable_go_button() { - let disable; + Huviz.prototype.enable_go_button = function() { + var disable; this.update_go_button((disable = false)); - } + }; - update_go_button(disable) { - if ((disable == null)) { + Huviz.prototype.update_go_button = function(disable) { + var ds_on, ds_v, on_v; + if (disable == null) { if (this.script_loader.value) { disable = false; } else if (this.using_sparql()) { disable = false; } else { - const ds_v = this.dataset_loader.value; - const on_v = this.ontology_loader.value; - //console.log("DATASET: #{ds_v}\nONTOLOGY: #{on_v}") - disable = (!(ds_v && on_v)) || ([ds_v, on_v].includes('provide')); - const ds_on = `${ds_v} AND ${on_v}`; + ds_v = this.dataset_loader.value; + on_v = this.ontology_loader.value; + disable = (!(ds_v && on_v)) || ('provide' === ds_v || 'provide' === on_v); + ds_on = "" + ds_v + " AND " + on_v; } } this.big_go_button.prop('disabled', disable); - } + }; - get_reload_uri() { + Huviz.prototype.get_reload_uri = function() { return this.reload_uri || new URL(window.location); - } + }; - generate_reload_uri(dataset, ontology, endpoint) { - let uri; - this.reload_uri = (uri = new URL(document.location)); + Huviz.prototype.generate_reload_uri = function(dataset, ontology, endpoint) { + var uri; + this.reload_uri = uri = new URL(document.location); if (dataset && ontology) { - uri.hash = `load+${dataset.value}+with+${ontology.value}`; + uri.hash = "load+" + dataset.value + "+with+" + ontology.value; } else if (endpoint) { - uri.hash = "query+"+encodeURIComponent(endpoint.value); + uri.hash = "query+" + encodeURIComponent(endpoint.value); if (endpoint.graph && endpoint.graph.value) { - uri.hash += "+from+"+encodeURIComponent(endpoint.graph.value); + uri.hash += "+from+" + encodeURIComponent(endpoint.graph.value); } if (endpoint.item && endpoint.item.value) { - uri.hash += "+seeking+"+encodeURIComponent(endpoint.item.value); + uri.hash += "+seeking+" + encodeURIComponent(endpoint.item.value); } if (endpoint.limit) { - uri.hash += "+limit+"+encodeURIComponent(endpoint.limit); + uri.hash += "+limit+" + encodeURIComponent(endpoint.limit); } } return uri; - } + }; - get_data_ontology_display_id() { - if (this.data_ontology_display_id == null) { this.data_ontology_display_id = this.unique_id('datontdisp_'); } + Huviz.prototype.get_data_ontology_display_id = function() { + if (this.data_ontology_display_id == null) { + this.data_ontology_display_id = this.unique_id('datontdisp_'); + } return this.data_ontology_display_id; - } + }; - hide_pickers() { - return $(this.pickersSel).attr("style","display:none"); - } + Huviz.prototype.hide_pickers = function() { + return $(this.pickersSel).attr("style", "display:none"); + }; - replace_loader_display(dataset, ontology, endpoint) { + Huviz.prototype.replace_loader_display = function(dataset, ontology, endpoint) { + var vis_src_args; this.generate_reload_uri(dataset, ontology, endpoint); this.hide_pickers(); - const vis_src_args = { + vis_src_args = { uri: this.get_reload_uri(), - dataset, - ontology, - endpoint, + dataset: dataset, + ontology: ontology, + endpoint: endpoint, script: "TODO include script stuff here" }; this.render_visualization_source_display(vis_src_args); - } + }; - render_visualization_source_display(vis_src_args) { - let add_reload_button, source_html; - const {dataset, ontology, endpoint, script, uri} = vis_src_args; + Huviz.prototype.render_visualization_source_display = function(vis_src_args) { + var add_reload_button, controls, dataset, endpoint, ontology, reload_html, script, sel, source_html, uri, visualization_source_display; + dataset = vis_src_args.dataset, ontology = vis_src_args.ontology, endpoint = vis_src_args.endpoint, script = vis_src_args.script, uri = vis_src_args.uri; if (dataset && ontology) { add_reload_button = true; - source_html = `\ -

    Dataset: ${dataset.label}

    -

    Ontology: ${ontology.label}

    \ -`; + source_html = "

    Dataset: " + dataset.label + "

    \n

    Ontology: " + ontology.label + "

    "; } else if (endpoint) { add_reload_button = true; - source_html = `\ -

    Endpoint: ${endpoint.label}

    \ -`; + source_html = "

    Endpoint: " + endpoint.label + "

    "; if (endpoint.graph) { - source_html += `\ -

    Graph: ${endpoint.graph.label}

    \ -`; + source_html += "

    Graph: " + endpoint.graph.label + "

    "; } if (endpoint.item) { - source_html += `\ -

    Item: ${endpoint.item.label}

    \ -`; + source_html += "

    Item: " + endpoint.item.label + "

    "; } if (endpoint.limit) { - source_html += `\ -

    Limit: ${endpoint.limit}

    \ -`; + source_html += "

    Limit: " + endpoint.limit + "

    "; } } else if (script) { - source_html = `\ -

    Script: ${script}

    \ -`; + source_html = "

    Script: " + script + "

    "; } else { - source_html = `\ -

    Source:TBD

    \ -`; - } - const reload_html = `\ -

    - - - -

    \ -`; - const visualization_source_display = `\ -
    - ${source_html} - ${(add_reload_button && reload_html) || ''} -
    -
    `; // """ the extra set of triple double quotes is for emacs coffescript mode - const sel = this.oldToUniqueTabSel['huvis_controls']; - const controls = document.querySelector(sel); + source_html = "

    Source:TBD

    "; + } + reload_html = "

    \n \n \n \n

    "; + visualization_source_display = "
    \n " + source_html + "\n " + (add_reload_button && reload_html || '') + "\n
    \n
    "; + sel = this.oldToUniqueTabSel['huvis_controls']; + controls = document.querySelector(sel); controls.insertAdjacentHTML('afterbegin', visualization_source_display); - } + }; - replace_loader_display_for_endpoint(endpoint, graph) { - let print_graph; - $(this.pickersSel).attr("style","display:none"); - //uri = new URL(location) - //uri.hash = "load+#{dataset.value}+with+#{ontology.value}" + Huviz.prototype.replace_loader_display_for_endpoint = function(endpoint, graph) { + var data_ontol_display, print_graph; + $(this.pickersSel).attr("style", "display:none"); if (graph) { - print_graph = `

    Graph: ${graph}

    `; + print_graph = "

    Graph: " + graph + "

    "; } else { print_graph = ""; } - const data_ontol_display = `\ -
    -

    Endpoint: ${endpoint}

    - ${print_graph} -
    -
    `; + data_ontol_display = "
    \n

    Endpoint: " + endpoint + "

    \n " + print_graph + "\n
    \n
    "; return $("#huvis_controls").prepend(data_ontol_display); - } + }; - update_browser_title(dataset) { + Huviz.prototype.update_browser_title = function(dataset) { if (dataset.value) { return this.set_browser_title(dataset.label); } - } + }; - set_browser_title(label) { + Huviz.prototype.set_browser_title = function(label) { return document.title = label + " - Huvis Graph Visualization"; - } + }; - make_git_link() { - const base = this.args.git_base_url; - return `${this.git_commit_hash}`; // """ - } + Huviz.prototype.make_git_link = function() { + var base; + base = this.args.git_base_url; + return "" + this.git_commit_hash + ""; + }; - create_caption() { + Huviz.prototype.create_caption = function() { + var dm, om; this.captionId = this.unique_id('caption_'); this.addDivWithIdAndClasses(this.captionId, "graph_title_set git_commit_hash_watermark"); this.captionElem = document.querySelector('#' + this.captionId); if (this.git_commit_hash) { this.insertBeforeEnd(this.captionElem, this.make_git_link()); } - const dm = 'dataset_watermark'; - this.insertBeforeEnd(this.captionElem, `
    `); // """ - this.make_JQElem(dm, this.args.huviz_top_sel + ' .' + dm); // @dataset_watermark_JQElem - const om = 'ontology_watermark'; - this.insertBeforeEnd(this.captionElem, `
    `); // """ - this.make_JQElem(om, this.args.huviz_top_sel + ' .' + om); // @ontology_watermark_JQElem - } + dm = 'dataset_watermark'; + this.insertBeforeEnd(this.captionElem, "
    "); + this.make_JQElem(dm, this.args.huviz_top_sel + ' .' + dm); + om = 'ontology_watermark'; + this.insertBeforeEnd(this.captionElem, "
    "); + this.make_JQElem(om, this.args.huviz_top_sel + ' .' + om); + }; - update_caption(dataset_str, ontology_str) { + Huviz.prototype.update_caption = function(dataset_str, ontology_str) { this.dataset_watermark_JQElem.text(dataset_str); this.ontology_watermark_JQElem.text(ontology_str); - } + }; - set_ontology_from_dataset_if_possible(args) { - if (args == null) { args = {}; } - if (args.pickOrProvide === this.ontology_loader) { // and @dataset_loader.value - // The ontology_loader being adjusted provoked this call. - // We do not want to override the adjustment just made by the user. + Huviz.prototype.set_ontology_from_dataset_if_possible = function(args) { + var ontologyUri, ontology_label, option; + if (args == null) { + args = {}; + } + if (args.pickOrProvide === this.ontology_loader) { return; } - if (this.dataset_loader.value) { // and not @ontology_loader.value - const option = this.dataset_loader.get_selected_option(); - const ontologyUri = option.data('ontologyUri'); - const ontology_label = option.data('ontology_label'); //default set in group json file - if (ontologyUri) { // let the uri (if present) dominate the label + if (this.dataset_loader.value) { + option = this.dataset_loader.get_selected_option(); + ontologyUri = option.data('ontologyUri'); + ontology_label = option.data('ontology_label'); + if (ontologyUri) { this.set_ontology_with_uri(ontologyUri); } else { this.set_ontology_with_label(ontology_label); } } this.ontology_loader.update_state(); - } + }; - set_ontology_with_label(ontology_label) { - const topSel = this.args.huviz_top_sel; - const sel = topSel + ` option[label='${ontology_label}']`; - for (let ont_opt of Array.from($(sel))) { // FIXME make this re-entrant + Huviz.prototype.set_ontology_with_label = function(ontology_label) { + var ont_opt, sel, topSel, _i, _len, _ref; + topSel = this.args.huviz_top_sel; + sel = topSel + (" option[label='" + ontology_label + "']"); + _ref = $(sel); + for (_i = 0, _len = _ref.length; _i < _len; _i++) { + ont_opt = _ref[_i]; this.ontology_loader.select_option($(ont_opt)); return; } - } + }; - set_dataset_with_uri(uri) { - // TODO use PickOrProvide.select_by_uri() as in query_from_seeking_limit() - const topSel = this.args.huviz_top_sel; - const option = $(topSel + ' option[value="' + uri + '"]'); + Huviz.prototype.set_dataset_with_uri = function(uri) { + var option, topSel; + topSel = this.args.huviz_top_sel; + option = $(topSel + ' option[value="' + uri + '"]'); return this.dataset_loader.select_option(option); - } + }; - set_ontology_with_uri(ontologyUri) { - // TODO use PickOrProvide.select_by_uri() as in query_from_seeking_limit() - const topSel = this.args.huviz_top_sel; - const ontology_option = $(topSel + ' option[value="' + ontologyUri + '"]'); + Huviz.prototype.set_ontology_with_uri = function(ontologyUri) { + var ontology_option, topSel; + topSel = this.args.huviz_top_sel; + ontology_option = $(topSel + ' option[value="' + ontologyUri + '"]'); return this.ontology_loader.select_option(ontology_option); - } + }; - build_sparql_form() { + Huviz.prototype.build_sparql_form = function() { + var endpoint_labels_id, endpoint_limit_id, fromGraph, select_box, sparqlGraphSelectorId, sparqlQryInput_id, spo_query_id; this.sparqlId = unique_id(); - const sparqlQryInput_id = `sparqlQryInput_${this.sparqlId}`; + sparqlQryInput_id = "sparqlQryInput_" + this.sparqlId; this.sparqlQryInput_selector = "#" + sparqlQryInput_id; - const endpoint_limit_id = unique_id('endpoint_limit_'); - const endpoint_labels_id = unique_id('endpoint_labels_'); - const spo_query_id = unique_id('spo_query_'); - const sparqlGraphSelectorId = `sparqlGraphOptions-${this.endpoint_loader.select_id}`; - const select_box = `\ - - -