Soy nuevo en D3.js y estoy tratando de hacer alguna animación con mi gráfico, pero no puedo resolver un problema con el método .get()
llamado en un d3.map
para la versión 6 de D3. Cuando ejecuto el código arroja un error:
nodeById.get no es una función
Mi código se basa en: https://bl.ocks.org/ctufts/bd6956a45ea69734f5909c8b526c13b5
//some fetch data in json file d3.json("someURLjsonfile").then(function (graph) { let nodes = graph.nodes, nodeById = d3.map(nodes, function (d) { return d.id; }), links = graph.links, bilinks = []; links.forEach(function (link) { var s = nodeById.get(link.source), // <-- error t = nodeById.get(link.target), // <-- error i = {}; // intermediate node nodes.push(i); links.push({ source: s, target: i }, { source: i, target: t }); bilinks.push([s, i, t]); });
Su problema se debe a un rediseño bastante desafortunado de la API. A partir de D3 v6, el módulo d3-collection
quedó obsoleto y se eliminó del paquete D3. Ese módulo contenía el método constructor d3.map()
que crearía un objeto d3.map
, es decir, una de las implementaciones de mapas internos de D3 que imitan el Map
nativo de JavaScript. Este método ha existido por un tiempo, pero perdió importancia una vez que la función ES6 estuvo disponible y, por lo tanto, se eliminó.
Lamentablemente, con la versión 2 del módulo d3-array
se introdujo un método con el mismo nombre que es básicamente equivalente a los métodos nativos array.map()
o Array.from()
:
# d3. map ( iterable , mapper ) · Fuente
Devuelve una nueva matriz que contiene los valores asignados de iterable , en orden, según lo definido por la función asignadora dada. Equivalente a array.map y Array.from :
Dado que d3-array
v2 se introdujo en el paquete con la misma versión 6 que también eliminó d3-collection
la propiedad d3.map
aún está disponible; sin embargo, su significado ha cambiado.
Su código parece haber sido escrito para D3 <v6 y se rompe debido a los cambios establecidos anteriormente. El nuevo d3.map()
es una función de mapeo, no un constructor; devuelve una matriz que no presenta un método .get()
, por lo tanto, el error.
Para solucionar el problema, puede cambiar su código para usar directamente el objeto Map
incorporado en su lugar:
nodeById = new Map(Array.from(nodes, d => [d.id, d]));
Con el resto intacto, su código debería funcionar como se esperaba.