Динамическое добавление вершин в строку в файле Three.js

Я выяснил, как нарисовать строку в трехjs, проблема в том, что мне нужно динамически добавлять вершины в строку. Когда я добавляю вершины к строке динамически, сцена не обновляется.

Я пробовал geometry.verticesNeedUpdate = true, который, похоже, не работает.

Ответ 1

EDIT: с помощью BufferGeometry и drawcalls теперь вы можете реализовать эквивалентную функциональность. См. Динамическое рисование строки с помощью функции three.js.

three.js r.71


Динамическое добавление вершин в строку не поддерживается. Как указано в Wiki:

Вы можете обновлять содержимое буферов, вы не можете изменять размер буферов (это очень дорого, в основном эквивалентно созданию новой геометрии).

Вы можете эмулировать изменение размера путем предварительного выделения большего буфера, а затем сбрасывания/скрытия ненужных вершин.

three.js r.55

Ответ 2

Я столкнулся с этим пару дней назад тоже. Как сказал WestLangley, вы не можете делать истинную динамическую геометрию из коробки, но alteredq имеет пару стратегий для "подделки" и достижения желаемого эффекта при https://github.com/mrdoob/three.js/issues/342.

Что касается вашего комментария к последнему ответу, не, просто удалите и снова добавьте новую строку из сцены в каждый кадр - вы, скорее всего, понесете огромный успех, Вы должны использовать либо первую, либо вторую из обходных стратегий alteredq.

В моем приложении я использовал вариант 1 следующим образом:

  • Создайте объект THREE.Geometry заранее и инициализируйте его с таким количеством вершин, которое вам кажется нужным (или иным образом достаточно большим числом вершин). (Вам также нужно будет скрыть их, прежде чем вы хотите их отобразить, - я установил их позиции на экране.)

  • Создайте объект THREE.Line с этой геометрией и добавьте в сцену.

  • Теперь, когда вы хотите добавить новую точку в строку, вам нужно будет индексировать вершины объектов геометрии, найти последний неиспользованный и обновить ее - изменить координаты на реальные, и установите geometry.verticesNeedUpdate = true; (иначе он ничего не изменит). (См. Как делать обновления в вики.)

Я все еще сглаживаю изломы на моем подходе, но это должно по крайней мере позволить вам рисовать линию на экране.

three.js r55

Ответ 3

Как говорит WestLangley, вы не можете этого сделать. Вот, по общему признанию, хакерское решение, которое я решил использовать:

  • Выделите больше вершин, чем мне нужно, заполнив geometry.vertices с начальной точкой моей строки
  • По мере того, как появляются новые точки, которые я хочу добавить, сдвиньте содержимое массива влево и напишите новую точку в последней записи массива geometry.vertices

код: Чтобы создать новую строку:

function createNewLine(startingPoint){
    var geometry = new THREE.Geometry();
    for (i=0; i<MAX_LINE_POINTS; i++){
    geometry.vertices.push(startingPoint.clone());
    }
    myLine = new THREE.Line(geometry, lineMaterial);
    myLine.geometry.dynamic = true;
    scene.add(myLine);
    render();
}

Чтобы добавить точку в строку:

function addPoint(myPoint) {
    myLine.geometry.vertices.push(myLine.geometry.vertices.shift()); //shift the array
    myLine.geometry.vertices[maxLinePoints-1] = myPoint; //add the point to the end of the array
    myLine.geometry.verticesNeedUpdate = true;
    render();
}

То, что вы в итоге получаете, это Линия, у которой есть куча точек, сложенных друг на друга, а затем точки, которые вы на самом деле хотите отобразить. Я представил проблему в репозитории three.js git для более простого решения этой проблемы. https://github.com/mrdoob/three.js/issues/4716