Вопрос по javascript – Перемещение фиксированных узлов в D3

7

У меня есть узлы в форсированном макете D3, которые установлены на.fixed = правда. Если я установлю значения .x или .y, сами узлы не переместятся в свое новое положение.

Вот моя функция:

<code>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;
            }
        }
    }
}
</code>

UPDATE 1:

Вот рабочая функция, основанная на совете Джейсона:

<code>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();
}
</code>

Ваш Ответ

1   ответ
12

еринга. Обычно у вас есть обработчик тиков, который обновляет атрибуты ваших элементов SVG для каждого & quot; тика & quot; алгоритма компоновки (хорошая вещь в развязке - это рендеринг<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() всегда срабатывает событие галочки независимо от охлаждения, но это не текущее поведение).

Как вы правильно заметили в комментариях, если вы установили вручнуюd.x а такжеd.yВы также должны установитьd.px а такжеd.py с теми же значениями, если вы хотите, чтобы узел оставался в определенной позиции.

Спасибо, теперь я понял. Я только что проверил поведение и хотел указать на то, что может отбросить людей из примеров по умолчанию: вам нужно изменить значения px / py, а также значения x / y, если узел двигался. Я опубликую обновленную функцию выше. Elijah

Похожие вопросы