<script type="text/javascript" src="../tests/range_tests.js"></script>
<script type="text/javascript" src="../tests/axis_labels.js"></script>
<script type="text/javascript" src="../tests/multi_csv.js"></script>
+ <script type="text/javascript" src="../tests/interaction_model.js"></script>
</head>
<body>
<div id='graph'></div>
g.canvas_.dispatchEvent(event);
};
-DygraphOps.dispatchMouseDown = function(g, x, y, custom) {
- var px = Dygraph.findPosX(g.canvas_);
- var py = Dygraph.findPosY(g.canvas_);
-
- var pageX = px + g.toDomXCoord(x);
- var pageY = py + g.toDomYCoord(y);
+DygraphOps.dispatchMouseDown_Point = function(g, x, y, custom) {
+ var pageX = Dygraph.findPosX(g.canvas_) + x;
+ var pageY = Dygraph.findPosY(g.canvas_) + y;
var opts = {
type : 'mousedown',
var event = DygraphOps.createEvent_(opts, custom);
g.canvas_.dispatchEvent(event);
-};
-
-DygraphOps.dispatchMouseMove = function(g, x, y, custom) {
- var px = Dygraph.findPosX(g.canvas_);
- var py = Dygraph.findPosY(g.canvas_);
+}
- var pageX = px + g.toDomXCoord(x);
- var pageY = py + g.toDomYCoord(y);
+DygraphOps.dispatchMouseMove_Point = function(g, x, y, custom) {
+ var pageX = Dygraph.findPosX(g.canvas_) + x;
+ var pageY = Dygraph.findPosY(g.canvas_) + y;
var opts = {
type : 'mousemove',
g.canvas_.dispatchEvent(event);
};
-DygraphOps.dispatchMouseUp = function(g, x, y, custom) {
- var px = Dygraph.findPosX(g.canvas_);
- var py = Dygraph.findPosY(g.canvas_);
-
- var pageX = px + g.toDomXCoord(x);
- var pageY = py + g.toDomYCoord(y);
+DygraphOps.dispatchMouseUp_Point = function(g, x, y, custom) {
+ var pageX = Dygraph.findPosX(g.canvas_) + x;
+ var pageY = Dygraph.findPosY(g.canvas_) + y;
var opts = {
type : 'mouseup',
var event = DygraphOps.createEvent_(opts, custom);
g.canvas_.dispatchEvent(event);
};
+
+DygraphOps.dispatchMouseDown = function(g, x, y, custom) {
+ DygraphOps.dispatchMouseDown_Point(
+ g,
+ g.toDomXCoord(x),
+ g.toDomYCoord(y),
+ custom);
+};
+
+DygraphOps.dispatchMouseMove = function(g, x, y, custom) {
+ DygraphOps.dispatchMouseMove_Point(
+ g,
+ g.toDomXCoord(x),
+ g.toDomYCoord(y),
+ custom);
+};
+
+DygraphOps.dispatchMouseUp = function(g, x, y, custom) {
+ DygraphOps.dispatchMouseUp_Point(
+ g,
+ g.toDomXCoord(x),
+ g.toDomYCoord(y),
+ custom);
+};
+
--- /dev/null
+/**
+ * @fileoverview Test cases for the interaction model.
+ *
+ * @author konigsberg@google.com (Robert Konigsbrg)
+ */
+var InteractionModelTestCase = TestCase("interaction-model");
+
+InteractionModelTestCase.prototype.setUp = function() {
+ document.body.innerHTML = "<div id='graph'></div>";
+};
+
+InteractionModelTestCase.prototype.tearDown = function() {
+};
+
+function getXLabels() {
+ var x_labels = document.getElementsByClassName("dygraph-axis-label-x");
+ var ary = [];
+ for (var i = 0; i < x_labels.length; i++) {
+ ary.push(x_labels[i].innerHTML);
+ }
+ return ary;
+}
+
+InteractionModelTestCase.prototype.pan = function(g, xRange, yRange) {
+ var originalXRange = g.xAxisRange();
+ var originalYRange = g.yAxisRange(0);
+
+ DygraphOps.dispatchMouseDown(g, xRange[0], yRange[0]);
+ DygraphOps.dispatchMouseMove(g, xRange[1], yRange[0]); // this is really necessary.
+ DygraphOps.dispatchMouseUp(g, xRange[1], yRange[0]);
+
+ assertEqualsDelta(xRange, g.xAxisRange(), 0.2);
+ // assertEqualsDelta(originalYRange, g.yAxisRange(0), 0.2); // Not true, it's something in the middle.
+
+ var midX = (xRange[1] - xRange[0]) / 2;
+ DygraphOps.dispatchMouseDown(g, midX, yRange[0]);
+ DygraphOps.dispatchMouseMove(g, midX, yRange[1]); // this is really necessary.
+ DygraphOps.dispatchMouseUp(g, midX, yRange[1]);
+
+ assertEqualsDelta(xRange, g.xAxisRange(), 0.2);
+ assertEqualsDelta(yRange, g.yAxisRange(0), 0.2);
+}
+
+/**
+ * This tests that when changing the interaction model so pan is used instead
+ * of zoom as the default behavior, a standard click method is still called.
+ */
+InteractionModelTestCase.prototype.testClickCallbackIsCalled = function() {
+ var clicked;
+
+ var clickCallback = function(event, x) {
+ clicked = x;
+ };
+
+ var data = "X,Y\n" +
+ "20,-1\n" +
+ "21,0\n" +
+ "22,1\n" +
+ "23,0\n"
+ ;
+
+ var graph = document.getElementById("graph");
+ var g = new Dygraph(graph, data,
+ {
+ width: 100,
+ height : 100,
+ clickCallback : clickCallback
+ });
+
+ DygraphOps.dispatchMouseDown_Point(g, 10, 10);
+ DygraphOps.dispatchMouseMove_Point(g, 10, 10);
+ DygraphOps.dispatchMouseUp_Point(g, 10, 10);
+
+ assertEquals(20, clicked);
+};
+
+/**
+ * This tests that when changing the interaction model so pan is used instead
+ * of zoom as the default behavior, a standard click method is still called.
+ */
+InteractionModelTestCase.prototype.testClickCallbackIsCalledOnCustomPan = function() {
+ var clicked;
+
+ var clickCallback = function(event, x) {
+ clicked = x;
+ };
+
+ var data = "X,Y\n" +
+ "20,-1\n" +
+ "21,0\n" +
+ "22,1\n" +
+ "23,0\n"
+ ;
+
+ function customDown(event, g, context) {
+ context.initializeMouseDown(event, g, context);
+ Dygraph.startPan(event, g, context);
+ }
+
+ function customMove(event, g, context) {
+ Dygraph.movePan(event, g, context);
+ }
+
+ function customUp(event, g, context) {
+ Dygraph.endPan(event, g, context);
+ }
+
+ var opts = {
+ width: 100,
+ height : 100,
+ clickCallback : clickCallback,
+ interactionModel : {
+ 'mousedown' : customDown,
+ 'mousemove' : customMove,
+ 'mouseup' : customUp,
+ }
+ };
+
+ var graph = document.getElementById("graph");
+ var g = new Dygraph(graph, data, opts);
+
+ DygraphOps.dispatchMouseDown_Point(g, 10, 10);
+ DygraphOps.dispatchMouseMove_Point(g, 10, 10);
+ DygraphOps.dispatchMouseUp_Point(g, 10, 10);
+
+ assertEquals(20, clicked);
+};
+
var originalXRange = g.xAxisRange();
var originalYRange = g.yAxisRange(0);
- // Editing e.shiftKey post construction doesn't work for Firefox. Damn.
DygraphOps.dispatchMouseDown(g, xRange[0], yRange[0]);
DygraphOps.dispatchMouseMove(g, xRange[1], yRange[0]); // this is really necessary.
DygraphOps.dispatchMouseUp(g, xRange[1], yRange[0]);
context.valueRange = null;
context.boundedDates = null;
context.boundedValues = null;
+
+ var dragEndX = g.dragGetX_(event, context);
+ var dragEndY = g.dragGetY_(event, context);
+ var regionWidth = Math.abs(context.dragEndX - context.dragStartX);
+ var regionHeight = Math.abs(context.dragEndY - context.dragStartY);
+
+ if (regionWidth < 2 && regionHeight < 2 &&
+ g.lastx_ != undefined && g.lastx_ != -1) {
+ Dygraph.Interaction.treatMouseOpAsClick(g);
+ }
};
/**
context.prevDragDirection = context.dragDirection;
};
+Dygraph.Interaction.treatMouseOpAsClick = function(g) {
+ // TODO(danvk): pass along more info about the points, e.g. 'x'
+ if (g.attr_('clickCallback') != null) {
+ g.attr_('clickCallback')(event, g.lastx_, g.selPoints_);
+ }
+ if (g.attr_('pointClickCallback')) {
+ // check if the click was on a particular point.
+ var closestIdx = -1;
+ var closestDistance = 0;
+ for (var i = 0; i < g.selPoints_.length; i++) {
+ var p = g.selPoints_[i];
+ var distance = Math.pow(p.canvasx - context.dragEndX, 2) +
+ Math.pow(p.canvasy - context.dragEndY, 2);
+ if (closestIdx == -1 || distance < closestDistance) {
+ closestDistance = distance;
+ closestIdx = i;
+ }
+ }
+
+ // Allow any click within two pixels of the dot.
+ var radius = g.attr_('highlightCircleSize') + 2;
+ if (closestDistance <= 5 * 5) {
+ g.attr_('pointClickCallback')(event, g.selPoints_[closestIdx]);
+ }
+ }
+}
+
/**
* Called in response to an interaction model operation that
* responds to an event that performs a zoom based on previously defined
* dragStartX/dragStartY/etc. properties). This function modifies the context.
*/
Dygraph.Interaction.endZoom = function(event, g, context) {
- // TODO(konigsberg): Refactor or rename this fn -- it deals with clicks, too.
context.isZooming = false;
context.dragEndX = g.dragGetX_(event, context);
context.dragEndY = g.dragGetY_(event, context);
if (regionWidth < 2 && regionHeight < 2 &&
g.lastx_ != undefined && g.lastx_ != -1) {
- // TODO(danvk): pass along more info about the points, e.g. 'x'
- if (g.attr_('clickCallback') != null) {
- g.attr_('clickCallback')(event, g.lastx_, g.selPoints_);
- }
- if (g.attr_('pointClickCallback')) {
- // check if the click was on a particular point.
- var closestIdx = -1;
- var closestDistance = 0;
- for (var i = 0; i < g.selPoints_.length; i++) {
- var p = g.selPoints_[i];
- var distance = Math.pow(p.canvasx - context.dragEndX, 2) +
- Math.pow(p.canvasy - context.dragEndY, 2);
- if (closestIdx == -1 || distance < closestDistance) {
- closestDistance = distance;
- closestIdx = i;
- }
- }
-
- // Allow any click within two pixels of the dot.
- var radius = g.attr_('highlightCircleSize') + 2;
- if (closestDistance <= 5 * 5) {
- g.attr_('pointClickCallback')(event, g.selPoints_[closestIdx]);
- }
- }
+ Dygraph.Interaction.treatMouseOpAsClick(g);
}
if (regionWidth >= 10 && context.dragDirection == Dygraph.HORIZONTAL) {