Mercurial > hg > NetworkVis
diff popoto_dev/js/app-ismi.js @ 12:d67c5ad47709
implementation with dropdown popup, unfinished
author | alistair |
---|---|
date | Fri, 02 Oct 2015 01:08:46 -0400 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/popoto_dev/js/app-ismi.js Fri Oct 02 01:08:46 2015 -0400 @@ -0,0 +1,401 @@ +/** + * URL used to access Neo4j REST API to execute queries. + * Update this parameter to your running server instance. + * + * For more information on Neo4J REST API the documentation is available here: http://neo4j.com/docs/stable/rest-api-cypher.html + */ +popoto.rest.CYPHER_URL = "https://ismi-dev.mpiwg-berlin.mpg.de/neo4j-ismi/db/data/transaction/commit"; +//popoto.rest.CYPHER_URL = "http://localhost:7474/db/data/transaction/commit"; + +/** + * Add this authorization property if your Neo4j server uses basic HTTP authentication. + * The value of this property must be "Basic <payload>", where "payload" is a base64 encoded string of "username:password". + * + * "btoa" is a JavaScript function that can be used to encode the user and password value in base64 but it is recommended to directly use the Base64 value. + * + * For example Base64 encoding value of "neo4j:password" is "bmVvNGo6cGFzc3dvcmQ=" + */ +popoto.rest.AUTHORIZATION = "Basic " + btoa("neo4j:neo5j"); +//popoto.rest.AUTHORIZATION = "Basic " + btoa("neo4j:eagrussell"); + +/** + * These functions fill the predefinedConstraints array for "PERSON" + * Called when the filter button is hit + * + * Uses the text box implementation currently + */ + // TODO: finish textbox implementation as backup + // have single filter button which on click sets constraints equal to d3.select("#constraintNUMBS)[0][0].value + // for a bunch of spots in the array + // will have to create only 1 d3.select + // the d3.select will need to know what constraints to pull from input boxes based on ids related to whether they + // are person/codex/witness/etc attributes and put them into the corresponding arrays + // personPredefinedConstraints codexPreDef +var personPredefinedConstraints = []; +var codexPredefinedConstraints = []; +var witnessPredefinedConstraints = []; +d3.select("#filter-button").on("click", function (d) { + personPredefinedConstraints = []; + codexPredefinedConstraints = []; + witnessPredefinedConstraints = []; + + var person1 = d3.select("#person-constraint")[0][0].value; + var person2 = d3.select("#person-constraint2")[0][0].value; + + var codex1 = d3.select("#codex-constraint")[0][0].value; + var codex2 = d3.select("#codex-constraint2")[0][0].value; + + var witness1 = d3.select("#witness-constraint")[0][0].value; + var witness2 = d3.select("#witness-constraint2")[0][0].value; + + if (person1.substring(person1.indexOf('"')+1,person1.lastIndexOf('"'))) personPredefinedConstraints.push(person1); + if (person2.substring(person2.indexOf('"')+1,person2.lastIndexOf('"'))) personPredefinedConstraints.push(person2); + + if (codex1.substring(codex1.indexOf('"')+1,codex1.lastIndexOf('"'))) codexPredefinedConstraints.push(codex1); + if (codex2.substring(codex2.indexOf('"')+1,codex2.lastIndexOf('"'))) codexPredefinedConstraints.push(codex2); + + if (witness1.substring(witness1.indexOf('"')+1,witness1.lastIndexOf('"'))) witnessPredefinedConstraints.push(witness1); + if (witness2.substring(witness2.indexOf('"')+1,witness2.lastIndexOf('"'))) witnessPredefinedConstraints.push(witness2); + + // Recreate taxonomies panel + d3.select("#" + popoto.taxonomy.containerId).selectAll("ul").data([]).exit().remove(); + popoto.taxonomy.createTaxonomyPanel(); + + popoto.tools.reset(); +}); + +d3.select("#clear-button").on("click", function (d) { + personPredefinedConstraints = []; + codexPredefinedConstraints = []; + witnessPredefinedConstraints = []; + + // Recreate taxonomies panel + d3.select("#" + popoto.taxonomy.containerId).selectAll("ul").data([]).exit().remove(); + popoto.taxonomy.createTaxonomyPanel(); + + popoto.tools.reset(); +}); + + +/** + * Define the Label provider you need for your application. + * This configuration is mandatory and should contain at least all the labels you could find in your graph model. + * + * In this alpha version only nodes with a label are supported. + * + * By default If no attributes are specified Neo4j internal ID will be used. + * These label provider configuration can be used to customize the node display in the graph. + * See www.popotojs.com or example for more details on available configuration options. + */ +// TODO: add in predefined constraint functions for other nodeProviders +popoto.provider.nodeProviders = { + "CODEX": { + "returnAttributes": ["label", "ismi_id", "identifier"], + "displayAttribute": "label", + "getPredefinedConstraints": function (node) { + return codexPredefinedConstraints; + }, + }, + "WITNESS": { + "returnAttributes": ["label", "ismi_id", "folios"], + "displayAttribute": "label", + "getPredefinedConstraints": function (node) { + return witnessPredefinedConstraints; + }, + }, + "TEXT": { + "returnAttributes": ["label", "full_title", "ismi_id"], + "displayAttribute": "label", + //"getPredefinedConstraints": function (node) { + // return textPredefinedConstraints; + //}, + }, + "PERSON": { + "returnAttributes": ["label", "ismi_id", "death_date_text", "url"], + "displayAttribute": "label", + "getPredefinedConstraints": function (node) { + return personPredefinedConstraints; + }, + }, + "REPOSITORY": { + "returnAttributes": ["label", "ismi_id"], + "displayAttribute": "label", + //"getPredefinedConstraints": function (node) { + // return repositoryPredefinedConstraints; + //}, + }, + "FLORUIT_DATE": { + "isSearchable": false, + //"getPredefinedConstraints": function (node) { + // return floruitPredefinedConstraints; + //}, + } +}; + +/** + * Popoto label provider + * Define the label provider used to customize the link displayed text: + */ +// TODO: ensure these cover all the different relations. Commented out for now. +/* +popoto.provider.linkProvider = { + + // Customize the text displayed on links: + "getLinkTextValue": function (link) { + + // The links labels are just changed in lower case in this example. + // But it is possible to use a localization mechanism here to replace values. + if (link.type === popoto.graph.link.LinkTypes.RELATION) { + + if (link.source.label == "PERSON") { + switch (link.label) { + case "was_student_of": + return "was student of"; + case "is_prime_alias_name_of": + return "is prime alias name of"; + case "was_born_in": + return "was born in"; + case "lived_in": + return "lived in"; + case "has_role": + return "has role"; + case "has_floruit_date": + return "has floruit date"; + case "died_in": + return "died in"; + default : + return "" + } + } + if (link.source.label == "CODEX") { + switch (link.label) { + case "owned_by": + return "owned by"; + case "is_alias_of": + return "is alias of"; + case "is_part_of": + return "is part of"; + } + } + if (link.source.label == "WITNESS") { + switch (link.label) { + case "was_copied_in": + return "was copied in"; + case "was_studied_by": + return "was studied by"; + case "had_patron": + return "had patron"; + case "is_part_of": + return "is part of"; + case "is_exemplar_of": + return "is exemplar of"; + case "has_title_written_as": + return "has title written as"; + case "has_author_written_as": + return "as author written as"; + case "was_copied_by": + return "was copied by"; + } + } + if (link.source.label == "PLACE") { + switch (link.label) { + case "is_part_of": + return "is part of"; + case "is_in": + return "is in"; + } + } + } else { + return popoto.provider.getSemanticValue(link.target); + } + } + +}; +*/ + + + + + + + +//d3.select("#clear-button").on("click", function (d) { +// popoto.graph.node.expandNode() +//}); + +//take d3.select of any click that calls popoto.graph.node.expandNode() +// make sure to search in popoto.js what kind of events trigger the expandNode fn +// +// on these events, instead of executing the normal expandNode function, call a modified function that will generate an +// html table with the required results. Still maintaining the info being sent to results but ensuring that what is +// displayed is thrown into a table. + +// to override the popoto.graph.node.expandNode() fn just use: + +// Expand Override +var tableArray = []; +(function() { + var oldVersionExpand = popoto.graph.node.expandNode; + popoto.graph.node.expandNode = function(clickedNode) { + console.log("NODES OPEN"); + //var result = oldVersionExpand.apply(this, arguments); + // do some more stuff + //return result; + + var dataToAdd = clickedNode.data; + // Then each node is created + var i = 1; + dataToAdd.forEach(function (d) { + // for each of these bits of data make sure to add the id and the attributes into the html list + var nx = clickedNode.x; + var ny = clickedNode.y; + + var node = { + "id": (++popoto.graph.node.idgen), + "parent": clickedNode, + "attributes": d, + "type": popoto.graph.node.NodeTypes.VALUE, + "label": clickedNode.label, + "count": d.count, + "x": nx, + "y": ny, + "internalID": d[popoto.query.NEO4J_INTERNAL_ID.queryInternalName] + }; + + popoto.graph.force.nodes().push(node); + // add this node to an array of node values + // popoto.graph.force.nodes().push(node); + tableArray.push(node); + + var dd = document.getElementById("dropdown"); + var newListOption = document.createElement("option"); + + // TODO: Haven't been able to + newListOption.text = node.internalID; + console.log(node.internalID); + dd.add(newListOption); + + i++; + }); + + $('#dropdown').attr('style','visibility: visible; overflow: scroll; position: fixed; left: '+clickedNode.x+'px; bottom: '+clickedNode.y+'px; z-index: 10;'); + //$('#dropdown').attr('style','visibility: visible; overflow: scroll; position: fixed;'); + + // Pin clicked node and its parent to avoid the graph to move for selection, only new value nodes will blossom around the clicked node. + clickedNode.fixed = true; + + if (clickedNode.parent && clickedNode.parent.type !== popoto.graph.node.NodeTypes.ROOT) { + clickedNode.parent.fixed = true; + } + // Change node state + clickedNode.valueExpanded = true; + popoto.update(); + + }; +})(); + +// Collapse Override +(function() { + popoto.graph.node.collapseNode = function(clickedNode) { + + if (clickedNode.valueExpanded) { // node is collapsed only if it has been expanded first + console.log("NODES CLOSED"); + + popoto.logger.debug("collapseNode (" + clickedNode.label + ")"); + + // Node has been fixed when expanded so we unfix it back here. + if (clickedNode.type !== popoto.graph.node.NodeTypes.ROOT) { + clickedNode.fixed = false; + } + + // Parent node too if not root + if (clickedNode.parent && clickedNode.parent.type !== popoto.graph.node.NodeTypes.ROOT) { + clickedNode.parent.fixed = false; + } + + clickedNode.valueExpanded = false; + popoto.update(); + + $('#dropdown').attr('style','visibility: hidden; overflow: scroll; position: fixed;'); + //TODO: need to delete existing options + var x = document.getElementById("dropdown"); + for (i=x.length; i > 0; i--) { + if (x.length > 1) { + x.remove(x.length-1); + } + } + + } else { + popoto.logger.debug("collapseNode called on an unexpanded node"); + } + }; +})(); + + +d3.select("#dropdown").on("change", function (d) { + if (document.getElementById('dropdown').value != '- Select -') { + console.log(document.getElementById('dropdown').value); + popoto.graph.node.valueNodeClick(document.getElementById('dropdown').value); + } +}); +// Value click override +(function() { + popoto.graph.node.valueNodeClick = function(selectValue) { + console.log("NODE SELECTED"); + + popoto.logger.debug("valueNodeClick (" + selectValue.label + ")"); + // change this next line to take the node id from the table and pull it from the nodes list + + var clickedNode; + for (i in tableArray) { + if (i.label == selectValue) { + clickedNode = i; + } + } + + clickedNode.parent.value = clickedNode; + popoto.result.hasChanged = true; + popoto.graph.hasGraphChanged = true; + + popoto.graph.node.collapseNode(clickedNode.parent); + }; +})(); + + +/** + * Here a listener is used to retrieve the total results count and update the page accordingly. + * This listener will be called on every graph modification. + */ +popoto.result.onTotalResultCount(function (count) { + document.getElementById("result-total-count").innerHTML = "(" + count + ")"; +}); + +/** + * The number of results returned can be changed with the following parameter. + * Default value is 100. + * + * Note that in this current alpha version no pagination mechanism is available in displayed results + */ +popoto.query.RESULTS_PAGE_SIZE = 1000; + + +/** + * For the alpha version, popoto.js has been generated with debug traces you can activate with the following properties: + * The value can be one in DEBUG, INFO, WARN, ERROR, NONE. + * + * With INFO level all the executed cypher query can be seen in the navigator console. + * Default is NONE + */ +popoto.logger.LEVEL = popoto.logger.LogLevels.INFO; + +/** + * Start popoto.js generation. + * The function requires the label to use as root element in the graph. + */ +popoto.start("PERSON"); + +/* do not zoom with scroll wheel */ +popoto.graph.WHEEL_ZOOM_ENABLED = false; + +/* show source and target relations */ +popoto.query.USE_RELATION_DIRECTION = true;