 
   zoom: (value) ->
     super(value)
-    if @force.alpha() < @force.alphaMin()
-      @onTick()
-
+    @redraw()
 
 
   # Canvas Mouse Events
   # -------------------
 
+  # Canvas Drag Events
+  onCanvasDragStart: =>
+    if @node_hovered
+      @force
+        .alphaTarget 0.1
+        .restart()
+    unless @node_hovered
+      @canvas.style 'cursor', 'move'
+
+  onCanvasDragged: =>
+    if @node_hovered
+      @node_hovered.fx = (d3.event.x - @viewport.center.x - @viewport.translate.x) / @viewport.scale
+      @node_hovered.fy = (d3.event.y - @viewport.center.y - @viewport.translate.y) / @viewport.scale
+      @redraw()
+    else
+      @viewport.x  += d3.event.dx
+      @viewport.y  += d3.event.dy
+      @viewport.dx += d3.event.dx
+      @viewport.dy += d3.event.dy
+      @rescale()
+
+  onCanvasDragEnd: =>
+    if @node_hovered
+      @force.alphaTarget 0
+    else
+      @canvas.style 'cursor','default'
+      #@force.alphaTarget(0)
+      # Skip if viewport has no translation
+      if @viewport.dx == 0 and @viewport.dy == 0
+        Backbone.trigger 'visualization.node.hideInfo'
+        return
+      # TODO! Add viewportMove action to history
+      @viewport.dx = @viewport.dy = 0;
+
+  # Canvas Mouse Events
   onCanvasEnter: =>
     @onCanvasMove()
 

  rescale: ->
    @viewport.translate.x = @viewport.origin.x + @viewport.x - @viewport.offsetx - @viewport.offsetnode.x
    @viewport.translate.y = @viewport.origin.y + @viewport.y - @viewport.offsety - @viewport.offsetnode.y
    if @force.alpha() < @force.alphaMin()
      @onTick()

  rescaleTransition: ->
    # implement transition here


  # Drawing methods
  # -------------------

  redraw: ->
    if @force.alpha() < @force.alphaMin()
      @onTick()

  # Tick Function
  onTick: =>
