Add update node logic; fix JSX formatting on SVG elements.

This commit is contained in:
Kia Lam
2022-09-08 09:48:34 -07:00
committed by Jeff Bradberry
parent c1ba769b20
commit d4b25058cd
2 changed files with 59 additions and 32 deletions

View File

@@ -1,3 +1,4 @@
/* eslint i18next/no-literal-string: "off" */
import React from 'react'; import React from 'react';
import { t } from '@lingui/macro'; import { t } from '@lingui/macro';
import styled from 'styled-components'; import styled from 'styled-components';
@@ -70,14 +71,14 @@ function Legend() {
<DescriptionList isHorizontal isFluid> <DescriptionList isHorizontal isFluid>
<DescriptionListGroup> <DescriptionListGroup>
<DescriptionListTerm> <DescriptionListTerm>
<Button isSmall>{t`C`}</Button> <Button isSmall>C</Button>
</DescriptionListTerm> </DescriptionListTerm>
<DescriptionListDescription>{t`Control node`}</DescriptionListDescription> <DescriptionListDescription>{t`Control node`}</DescriptionListDescription>
</DescriptionListGroup> </DescriptionListGroup>
<DescriptionListGroup> <DescriptionListGroup>
<DescriptionListTerm> <DescriptionListTerm>
<Button variant="primary" isSmall> <Button variant="primary" isSmall>
{t`Ex`} Ex
</Button> </Button>
</DescriptionListTerm> </DescriptionListTerm>
<DescriptionListDescription> <DescriptionListDescription>
@@ -87,7 +88,7 @@ function Legend() {
<DescriptionListGroup> <DescriptionListGroup>
<DescriptionListTerm> <DescriptionListTerm>
<Button variant="primary" isSmall> <Button variant="primary" isSmall>
{t`Hy`} Hy
</Button> </Button>
</DescriptionListTerm> </DescriptionListTerm>
<DescriptionListDescription>{t`Hybrid node`}</DescriptionListDescription> <DescriptionListDescription>{t`Hybrid node`}</DescriptionListDescription>
@@ -95,7 +96,7 @@ function Legend() {
<DescriptionListGroup> <DescriptionListGroup>
<DescriptionListTerm> <DescriptionListTerm>
<Button variant="primary" isSmall> <Button variant="primary" isSmall>
{t`h`} h
</Button> </Button>
</DescriptionListTerm> </DescriptionListTerm>
<DescriptionListDescription>{t`Hop node`}</DescriptionListDescription> <DescriptionListDescription>{t`Hop node`}</DescriptionListDescription>
@@ -183,18 +184,18 @@ function Legend() {
cx="10" cx="10"
cy="10" cy="10"
fill="transparent" fill="transparent"
stroke-width="1px" strokeWidth="1px"
stroke="#ccc" stroke="#ccc"
></circle> />
<text <text
x="10" x="10"
y="10" y="10"
text-anchor="middle" textAnchor="middle"
dominant-baseline="central" dominantBaseline="central"
fill="black" fill="black"
font-size="11px" fontSize="11px"
font-family="inherit" fontFamily="inherit"
font-weight="400" fontWeight="400"
> >
C C
</text> </text>
@@ -210,19 +211,19 @@ function Legend() {
cx="10" cx="10"
cy="10" cy="10"
fill="transparent" fill="transparent"
stroke-dasharray="3" strokeDasharray="5"
stroke-width="1px" strokeWidth="1px"
stroke="#ccc" stroke="#ccc"
></circle> />
<text <text
x="10" x="10"
y="10" y="10"
text-anchor="middle" textAnchor="middle"
dominant-baseline="central" dominantBaseline="central"
fill="black" fill="black"
font-size="11px" fontSize="11px"
font-family="inherit" fontFamily="inherit"
font-weight="400" fontWeight="400"
> >
C C
</text> </text>

View File

@@ -41,6 +41,7 @@ const Loader = styled(ContentLoading)`
background: white; background: white;
`; `;
function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) { function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) {
const [storedNodes, setStoredNodes] = useState(null);
const [isNodeSelected, setIsNodeSelected] = useState(false); const [isNodeSelected, setIsNodeSelected] = useState(false);
const [selectedNode, setSelectedNode] = useState(null); const [selectedNode, setSelectedNode] = useState(null);
const [simulationProgress, setSimulationProgress] = useState(null); const [simulationProgress, setSimulationProgress] = useState(null);
@@ -75,6 +76,42 @@ function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) {
fetchDetails(); fetchDetails();
}, [selectedNode, fetchDetails]); }, [selectedNode, fetchDetails]);
function updateNodeSVG(nodes) {
if (nodes) {
d3.selectAll('[class*="id-"]')
.data(nodes)
.attr('stroke-dasharray', (d) => (d.enabled ? `1 0` : `5`));
}
}
useEffect(() => {
function handleResize() {
d3.select('.simulation-loader').style('visibility', 'visible');
setSelectedNode(null);
setIsNodeSelected(false);
draw();
}
window.addEventListener('resize', debounce(handleResize, 500));
handleResize();
return () => window.removeEventListener('resize', handleResize);
}, []); // eslint-disable-line react-hooks/exhaustive-deps
// update mesh when user toggles enabled/disabled slider
useEffect(() => {
if (instance?.id) {
const updatedNodes = storedNodes.map((n) =>
n.id === instance.id ? { ...n, enabled: instance.enabled } : n
);
setStoredNodes(updatedNodes);
}
}, [instance]); // eslint-disable-line react-hooks/exhaustive-deps
useEffect(() => {
if (storedNodes) {
updateNodeSVG(storedNodes);
}
}, [storedNodes]);
const draw = () => { const draw = () => {
let width; let width;
let height; let height;
@@ -124,6 +161,7 @@ function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) {
} }
function ended({ nodes, links }) { function ended({ nodes, links }) {
setStoredNodes(nodes);
// Remove loading screen // Remove loading screen
d3.select('.simulation-loader').style('visibility', 'hidden'); d3.select('.simulation-loader').style('visibility', 'hidden');
setShowZoomControls(true); setShowZoomControls(true);
@@ -205,7 +243,7 @@ function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) {
.attr('class', (d) => d.node_type) .attr('class', (d) => d.node_type)
.attr('class', (d) => `id-${d.id}`) .attr('class', (d) => `id-${d.id}`)
.attr('fill', DEFAULT_NODE_COLOR) .attr('fill', DEFAULT_NODE_COLOR)
.attr('stroke-dasharray', (d) => (d.enabled ? null : 3)) .attr('stroke-dasharray', (d) => (d.enabled ? `1 0` : `5`))
.attr('stroke', DEFAULT_NODE_STROKE_COLOR); .attr('stroke', DEFAULT_NODE_STROKE_COLOR);
// node type labels // node type labels
@@ -341,18 +379,6 @@ function MeshGraph({ data, showLegend, zoom, setShowZoomControls }) {
} }
}; };
useEffect(() => {
function handleResize() {
d3.select('.simulation-loader').style('visibility', 'visible');
setSelectedNode(null);
setIsNodeSelected(false);
draw();
}
window.addEventListener('resize', debounce(handleResize, 500));
handleResize();
return () => window.removeEventListener('resize', handleResize);
}, []); // eslint-disable-line react-hooks/exhaustive-deps
return ( return (
<div id="chart" style={{ position: 'relative', height: '100%' }}> <div id="chart" style={{ position: 'relative', height: '100%' }}>
{showLegend && <Legend />} {showLegend && <Legend />}