Skip to content

Instantly share code, notes, and snippets.

@PatWie
Last active August 29, 2015 14:15
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save PatWie/a68eed8e5773155c2571 to your computer and use it in GitHub Desktop.
Save PatWie/a68eed8e5773155c2571 to your computer and use it in GitHub Desktop.
simple d3js binding for animaitions

To make animation in d3js you usually have an interplay between multiple attributes of objects. This simple solution should simplify the process of animation. You just connect a value

var bindIncrease = new d3binding();
    bindIncrease.ease = "elastic"
    bindIncrease.duration = 2000
    bindIncrease.connect(line, "x2", function(v) {return 100 + v;});
    bindIncrease.connect(dot_center, "cx", function(v) {return 100 + v;});
    bindIncrease.connect(dot_extra, "cx", function(v) {return 3 * v;});
    bindIncrease.connect(hline, "x2", function(v) {return 3 * v;});
    bindIncrease.connect(hline2, "x2", function(v) {return 3 * v;});
    bindIncrease.connect(circle, "r");

and call bindIncrease.animate(100); to start the animation where x the the new target value.

<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script>
<svg id="canvas"></svg>
<button onclick="increase()">increase</button>
<button onclick="reset()">reset</button>
<script>
// a custom binding
var d3binding = function() {
// element to each object (diffeent d3-objects)
this.connections = [];
this.duration = 750;
this.ease = "linear";
// connects a binding to each attribut "property_" of "element" modified by "func"
this.connect = function(element_, property_, function_) {
this.connections.push({
element: element_,
property: property_,
function: function_
});
}
// the value
this.currentValue = null;
this.value = function() {
return this.currentValue;
}
// on value changes
this.animate = function(x) {
// update the value itself
this.currentValue = x;
var parent = this;
d3.transition()
.duration(parent.duration)
.ease(parent.ease)
.each(function() {
// update each binded-object
for (var i = 0; i < parent.connections.length; i++) {
var bindObject = parent.connections[i];
var modifier = function(x) {
return x;
};
if (typeof bindObject.function !== "undefined") {
modifier = bindObject.function;
}
var to = modifier(x);
var attrName = bindObject.property;
bindObject.element
.transition()
.attr(attrName, to);
}
});
};
// on value changes
this.jump = function(x) {
// update the value itself
this.currentValue = x;
var parent = this;
// update each binded-object
for (var i = 0; i < parent.connections.length; i++) {
var bindObject = parent.connections[i];
var modifier = function(x) {
return x;
};
if (typeof bindObject.function !== "undefined") {
modifier = bindObject.function;
}
var to = modifier(x);
var attrName = bindObject.property;
bindObject.element.attr(attrName, to);
}
};
}
</script>
<script>
// select the svg object
var svg = d3.select("#canvas")
.attr("width", 350)
.attr("height", 350);
// create dummy scene
var circle = svg.append("circle")
.attr("r", 50)
.attr("cx", 100)
.attr("cy", 100)
.attr("fill", "lightsteelblue")
.attr("fill-opacity", 0.5);
var line = svg.append("line")
.attr("stroke", "steelblue")
.attr("stroke-width", 2)
.attr("x1", 100)
.attr("y1", 0)
.attr("x2", 100)
.attr("y2", 100);
var hline = svg.append("line")
.attr("stroke", "red")
.attr("stroke-width", "5,5")
.attr("x1", 100)
.attr("y1", 0)
.attr("x2", 100)
.attr("y2", 150);
var hline2 = svg.append("line")
.attr("stroke", "red")
.attr("stroke-dasharray", "5,5")
.attr("x1", 100)
.attr("y1", 150)
.attr("x2", 100)
.attr("y2", 150);
var dot_center = svg.append("circle")
.attr("fill", "steelblue")
.attr("r", 5)
.attr("cx", 100)
.attr("cy", 100);
var dot_extra = svg.append("circle")
.attr("r", 3.5)
.attr("cx", 100)
.attr("fill", "red")
.attr("cy", 150);
var bindIncrease = new d3binding();
bindIncrease.ease = "elastic"
bindIncrease.duration = 2000
bindIncrease.connect(line, "x2", function(v) {return 100 + v;});
bindIncrease.connect(dot_center, "cx", function(v) {return 100 + v;});
bindIncrease.connect(dot_extra, "cx", function(v) {return 3 * v;});
bindIncrease.connect(hline, "x2", function(v) {return 3 * v;});
bindIncrease.connect(hline2, "x2", function(v) {return 3 * v;});
bindIncrease.connect(circle, "r");
var bindReset = new d3binding();
bindReset.ease = "bounce"
bindReset.duration = 2000
bindReset.connect(line, "x2");
bindReset.connect(dot_center, "cx");
bindReset.connect(dot_extra, "cx");
bindReset.connect(hline, "x2");
bindReset.connect(hline2, "x2");
bindReset.connect(circle, "r", function(v) {return v - 50;});
var increase = function() {
bindIncrease.animate(100);
}
var reset = function() {
bindReset.animate(100);
}
</script>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment