[TASK] Add animation & improve behaviour of forcegraph
This commit is contained in:
		
							parent
							
								
									0987b4b39a
								
							
						
					
					
						commit
						3e63b6432e
					
				| @ -1,5 +1,5 @@ | ||||
| define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'utils/math', 'forcegraph/draw'], | ||||
|   function (d3Selection, d3Force, d3Zoom, d3Drag, math, draw) { | ||||
| define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'd3-timer', 'd3-ease', 'd3-interpolate', 'utils/math', 'forcegraph/draw'], | ||||
|   function (d3Selection, d3Force, d3Zoom, d3Drag, d3Timer, d3Ease, d3Interpolate, math, draw) { | ||||
|     'use strict'; | ||||
| 
 | ||||
|     return function (config, linkScale, sidebar, router) { | ||||
| @ -14,10 +14,12 @@ define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'utils/math', 'forcegr | ||||
|       var intNodes = []; | ||||
|       var dictNodes = {}; | ||||
|       var intLinks = []; | ||||
|       var movetoTimer; | ||||
| 
 | ||||
|       var NODE_RADIUS_DRAG = 10; | ||||
|       var NODE_RADIUS_SELECT = 15; | ||||
|       var LINK_RADIUS_SELECT = 12; | ||||
|       var ZOOM_ANIMATE_DURATION = 350; | ||||
| 
 | ||||
|       var ZOOM_MIN = 1 / 8; | ||||
|       var ZOOM_MAX = 3; | ||||
| @ -32,9 +34,43 @@ define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'utils/math', 'forcegr | ||||
|         draw.setMaxArea(canvas.width, canvas.height); | ||||
|       } | ||||
| 
 | ||||
|       function moveTo(x, y) { | ||||
|         transform.x = (canvas.width + sidebar()) / 2 - x * transform.k; | ||||
|         transform.y = canvas.height / 2 - y * transform.k; | ||||
|       function transformPosition(p) { | ||||
|         transform.x = p.x; | ||||
|         transform.y = p.y; | ||||
|         transform.k = p.k; | ||||
|       } | ||||
| 
 | ||||
|       function moveTo(callback, forceMove) { | ||||
|         clearTimeout(movetoTimer); | ||||
|         if (!forceMove && force.alpha() > 0.3) { | ||||
|           movetoTimer = setTimeout(function timerOfMoveTo() { | ||||
|             moveTo(callback); | ||||
|           }, 300); | ||||
|           return; | ||||
|         } | ||||
|         var result = callback(); | ||||
|         var x = result[0]; | ||||
|         var y = result[1]; | ||||
|         var k = result[2]; | ||||
|         var end = { k: k }; | ||||
| 
 | ||||
|         end.x = (canvas.width + sidebar()) / 2 - x * k; | ||||
|         end.y = canvas.height / 2 - y * k; | ||||
| 
 | ||||
|         var start = { x: transform.x, y: transform.y, k: transform.k }; | ||||
| 
 | ||||
|         var interpolate = d3Interpolate.interpolateObject(start, end); | ||||
| 
 | ||||
|         var timer = d3Timer.timer(function (t) { | ||||
|           if (t >= ZOOM_ANIMATE_DURATION) { | ||||
|             timer.stop(); | ||||
|             return; | ||||
|           } | ||||
| 
 | ||||
|           var v = interpolate(d3Ease.easeQuadInOut(t / ZOOM_ANIMATE_DURATION)); | ||||
|           transformPosition(v); | ||||
|           window.requestAnimationFrame(redraw); | ||||
|         }); | ||||
|       } | ||||
| 
 | ||||
|       function onClick() { | ||||
| @ -111,7 +147,8 @@ define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'utils/math', 'forcegr | ||||
|         .force('x', d3Force.forceX().strength(0.02)) | ||||
|         .force('y', d3Force.forceY().strength(0.02)) | ||||
|         .force('collide', d3Force.forceCollide()) | ||||
|         .on('tick', redraw); | ||||
|         .on('tick', redraw) | ||||
|         .alphaDecay(0.015); | ||||
| 
 | ||||
|       var drag = d3Drag.drag() | ||||
|         .subject(function () { | ||||
| @ -192,40 +229,40 @@ define(['d3-selection', 'd3-force', 'd3-zoom', 'd3-drag', 'utils/math', 'forcegr | ||||
|       }; | ||||
| 
 | ||||
|       self.resetView = function resetView() { | ||||
|         draw.setHighlight(null); | ||||
|         transform.k = (ZOOM_MIN + 1) / 2; | ||||
|         moveTo(0, 0); | ||||
|         redraw(); | ||||
|         moveTo(function calcToReset() { | ||||
|           draw.setHighlight(null); | ||||
|           return [0, 0, (ZOOM_MIN + 1) / 2]; | ||||
|         }, true); | ||||
|       }; | ||||
| 
 | ||||
|       self.gotoNode = function gotoNode(d) { | ||||
|         for (var i = 0; i < intNodes.length; i++) { | ||||
|           var n = intNodes[i]; | ||||
|           if (n.o.node.nodeinfo.node_id !== d.nodeinfo.node_id) { | ||||
|             continue; | ||||
|         moveTo(function calcToNode() { | ||||
|           for (var i = 0; i < intNodes.length; i++) { | ||||
|             var n = intNodes[i]; | ||||
|             if (n.o.node.nodeinfo.node_id !== d.nodeinfo.node_id) { | ||||
|               continue; | ||||
|             } | ||||
|             draw.setHighlight({ type: 'node', o: n.o.node }); | ||||
|             return [n.x, n.y, (ZOOM_MAX + 1) / 2]; | ||||
|           } | ||||
|           draw.setHighlight({ type: 'node', o: n.o.node }); | ||||
|           transform.k = (ZOOM_MAX + 1) / 2; | ||||
|           moveTo(n.x, n.y); | ||||
|           break; | ||||
|         } | ||||
|         redraw(); | ||||
|           return [0, 0, (ZOOM_MIN + 1) / 2]; | ||||
|         }); | ||||
|       }; | ||||
| 
 | ||||
|       self.gotoLink = function gotoLink(d) { | ||||
|         draw.setHighlight({ type: 'link', o: d }); | ||||
|         for (var i = 0; i < intLinks.length; i++) { | ||||
|           var l = intLinks[i]; | ||||
|           if (l.o !== d) { | ||||
|             continue; | ||||
|         moveTo(function calcToLink() { | ||||
|           draw.setHighlight({ type: 'link', o: d }); | ||||
|           for (var i = 0; i < intLinks.length; i++) { | ||||
|             var l = intLinks[i]; | ||||
|             if (l.o !== d) { | ||||
|               continue; | ||||
|             } | ||||
|             return [(l.source.x + l.target.x) / 2, (l.source.y + l.target.y) / 2, (ZOOM_MAX / 2) + ZOOM_MIN]; | ||||
|           } | ||||
|           moveTo((l.source.x + l.target.x) / 2, (l.source.y + l.target.y) / 2); | ||||
|           break; | ||||
|         } | ||||
|         redraw(); | ||||
|           return [0, 0, (ZOOM_MIN + 1) / 2]; | ||||
|         }); | ||||
|       }; | ||||
| 
 | ||||
| 
 | ||||
|       self.gotoLocation = function gotoLocation() { | ||||
|         // ignore
 | ||||
|       }; | ||||
|  | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user