Redux
Modifying particles with Redux
by IPWright83
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/redux/3.7.2/redux.js"></script>
<svg width="960" height="500"></svg>
JavaScript
const nodes = 200;
const width = 960;
const height = 500;
const initState = {};
d3.range(nodes).forEach((d, i) => initState[i] = { xloc: 0, yloc: 0, xvel: 0, yvel: 0 });
const x = d3.scaleLinear().domain([-5, 5]).range([0, width]);
const y = d3.scaleLinear().domain([-5, 5]).range([0, height]);
const circle = d3.select("svg")
.selectAll("circle")
.data(Object.values(initState)).enter()
.append("circle")
.attr("cx", 10)
.attr("cy", 10)
.attr("r", 1);
const reducer = (state = initState, action) => {
switch(action.type) {
case "VELOCITY": {
const payload = action.payload;
const index = payload.i;
const datum = state[index];
const newDatum = {
xloc: datum.xloc + datum.xvel,
yloc: datum.yloc + datum.yvel,
xvel: datum.xvel + payload.vx,
yvel: datum.yvel + payload.vy,
};
return {
...state,
[index]: newDatum
};
}
default: return state;
}
};
const store = Redux.createStore(reducer);
store.subscribe(() => {
const data = Object.values(store.getState());
d3.select("svg")
.selectAll("circle")
.data(data)
.attr("transform", function(d) { return "translate(" + x(d.xloc) + "," + y(d.yloc) + ")"; })
.attr("r", function(d) { return Math.min(1 + 1000 * Math.abs(d.xvel * d.yvel), 10); });
});
d3.timer(function() {
const data = Object.values(store.getState());
data.forEach(function(d, i) {
const vx = 0.04 * (Math.random() - .5) - 0.05 * d.xvel - 0.0005 * d.xloc;
const vy = 0.04 * (Math.random() - .5) - 0.05 * d.yvel - 0.0005 * d.yloc;
const payload = { i, vx, vy };
store.dispatch({ type: "VELOCITY", payload })
})
});;