[英]How to make d3 concurrent transitions work?
I've started doing this as a side project to learn D3. 我已经开始这样做作为学习D3的侧面项目。 So please go easy on me;
所以请放轻松我;
Goal: Making an interactive airports map. 目标:制作互动机场地图。 When mouse is over a city planes will take off from that city's airport and land on to the destination.
当鼠标飞过城市时,飞机将从该城市的机场起飞并降落到目的地。
Steps I've followed; 我遵循的步骤;
Problem: When I have more than one plane to take from a city it's just not moving. 问题:当我从一个城市乘坐多架飞机时,它就不会移动。 Instead it stays on the same position until the transition ends.
相反,它会一直保持在同一位置,直到转换结束。 I can't add concurrent transitions to the objects.
我无法向对象添加并发转换。
My transition function is like; 我的过渡功能就像;
function myTransition(destPoi, originPoi) {
var tr_bl = true;
pathData = []; t_dest_poi = [];
if (tr_bl) {
//Origin destination coordinates taken from the Origin Poi
originPoint[0] = originPoi[1];
originPoint[1] = originPoi[2];
originPoint = geoMercator(originPoint);//Need transformation before using on screen.
var lineGenerator = d3.line().curve(d3.curveCatmullRom);
// Destination coordinate pairs transformed to screen coordinates
// and assigned to an array
for (i = 0; i < destPoi.length; i++) {
t_dest_poi[i] = geoMercator(destPoi[i]);
}
//appending new group g2 with id fp
var g2 = map_svg.append("g").attr("id", "fp");
// Creating the planes and flight paths programmatically.*************************************
for (i = 0; i < destPoi.length; i++) {
var plane = map_svg.append("path")
.attr("class", "plane")
.attr("d", "m25.21488,3.93375c-0.44355,0 -0.84275,0.18332 -1.17933,0.51592c-0.33397,0.33267 -0.61055,0.80884 -0.84275,1.40377c-0.45922,1.18911 -0.74362,2.85964 -0.89755,4.86085c-0.15655,1.99729 -0.18263,4.32223 -0.11741,6.81118c-5.51835,2.26427 -16.7116,6.93857 -17.60916,7.98223c-1.19759,1.38937 -0.81143,2.98095 -0.32874,4.03902l18.39971,-3.74549c0.38616,4.88048 0.94192,9.7138 1.42461,13.50099c-1.80032,0.52703 -5.1609,1.56679 -5.85232,2.21255c-0.95496,0.88711 -0.95496,3.75718 -0.95496,3.75718l7.53,-0.61316c0.17743,1.23545 0.28701,1.95767 0.28701,1.95767l0.01304,0.06557l0.06002,0l0.13829,0l0.0574,0l0.01043,-0.06557c0,0 0.11218,-0.72222 0.28961,-1.95767l7.53164,0.61316c0,0 0,-2.87006 -0.95496,-3.75718c-0.69044,-0.64577 -4.05363,-1.68813 -5.85133,-2.21516c0.48009,-3.77545 1.03061,-8.58921 1.42198,-13.45404l18.18207,3.70115c0.48009,-1.05806 0.86881,-2.64965 -0.32617,-4.03902c-0.88969,-1.03062 -11.81147,-5.60054 -17.39409,-7.89352c0.06524,-2.52287 0.04175,-4.88024 -0.1148,-6.89989l0,-0.00476c-0.15655,-1.99844 -0.44094,-3.6683 -0.90277,-4.8561c-0.22699,-0.59493 -0.50356,-1.07111 -0.83754,-1.40377c-0.33658,-0.3326 -0.73578,-0.51592 -1.18194,-0.51592l0,0l-0.00001,0l0,0z")
.style("opacity", 1)
.style("fill", "transparent");
//creating flight path data with line generator
pathData[i] = lineGenerator([originPoint, t_dest_poi[i]]);
//appending created flight path to variable
var path = g2.append("path").data([
[originPoint],
[t_dest_poi[i]]
]).attr("d", d3.line());
//flight path
g2.selectAll('path')
.data([
[originPoint],
[t_dest_poi[i]]
])
.attr('d', pathData)
.attr("stroke", "blue")
.attr("fill", "transparent");
plane.style("fill", "grey");
var route = g2.append("path")
.datum({
type: "LineString", coordinates: [
[originPoint],
[t_dest_poi[i]]]
})
.attr("class", "route")
.attr("d", geoPath)
.attr("stroke", "blue")
.attr("fill", "transparent");
// adding transition to plane
plane.transition()
.duration(5000)
.attrTween("transform", translateAlong([originPoint, t_dest_poi[i]], path.node()))
.remove();
}
}
else {
}}
function translateAlong(co, path) {
var l = path.getTotalLength();
return function (d, i, a) {
return function (t) {
var p = path.getPointAtLength(t * l);
[a1, b1] = co[0];
[a2, b2] = co[1];
aci = Math.atan((b2 - b1) / (a2 - a1));
aci = aci * 180 / Math.PI;
if (a2 > a1) {
aci = aci + 90;
} else {
aci = aci - 90;
}
return "translate(" + (p.x) + "," + (p.y) + ") scale(" + Math.sin(Math.PI * t) + ") rotate(" + aci + ")";
};
};
}
This seems like an issue with updating the path of the #fp element during the transition. 这似乎是在转换期间更新#fp元素的路径的问题。 The relatively easy fix in this case is to handle the transitions separately.
在这种情况下相对容易的修复是分别处理过渡。
In your code, in basemap.js circa line 58-63, you call myTransition() on an array of multiple elements after populating the array in a for loop. 在你的代码中,在第58-63行的basemap.js中,在for循环中填充数组之后,在多个元素的数组上调用myTransition()。
for (i = 0; i <= n - 1; i++) {
fp[i] = [destAirportObjects[i][1], destAirportObjects[i][2]];
}
myTransition(fp, OriginAirport);
Call the function from within the for loop instead and your transition works fine: 从for循环中调用该函数,您的过渡工作正常:
for (i = 0; i <= n - 1; i++) {
fp[i] = [destAirportObjects[i][1], destAirportObjects[i][2]];
myTransition([fp[i]], OriginAirport);
}
If you choose this solution, you should update myTransition() to take a single set of coordinates to make the code easier to understand. 如果选择此解决方案,则应更新myTransition()以获取一组坐标以使代码更易于理解。
Alternatively , don't make any changes to the basemap.js file, but update myTransition so that the creation of the group (var g2) is completed within the destination for loop. 或者 ,不要对basemap.js文件进行任何更改,而是更新myTransition,以便在目标for循环内完成组(var g2)的创建。 Here's what you currently have in move.js starting at line 21:
以下是您目前在第21行开始的move.js中所拥有的内容:
var g2 = map_svg.append("g").attr("id", "fp");
// Creating the planes and flight paths programmatically.*************************************
for (i = 0; i < destPoi.length; i++) {
//creating flight path data with line generator
pathData[i] = lineGenerator([originPoint, t_dest_poi[i]]);
//continue with loop
This is causing the g2 variable to be overwritten each time we move through the loop. 这导致每次我们在循环中移动时都会覆盖g2变量。 There needs to be a distinct group created for each transition/path.
需要为每个转换/路径创建一个不同的组。
// Creating the planes and flight paths programmatically.*************************************
for (i = 0; i < destPoi.length; i++) {
var g2 = map_svg.append("g").attr("class", "fp");
//creating flight path data with line generator
pathData[i] = lineGenerator([originPoint, t_dest_poi[i]]);
//continue with loop
Finally, since there are multiple elements in this case, "fp" should be the class of var g2, not the ID. 最后,由于在这种情况下有多个元素,“fp”应该是var g2的类,而不是ID。 Remember to update your accessors accordingly.
请记住相应地更新您的访问者。
Edit: Here's the sample for method #1 and method #2 编辑:这是方法#1和方法#2的示例
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.