playcanvas
Version:
PlayCanvas WebGL game engine
91 lines (88 loc) • 3.44 kB
JavaScript
import { Mat4 } from '../../core/math/mat4.js';
import { PRIMITIVE_LINES } from '../../platform/graphics/constants.js';
import { Mesh } from '../mesh.js';
import { MeshInstance } from '../mesh-instance.js';
import { GraphNode } from '../graph-node.js';
var identityGraphNode = new GraphNode();
identityGraphNode.worldTransform = Mat4.IDENTITY;
identityGraphNode._dirtyWorld = identityGraphNode._dirtyNormal = false;
// helper class storing data for a single batch of line rendering using a single material
class ImmediateBatch {
// add line positions and colors to the batch
// this function expects position in Vec3 and colors in Color format
addLines(positions, color) {
// positions
var destPos = this.positions;
var count = positions.length;
for(var i = 0; i < count; i++){
var pos = positions[i];
destPos.push(pos.x, pos.y, pos.z);
}
// colors
var destCol = this.colors;
if (color.length) {
// multi colored line
for(var i1 = 0; i1 < count; i1++){
var col = color[i1];
destCol.push(col.r, col.g, col.b, col.a);
}
} else {
// single colored line
for(var i2 = 0; i2 < count; i2++){
destCol.push(color.r, color.g, color.b, color.a);
}
}
}
// add line positions and colors to the batch
// this function expects positions as arrays of numbers
// and color as instance of Color or array of number specifying the same number of vertices as positions
addLinesArrays(positions, color) {
// positions
var destPos = this.positions;
for(var i = 0; i < positions.length; i += 3){
destPos.push(positions[i], positions[i + 1], positions[i + 2]);
}
// colors
var destCol = this.colors;
if (color.length) {
for(var i1 = 0; i1 < color.length; i1 += 4){
destCol.push(color[i1], color[i1 + 1], color[i1 + 2], color[i1 + 3]);
}
} else {
// single colored line
var count = positions.length / 3;
for(var i2 = 0; i2 < count; i2++){
destCol.push(color.r, color.g, color.b, color.a);
}
}
}
onPreRender(visibleList, transparent) {
// prepare mesh if its transparency matches
if (this.positions.length > 0 && this.material.transparent === transparent) {
// update mesh vertices
this.mesh.setPositions(this.positions);
this.mesh.setColors(this.colors);
this.mesh.update(PRIMITIVE_LINES, false);
if (!this.meshInstance) {
this.meshInstance = new MeshInstance(this.mesh, this.material, identityGraphNode);
}
// inject mesh instance into visible list to be rendered
visibleList.push(this.meshInstance);
}
}
clear() {
// clear lines after they are rendered as their lifetime is one frame
this.positions.length = 0;
this.colors.length = 0;
}
constructor(device, material, layer){
this.material = material;
this.layer = layer;
// line data, arrays of numbers
this.positions = [];
this.colors = [];
this.mesh = new Mesh(device);
this.meshInstance = null;
}
}
export { ImmediateBatch };