I need to override the default node hover effect on a network graph in Highchart.js. The default behaviour is that when you hover on a Node the linkedTo and linkedFrom Nodes are highlighted, the desired behaviour would be that when I hover on a Node,only the linkedFrom Nodes are highlighted, basically like a Breadth-First-Search visualization, I’ve managed to write the algorithm, but some extra Nodes are highlighted.
This is the algorithm I use to highlight all the Nodes, but this doesn’t override the default functionality
point: {
events: {
mouseOver: function () {
var point = this,
chart = this.series.chart,
nodes = chart.series[0].nodes;
bfs(this.id);
function bfs(start) {
const queue = [findNodeById(start)];
// Store visited nodes in a set
const visited = new Set();
// Loop until we have something in the queue
while (queue.length > 0) {
// Pop out first element from queue
const topNode = queue.shift();
// Edges TO first element
const prevEdges = topNode.linksTo;
for (const edge of prevEdges) {
// For each edge find their corresponding nodes and set their state to 'hover'
let prevNode = findNodeById(edge.from);
prevNode.setState("hover");
// If edge is not visited yet, push to Set and add to queue
if (!visited.has(prevNode)) {
visited.add(prevNode);
queue.push(prevNode);
}
// nextNode.setState('inactive')
}
}
}
function findNodeById(id) {
return nodes.filter((node) => node.id == id)[0];
}
},
},
},
I’ve tried to disable/enable the hover state, but didn’t work. My approach might be completely wrong here, any suggestion is appreciated!
Advertisement
Answer
The simplest solution is to overwrite the default setState function, example:
(function(H) {
H.seriesTypes.networkgraph.prototype.pointClass.prototype.setState = function(state) {
var args = arguments,
Point = H.Point,
others = this.isNode ? this.linksTo.concat(this.linksFrom) : [this.fromNode,
this.toNode
];
if (state !== 'select') {
others.forEach(function(linkOrNode) {
if (linkOrNode && linkOrNode.series) {
Point.prototype.setState.apply(linkOrNode, args);
if (!linkOrNode.isNode) {
if (linkOrNode.fromNode.graphic) {
Point.prototype.setState.apply(linkOrNode.fromNode, args);
}
/* Modification - prevent hover effect on toNode
if (linkOrNode.toNode && linkOrNode.toNode.graphic) {
Point.prototype.setState.apply(linkOrNode.toNode, args);
}
*/
}
}
});
}
Point.prototype.setState.apply(this, args);
}
}(Highcharts));
Live demo: https://jsfiddle.net/BlackLabel/1039zwbt/1/
Docs: https://www.highcharts.com/docs/extending-highcharts/extending-highcharts