Reputation: 125
I'm trying to change the following code to use TextBufferGeometry instead of TextGeometry as I feel like it may improve the performance in my use case. The code below works for rendering multiple text elements into my scene however when I change..
let geometry = new THREE.TextGeometry(...
to let geometry = new THREE.TextBufferGeometry(...
this code no longer renders text into the scene. I'm unsure of what needs changing in order to make use of TextBufferGeometry
const materialWhite = new THREE.MeshBasicMaterial({ color: 0xffffff, side: THREE.DoubleSide });
const textArray = [
{ text: `Message 12345`, zDistance: 100 },
{ text: `Message 67890`, zDistance: 200 },
{ text: `Message 13579`, zDistance: 300 },
];
var singleFontGeometry = new THREE.Geometry();
for (let index = 0; index < textArray.length; index++) {
loaderFonts.load('./assets/fonts/Oxanium.json', function(font) {
let geometry = new THREE.TextGeometry(`${textArray[index].text}`, {
font: font,
size: 20,
height: 1
});
let mesh = new THREE.Mesh(geometry, materialWhite);
mesh.position.set(100, 100, textArray[index].zDistance);
singleFontGeometry.mergeMesh(mesh);
});
}
var meshFont = new THREE.Mesh(singleFontGeometry, materialWhite);
this.scene.add(meshFont);
Upvotes: 0
Views: 1429
Reputation: 11970
The code above will require three main changes:
THREE.TextBufferGeometry
instances instead of TextGeometry
.geometry.translate(...)
.THREE.Geometry
instance, create a merged BufferGeometry instance using BufferGeometryUtils. BufferGeometry does not have a .mergeMesh()
method, and .merge()
overwrites vertices rather than creating a union, so neither are available here.Also, but somewhat unrelated to the question, you probably don't want to load the font inside your For-loop, to avoid unnecessary requests. With these changes, the code should look something like this:
import * as THREE from 'three';
import { BufferGeometryUtils } from 'three/examples/jsm/utils/BufferGeometryUtils.js';
var mergedGeometry;
// Load the font once.
loaderFonts.load('./assets/fonts/Oxanium.json', function(font) {
// Then create a *BufferGeometry for each item of text.
var geometries = textArray.map(function(text) {
var geometry = new THREE.TextBufferGeometry(text.text, {
font: font,
size: 20,
height: 1
});
// Take each item's unique Z offset, and bake it into the geometry.
geometry.translate(0, 0, text.zDistance);
return geometry;
});
// Merge all text geometries.
mergedGeometry = BufferGeometryUtils.mergeBufferGeometries( geometries );
var mesh = new THREE.Mesh(mergedGeometry, materialWhite);
// Put the shared x=100,y=100 offset onto the mesh, so it can be changed later.
mesh.position.set(100, 100, 0);
scene.add(mesh);
});
^Note that BufferGeometryUtils is not included in the three.js build itself, and must be added to your application separately, like loaders, controls, and other things in the examples/js*
folder.
Upvotes: 1