Skip to content

Commit

Permalink
Merge pull request #57 from chanzuckerberg/responsiveBrush
Browse files Browse the repository at this point in the history
reset brush on window resize
  • Loading branch information
colinmegill authored May 15, 2018
2 parents 82a5bae + 2b2bdba commit f5f9700
Show file tree
Hide file tree
Showing 2 changed files with 62 additions and 51 deletions.
74 changes: 42 additions & 32 deletions src/components/graph/graph.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import React from "react";
import _ from "lodash";
import * as globals from "../../globals";
import styles from "./graph.css";
import { setupGraphElements } from "./drawGraph";
import { setupSVGandBrushElements } from "./setupSVGandBrush";
import SectionHeader from "../framework/sectionHeader";
import { connect } from "react-redux";
import actions from "../../actions";
Expand Down Expand Up @@ -64,12 +64,6 @@ class Graph extends React.Component {
};
}
componentDidMount() {
const { svg } = setupGraphElements(
this.handleBrushSelectAction.bind(this),
this.handleBrushDeselectAction.bind(this)
);
this.setState({ svg });

// setup canvas and camera
const camera = _camera(this.reglCanvas, { scale: true, rotate: false });
const regl = _regl(this.reglCanvas);
Expand Down Expand Up @@ -111,49 +105,61 @@ class Graph extends React.Component {

componentWillReceiveProps(nextProps) {
if (this.state.regl && nextProps.vertices) {
/* update regl */
const vertices = nextProps.currentCellSelection;
const vertexCount = vertices.length;
const positions = new Float32Array(2 * vertexCount);
const colors = new Float32Array(3 * vertexCount);
const sizes = new Float32Array(vertexCount);

// Cache a scaled graph
if (!this.scaledGraphVec || this.props.graphVec !== nextProps.graphVec) {
const positions = new Float32Array(2 * vertexCount);

// d3.scaleLinear().domain([0,1]).range([-1,1])
const glScaleX = scaleLinear([0, 1], [-1, 1]);
// d3.scaleLinear().domain([0,1]).range([1,-1])
const glScaleY = scaleLinear([0, 1], [1, -1]);

const graphVec = nextProps.graphVec;
for (var i = 0; i < vertexCount; i++) {
const cell = vertices[i];
const cellIdx = cell.__cellIndex__;

const x = glScaleX(graphVec[2 * cellIdx]);
const y = glScaleY(graphVec[2 * cellIdx + 1]);
positions[2 * i] = x;
positions[2 * i + 1] = y;
}
this.scaledGraphVec = positions;
}
// d3.scaleLinear().domain([0,1]).range([-1,1])
const glScaleX = scaleLinear([0, 1], [-1, 1]);
// d3.scaleLinear().domain([0,1]).range([1,-1])
const glScaleY = scaleLinear([0, 1], [1, -1]);

/*
Construct Size & Color Vectors
Construct Vectors
*/
const graphVec = nextProps.graphVec;
for (var i = 0; i < vertexCount; i++) {
const cell = vertices[i];
const cellIdx = cell.__cellIndex__;
const x = glScaleX(graphVec[2 * cellIdx]);
const y = glScaleY(graphVec[2 * cellIdx + 1]);
positions[2 * i] = x;
positions[2 * i + 1] = y;

colors.set(cell.__colorRGB__, 3 * i);

sizes[i] = cell.__selected__
? 4
: 0.2; /* make this a function of the number of total cells, including regraph */
}

this.state.pointBuffer({ data: this.scaledGraphVec, dimension: 2 });
this.state.pointBuffer({ data: positions, dimension: 2 });
this.state.colorBuffer({ data: colors, dimension: 3 });
this.state.sizeBuffer({ data: sizes, dimension: 1 });
this.count = vertexCount;
}

if (
/* invisibly handles the initial null vs integer case as well as resize events */
nextProps.responsive.height !== this.props.responsive.height ||
nextProps.responsive.width !== this.props.responsive.width
) {
/* clear out whatever was on the div, even if nothing, but usually the brushes etc */
d3
.select("#graphAttachPoint")
.selectAll("*")
.remove();
const { svg } = setupSVGandBrushElements(
this.handleBrushSelectAction.bind(this),
this.handleBrushDeselectAction.bind(this),
nextProps.responsive,
this.graphPaddingTop
);
this.setState({ svg });
}
}
handleBrushSelectAction() {
/*
Expand All @@ -176,8 +182,12 @@ class Graph extends React.Component {

// transform screen coordinates -> cell coordinates
const invert = pin => {
const x = 2 * pin[0] / globals.graphWidth - 1;
const y = 2 * (1 - pin[1] / globals.graphHeight) - 1;
const x =
2 * pin[0] / (this.props.responsive.height - this.graphPaddingTop) - 1;
const y =
2 *
(1 - pin[1] / (this.props.responsive.height - this.graphPaddingTop)) -
1;
const pout = [x + inverse[12], y + inverse[13]];
return [(pout[0] + 1) / 2, (pout[1] + 1) / 2];
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,38 +5,39 @@ import * as globals from "../../globals";

/******************************************
*******************************************
put svg in DOM
put svg & brush in DOM
*******************************************
******************************************/

export const setupGraphElements = (
export const setupSVGandBrushElements = (
handleBrushSelectAction,
handleBrushDeselectAction
handleBrushDeselectAction,
responsive,
graphPaddingTop
) => {
var svg = d3
const side = responsive.height - graphPaddingTop;
const svg = d3
.select("#graphAttachPoint")
.append("svg")
.attr("width", globals.graphWidth)
.attr("height", globals.graphHeight)
.attr("width", side)
.attr("height", side)
.attr("class", `${styles.graphSVG}`);

setupGraphBrush(svg, handleBrushSelectAction, handleBrushDeselectAction);

return {
svg
};
};

const setupGraphBrush = (
svg,
handleBrushSelectAction,
handleBrushDeselectAction
) => {
svg.append("g").call(
d3
.brush()
.extent([[0, 0], [globals.graphWidth, globals.graphHeight]])
.extent([
[0, 0],
[
responsive.height - graphPaddingTop,
responsive.height - graphPaddingTop
]
])
.on("brush", handleBrushSelectAction)
.on("end", handleBrushDeselectAction)
);

return {
svg
};
};

0 comments on commit f5f9700

Please sign in to comment.