radial sugiyama positioning integration
This commit is contained in:
@@ -76,6 +76,9 @@ export class Renderer {
|
||||
private selectedProgram: WebGLProgram;
|
||||
private neighborProgram: WebGLProgram;
|
||||
private vao: WebGLVertexArrayObject;
|
||||
private nodeVbo: WebGLBuffer;
|
||||
private lineVao: WebGLVertexArrayObject;
|
||||
private lineVbo: WebGLBuffer;
|
||||
|
||||
// Data
|
||||
private leaves: Leaf[] = [];
|
||||
@@ -88,6 +91,8 @@ export class Renderer {
|
||||
private leafEdgeStarts: Uint32Array = new Uint32Array(0);
|
||||
private leafEdgeCounts: Uint32Array = new Uint32Array(0);
|
||||
private maxPtSize = 256;
|
||||
private useRawLineSegments = false;
|
||||
private rawLineVertexCount = 0;
|
||||
|
||||
// Multi-draw extension
|
||||
private multiDrawExt: any = null;
|
||||
@@ -163,15 +168,23 @@ export class Renderer {
|
||||
|
||||
// Create VAO + VBO (empty for now)
|
||||
this.vao = gl.createVertexArray()!;
|
||||
this.nodeVbo = gl.createBuffer()!;
|
||||
gl.bindVertexArray(this.vao);
|
||||
const vbo = gl.createBuffer()!;
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, vbo);
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.nodeVbo);
|
||||
|
||||
// We forced a_pos to location 0 in compileProgram
|
||||
gl.enableVertexAttribArray(0);
|
||||
gl.vertexAttribPointer(0, 2, gl.FLOAT, false, 0, 0);
|
||||
gl.bindVertexArray(null);
|
||||
|
||||
this.lineVao = gl.createVertexArray()!;
|
||||
this.lineVbo = gl.createBuffer()!;
|
||||
gl.bindVertexArray(this.lineVao);
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.lineVbo);
|
||||
gl.enableVertexAttribArray(0);
|
||||
gl.vertexAttribPointer(0, 2, gl.FLOAT, false, 0, 0);
|
||||
gl.bindVertexArray(null);
|
||||
|
||||
this.linesIbo = gl.createBuffer()!;
|
||||
this.selectionIbo = gl.createBuffer()!;
|
||||
this.neighborIbo = gl.createBuffer()!;
|
||||
@@ -192,7 +205,8 @@ export class Renderer {
|
||||
xs: Float32Array,
|
||||
ys: Float32Array,
|
||||
vertexIds: Uint32Array,
|
||||
edges: Uint32Array
|
||||
edges: Uint32Array,
|
||||
routeLineVertices: Float32Array | null = null
|
||||
): number {
|
||||
const t0 = performance.now();
|
||||
const gl = this.gl;
|
||||
@@ -213,6 +227,7 @@ export class Renderer {
|
||||
|
||||
// Upload sorted particles to GPU as STATIC VBO (never changes)
|
||||
gl.bindVertexArray(this.vao);
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.nodeVbo);
|
||||
gl.bufferData(gl.ARRAY_BUFFER, sorted, gl.STATIC_DRAW);
|
||||
gl.bindVertexArray(null);
|
||||
|
||||
@@ -236,6 +251,19 @@ export class Renderer {
|
||||
}
|
||||
this.vertexIdToSortedIndex = vertexIdToSortedIndex;
|
||||
|
||||
this.useRawLineSegments = routeLineVertices !== null && routeLineVertices.length > 0;
|
||||
this.rawLineVertexCount = this.useRawLineSegments && routeLineVertices ? routeLineVertices.length / 2 : 0;
|
||||
if (this.useRawLineSegments && routeLineVertices) {
|
||||
this.edgeCount = edgeCount;
|
||||
this.leafEdgeStarts = new Uint32Array(0);
|
||||
this.leafEdgeCounts = new Uint32Array(0);
|
||||
gl.bindVertexArray(this.lineVao);
|
||||
gl.bindBuffer(gl.ARRAY_BUFFER, this.lineVbo);
|
||||
gl.bufferData(gl.ARRAY_BUFFER, routeLineVertices, gl.STATIC_DRAW);
|
||||
gl.bindVertexArray(null);
|
||||
return performance.now() - t0;
|
||||
}
|
||||
|
||||
// Remap edges from vertex IDs to sorted indices
|
||||
const lineIndices = new Uint32Array(edgeCount * 2);
|
||||
let validEdges = 0;
|
||||
@@ -572,24 +600,30 @@ export class Renderer {
|
||||
}
|
||||
|
||||
// 5. Draw Lines if deeply zoomed in (< 20k total visible particles)
|
||||
if (totalVisibleParticles < 20000 && visibleCount > 0) {
|
||||
if (totalVisibleParticles < 20000) {
|
||||
gl.useProgram(this.lineProgram);
|
||||
gl.uniform2f(this.uCenterLine, this.cx, this.cy);
|
||||
gl.uniform2f(this.uScaleLine, (this.zoom * 2) / cw, (-this.zoom * 2) / ch);
|
||||
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, this.linesIbo);
|
||||
if (this.useRawLineSegments) {
|
||||
gl.bindVertexArray(this.lineVao);
|
||||
gl.drawArrays(gl.LINES, 0, this.rawLineVertexCount);
|
||||
gl.bindVertexArray(this.vao);
|
||||
} else if (visibleCount > 0) {
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, this.linesIbo);
|
||||
|
||||
for (let i = 0; i < visibleCount; i++) {
|
||||
const leafIdx = this.visibleLeafIndices[i];
|
||||
const edgeCount = this.leafEdgeCounts[leafIdx];
|
||||
if (edgeCount === 0) continue;
|
||||
// Each edge is 2 indices (1 line segment)
|
||||
// Offset is in bytes: edgeStart * 2 (indices per edge) * 4 (bytes per uint32)
|
||||
const edgeStart = this.leafEdgeStarts[leafIdx];
|
||||
gl.drawElements(gl.LINES, edgeCount * 2, gl.UNSIGNED_INT, edgeStart * 2 * 4);
|
||||
for (let i = 0; i < visibleCount; i++) {
|
||||
const leafIdx = this.visibleLeafIndices[i];
|
||||
const edgeCount = this.leafEdgeCounts[leafIdx];
|
||||
if (edgeCount === 0) continue;
|
||||
// Each edge is 2 indices (1 line segment)
|
||||
// Offset is in bytes: edgeStart * 2 (indices per edge) * 4 (bytes per uint32)
|
||||
const edgeStart = this.leafEdgeStarts[leafIdx];
|
||||
gl.drawElements(gl.LINES, edgeCount * 2, gl.UNSIGNED_INT, edgeStart * 2 * 4);
|
||||
}
|
||||
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, null);
|
||||
}
|
||||
|
||||
gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, null);
|
||||
}
|
||||
|
||||
// 6. Draw Neighbor Nodes (yellow) - drawn before selected so selected appears on top
|
||||
|
||||
Reference in New Issue
Block a user