[英]Moving fixed nodes in D3
我在D3強制定向布局中設置了節點。 fixed = true。 如果我設置.x或.y值,節點本身不會移動到新位置。
這是我的功能:
function fixNode(idArray, locationX, locationY) {
for ( x = 0; x < idArray.length; x++ ) {
for ( y = 0; y < nodes.length; y++ ) {
if (nodes[y].id == idArray[x]) {
nodes[y].fixed = true;
nodes[y].x = 50;
nodes[y].y = 50;
break;
}
}
}
}
更新1:
這是基於傑森建議的工作函數:
function fixNode(idArray, locationX, locationY) {
for ( x = 0; x < idArray.length; x++ ) {
for ( y = 0; y < nodes.length; y++ ) {
if (nodes[y].id == idArray[x]) {
nodes[y].fixed = true;
nodes[y].x = 50;
nodes[y].y = 50;
nodes[y].px = 50;
nodes[y].py = 50;
break;
}
}
}
tick();
}
力導向布局與實際渲染分離。 通常你有一個tick處理程序,它可以為布局算法的每個“tick”更新SVG元素的屬性(關於解耦的好處是你渲染到<canvas>
,或其他東西)。
因此,要回答您的問題,您只需直接調用此處理程序即可更新SVG元素的屬性。 例如,您的代碼可能如下所示:
var node = …; // append circle elements
var force = d3.layout.force()
.nodes(…)
.links(…)
.on("tick", tick)
.start();
function tick() {
// Update positions of circle elements.
node.attr("cx", function(d) { return d.x; })
.attr("cy", function(d) { return d.y; });
}
所以你可以隨時調用tick()
並更新元素位置。
您可能想要調用force.tick()
,但這可以用作force.start()
的同步替代方法:您可以重復調用它,每次調用都會執行布局算法的一個步驟。 但是,有一個內部alpha
變量用於控制內部使用的模擬退火,一旦布局“冷卻”,該變量將為0
並且對force.tick()
進一步調用將不起作用。 (不可否認,如果force.tick()
總是觸發一個tick事件而不管冷卻,那可能會很好,但這不是當前行為)。
正如您在注釋中正確指出的那樣,如果手動設置dx
和dy
,如果希望節點保持在某個位置,還應該將d.px
和d.py
設置為相同的值。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.