Browse Source

avoid namespace lookups for better performance

- in performance critical code
Alexander Rose 4 years ago
parent
commit
f7ccff61e0

+ 14 - 9
src/mol-geo/geometry/lines/lines-builder.ts

@@ -21,6 +21,11 @@ const tmpVecA = Vec3();
 const tmpVecB = Vec3();
 const tmpDir = Vec3();
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const caAdd = ChunkedArray.add;
+const caAdd2 = ChunkedArray.add2;
+const caAdd3 = ChunkedArray.add3;
+
 export namespace LinesBuilder {
     export function create(initialCount = 2048, chunkSize = 1024, lines?: Lines): LinesBuilder {
         const mappings = ChunkedArray.create(Float32Array, 2, chunkSize, lines ? lines.mappingBuffer.ref.value : initialCount);
@@ -32,16 +37,16 @@ export namespace LinesBuilder {
         const add = (startX: number, startY: number, startZ: number, endX: number, endY: number, endZ: number, group: number) => {
             const offset = mappings.elementCount;
             for (let i = 0; i < 4; ++i) {
-                ChunkedArray.add3(starts, startX, startY, startZ);
-                ChunkedArray.add3(ends, endX, endY, endZ);
-                ChunkedArray.add(groups, group);
+                caAdd3(starts, startX, startY, startZ);
+                caAdd3(ends, endX, endY, endZ);
+                caAdd(groups, group);
             }
-            ChunkedArray.add2(mappings, -1, 1);
-            ChunkedArray.add2(mappings, -1, -1);
-            ChunkedArray.add2(mappings, 1, 1);
-            ChunkedArray.add2(mappings, 1, -1);
-            ChunkedArray.add3(indices, offset, offset + 1, offset + 2);
-            ChunkedArray.add3(indices, offset + 1, offset + 3, offset + 2);
+            caAdd2(mappings, -1, 1);
+            caAdd2(mappings, -1, -1);
+            caAdd2(mappings, 1, 1);
+            caAdd2(mappings, 1, -1);
+            caAdd3(indices, offset, offset + 1, offset + 2);
+            caAdd3(indices, offset + 1, offset + 3, offset + 2);
         };
 
         const addFixedCountDashes = (start: Vec3, end: Vec3, segmentCount: number, group: number) => {

+ 109 - 97
src/mol-geo/geometry/mesh/builder/sheet.ts

@@ -1,5 +1,5 @@
 /**
- * Copyright (c) 2018-2019 mol* contributors, licensed under MIT, See LICENSE file for more info.
+ * Copyright (c) 2018-2020 mol* contributors, licensed under MIT, See LICENSE file for more info.
  *
  * @author Alexander Rose <alexander.rose@weirdbyte.de>
  * @author David Sehnal <david.sehnal@gmail.com>
@@ -9,65 +9,77 @@ import { Vec3 } from '../../../../mol-math/linear-algebra';
 import { ChunkedArray } from '../../../../mol-data/util';
 import { MeshBuilder } from '../mesh-builder';
 
-const tA = Vec3.zero();
-const tB = Vec3.zero();
-const tV = Vec3.zero();
-
-const horizontalVector = Vec3.zero();
-const verticalVector = Vec3.zero();
-const verticalRightVector = Vec3.zero();
-const verticalLeftVector = Vec3.zero();
-const normalOffset = Vec3.zero();
-const positionVector = Vec3.zero();
-const normalVector = Vec3.zero();
-const torsionVector = Vec3.zero();
-
-const p1 = Vec3.zero();
-const p2 = Vec3.zero();
-const p3 = Vec3.zero();
-const p4 = Vec3.zero();
+const tA = Vec3();
+const tB = Vec3();
+const tV = Vec3();
+
+const horizontalVector = Vec3();
+const verticalVector = Vec3();
+const verticalRightVector = Vec3();
+const verticalLeftVector = Vec3();
+const normalOffset = Vec3();
+const positionVector = Vec3();
+const normalVector = Vec3();
+const torsionVector = Vec3();
+
+const p1 = Vec3();
+const p2 = Vec3();
+const p3 = Vec3();
+const p4 = Vec3();
+
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const v3fromArray = Vec3.fromArray;
+const v3scale = Vec3.scale;
+const v3add = Vec3.add;
+const v3sub = Vec3.sub;
+const v3magnitude = Vec3.magnitude;
+const v3negate = Vec3.negate;
+const v3copy = Vec3.copy;
+const v3cross = Vec3.cross;
+const caAdd3 = ChunkedArray.add3;
+const caAdd = ChunkedArray.add;
 
 function addCap(offset: number, state: MeshBuilder.State, controlPoints: ArrayLike<number>, normalVectors: ArrayLike<number>, binormalVectors: ArrayLike<number>, width: number, leftHeight: number, rightHeight: number) {
     const { vertices, normals, indices } = state;
     const vertexCount = vertices.elementCount;
 
-    Vec3.fromArray(verticalLeftVector, normalVectors, offset);
-    Vec3.scale(verticalLeftVector, verticalLeftVector, leftHeight);
+    v3fromArray(verticalLeftVector, normalVectors, offset);
+    v3scale(verticalLeftVector, verticalLeftVector, leftHeight);
 
-    Vec3.fromArray(verticalRightVector, normalVectors, offset);
-    Vec3.scale(verticalRightVector, verticalRightVector, rightHeight);
+    v3fromArray(verticalRightVector, normalVectors, offset);
+    v3scale(verticalRightVector, verticalRightVector, rightHeight);
 
-    Vec3.fromArray(horizontalVector, binormalVectors, offset);
-    Vec3.scale(horizontalVector, horizontalVector, width);
+    v3fromArray(horizontalVector, binormalVectors, offset);
+    v3scale(horizontalVector, horizontalVector, width);
 
-    Vec3.fromArray(positionVector, controlPoints, offset);
+    v3fromArray(positionVector, controlPoints, offset);
 
-    Vec3.add(p1, Vec3.add(p1, positionVector, horizontalVector), verticalRightVector);
-    Vec3.sub(p2, Vec3.add(p2, positionVector, horizontalVector), verticalLeftVector);
-    Vec3.sub(p3, Vec3.sub(p3, positionVector, horizontalVector), verticalLeftVector);
-    Vec3.add(p4, Vec3.sub(p4, positionVector, horizontalVector), verticalRightVector);
+    v3add(p1, v3add(p1, positionVector, horizontalVector), verticalRightVector);
+    v3sub(p2, v3add(p2, positionVector, horizontalVector), verticalLeftVector);
+    v3sub(p3, v3sub(p3, positionVector, horizontalVector), verticalLeftVector);
+    v3add(p4, v3sub(p4, positionVector, horizontalVector), verticalRightVector);
 
     if (leftHeight < rightHeight) {
-        ChunkedArray.add3(vertices, p4[0], p4[1], p4[2]);
-        ChunkedArray.add3(vertices, p3[0], p3[1], p3[2]);
-        ChunkedArray.add3(vertices, p2[0], p2[1], p2[2]);
-        ChunkedArray.add3(vertices, p1[0], p1[1], p1[2]);
-        Vec3.copy(verticalVector, verticalRightVector);
+        caAdd3(vertices, p4[0], p4[1], p4[2]);
+        caAdd3(vertices, p3[0], p3[1], p3[2]);
+        caAdd3(vertices, p2[0], p2[1], p2[2]);
+        caAdd3(vertices, p1[0], p1[1], p1[2]);
+        v3copy(verticalVector, verticalRightVector);
     } else {
-        ChunkedArray.add3(vertices, p1[0], p1[1], p1[2]);
-        ChunkedArray.add3(vertices, p2[0], p2[1], p2[2]);
-        ChunkedArray.add3(vertices, p3[0], p3[1], p3[2]);
-        ChunkedArray.add3(vertices, p4[0], p4[1], p4[2]);
-        Vec3.copy(verticalVector, verticalLeftVector);
+        caAdd3(vertices, p1[0], p1[1], p1[2]);
+        caAdd3(vertices, p2[0], p2[1], p2[2]);
+        caAdd3(vertices, p3[0], p3[1], p3[2]);
+        caAdd3(vertices, p4[0], p4[1], p4[2]);
+        v3copy(verticalVector, verticalLeftVector);
     }
 
-    Vec3.cross(normalVector, horizontalVector, verticalVector);
+    v3cross(normalVector, horizontalVector, verticalVector);
 
     for (let i = 0; i < 4; ++i) {
-        ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+        caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
     }
-    ChunkedArray.add3(indices, vertexCount + 2, vertexCount + 1, vertexCount);
-    ChunkedArray.add3(indices, vertexCount, vertexCount + 3, vertexCount + 2);
+    caAdd3(indices, vertexCount + 2, vertexCount + 1, vertexCount);
+    caAdd3(indices, vertexCount, vertexCount + 3, vertexCount + 2);
 }
 
 /** set arrowHeight = 0 for no arrow */
@@ -78,9 +90,9 @@ export function addSheet(state: MeshBuilder.State, controlPoints: ArrayLike<numb
     let offsetLength = 0;
 
     if (arrowHeight > 0) {
-        Vec3.fromArray(tA, controlPoints, 0);
-        Vec3.fromArray(tB, controlPoints, linearSegments * 3);
-        offsetLength = arrowHeight / Vec3.magnitude(Vec3.sub(tV, tB, tA));
+        v3fromArray(tA, controlPoints, 0);
+        v3fromArray(tB, controlPoints, linearSegments * 3);
+        offsetLength = arrowHeight / v3magnitude(v3sub(tV, tB, tA));
     }
 
     for (let i = 0; i <= linearSegments; ++i) {
@@ -90,70 +102,70 @@ export function addSheet(state: MeshBuilder.State, controlPoints: ArrayLike<numb
         const actualHeight = arrowHeight === 0 ? height : arrowHeight * (1 - i / linearSegments);
         const i3 = i * 3;
 
-        Vec3.fromArray(verticalVector, normalVectors, i3);
-        Vec3.scale(verticalVector, verticalVector, actualHeight);
+        v3fromArray(verticalVector, normalVectors, i3);
+        v3scale(verticalVector, verticalVector, actualHeight);
 
-        Vec3.fromArray(horizontalVector, binormalVectors, i3);
-        Vec3.scale(horizontalVector, horizontalVector, width);
+        v3fromArray(horizontalVector, binormalVectors, i3);
+        v3scale(horizontalVector, horizontalVector, width);
 
         if (arrowHeight > 0) {
-            Vec3.fromArray(tA, normalVectors, i3);
-            Vec3.fromArray(tB, binormalVectors, i3);
-            Vec3.scale(normalOffset, Vec3.cross(normalOffset, tA, tB), offsetLength);
+            v3fromArray(tA, normalVectors, i3);
+            v3fromArray(tB, binormalVectors, i3);
+            v3scale(normalOffset, v3cross(normalOffset, tA, tB), offsetLength);
         }
 
-        Vec3.fromArray(positionVector, controlPoints, i3);
-        Vec3.fromArray(normalVector, normalVectors, i3);
-        Vec3.fromArray(torsionVector, binormalVectors, i3);
-
-        Vec3.add(tA, Vec3.add(tA, positionVector, horizontalVector), verticalVector);
-        Vec3.copy(tB, normalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        Vec3.add(tA, Vec3.sub(tA, positionVector, horizontalVector), verticalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        // Vec3.add(tA, Vec3.sub(tA, positionVector, horizontalVector), verticalVector) // reuse tA
-        Vec3.add(tB, Vec3.negate(tB, torsionVector), normalOffset);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        Vec3.sub(tA, Vec3.sub(tA, positionVector, horizontalVector), verticalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        // Vec3.sub(tA, Vec3.sub(tA, positionVector, horizontalVector), verticalVector) // reuse tA
-        Vec3.negate(tB, normalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        Vec3.sub(tA, Vec3.add(tA, positionVector, horizontalVector), verticalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        // Vec3.sub(tA, Vec3.add(tA, positionVector, horizontalVector), verticalVector) // reuse tA
-        Vec3.add(tB, torsionVector, normalOffset);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
-
-        Vec3.add(tA, Vec3.add(tA, positionVector, horizontalVector), verticalVector);
-        ChunkedArray.add3(vertices, tA[0], tA[1], tA[2]);
-        ChunkedArray.add3(normals, tB[0], tB[1], tB[2]);
+        v3fromArray(positionVector, controlPoints, i3);
+        v3fromArray(normalVector, normalVectors, i3);
+        v3fromArray(torsionVector, binormalVectors, i3);
+
+        v3add(tA, v3add(tA, positionVector, horizontalVector), verticalVector);
+        v3copy(tB, normalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        v3add(tA, v3sub(tA, positionVector, horizontalVector), verticalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        // v3add(tA, v3sub(tA, positionVector, horizontalVector), verticalVector) // reuse tA
+        v3add(tB, v3negate(tB, torsionVector), normalOffset);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        v3sub(tA, v3sub(tA, positionVector, horizontalVector), verticalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        // v3sub(tA, v3sub(tA, positionVector, horizontalVector), verticalVector) // reuse tA
+        v3negate(tB, normalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        v3sub(tA, v3add(tA, positionVector, horizontalVector), verticalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        // v3sub(tA, v3add(tA, positionVector, horizontalVector), verticalVector) // reuse tA
+        v3add(tB, torsionVector, normalOffset);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
+
+        v3add(tA, v3add(tA, positionVector, horizontalVector), verticalVector);
+        caAdd3(vertices, tA[0], tA[1], tA[2]);
+        caAdd3(normals, tB[0], tB[1], tB[2]);
     }
 
     for (let i = 0; i < linearSegments; ++i) {
         // the triangles are arranged such that opposing triangles of the sheet align
         // which prevents triangle intersection within tight curves
         for (let j = 0; j < 2; j++) {
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + i * 8 + 2 * j, // a
                 vertexCount + (i + 1) * 8 + 2 * j + 1, // c
                 vertexCount + i * 8 + 2 * j + 1 // b
             );
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + i * 8 + 2 * j, // a
                 vertexCount + (i + 1) * 8 + 2 * j, // d
@@ -161,13 +173,13 @@ export function addSheet(state: MeshBuilder.State, controlPoints: ArrayLike<numb
             );
         }
         for (let j = 2; j < 4; j++) {
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + i * 8 + 2 * j, // a
                 vertexCount + (i + 1) * 8 + 2 * j, // d
                 vertexCount + i * 8 + 2 * j + 1, // b
             );
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + (i + 1) * 8 + 2 * j, // d
                 vertexCount + (i + 1) * 8 + 2 * j + 1, // c
@@ -198,5 +210,5 @@ export function addSheet(state: MeshBuilder.State, controlPoints: ArrayLike<numb
     const addedVertexCount = (linearSegments + 1) * 8 +
         (startCap ? 4 : (arrowHeight > 0 ? 8 : 0)) +
         (endCap && arrowHeight === 0 ? 4 : 0);
-    for (let i = 0, il = addedVertexCount; i < il; ++i) ChunkedArray.add(groups, currentGroup);
+    for (let i = 0, il = addedVertexCount; i < il; ++i) caAdd(groups, currentGroup);
 }

+ 35 - 26
src/mol-geo/geometry/mesh/builder/tube.ts

@@ -27,6 +27,13 @@ function add3AndScale2(out: Vec3, a: Vec3, b: Vec3, c: Vec3, sa: number, sb: num
     out[2] = (a[2] * sa) + (b[2] * sb) + c[2];
 }
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const v3fromArray = Vec3.fromArray;
+const v3normalize = Vec3.normalize;
+const v3negate = Vec3.negate;
+const v3copy = Vec3.copy;
+const v3cross = Vec3.cross;
+const caAdd3 = ChunkedArray.add3;
 
 const CosSinCache = new Map<number, { cos: number[], sin: number[] }>();
 function getCosSin(radialSegments: number) {
@@ -52,9 +59,9 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
 
     for (let i = 0; i <= linearSegments; ++i) {
         const i3 = i * 3;
-        Vec3.fromArray(u, normalVectors, i3);
-        Vec3.fromArray(v, binormalVectors, i3);
-        Vec3.fromArray(controlPoint, controlPoints, i3);
+        v3fromArray(u, normalVectors, i3);
+        v3fromArray(v, binormalVectors, i3);
+        v3fromArray(controlPoint, controlPoints, i3);
 
         const width = widthValues[i];
         const height = heightValues[i];
@@ -62,26 +69,28 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
         for (let j = 0; j < radialSegments; ++j) {
             add3AndScale2(surfacePoint, u, v, controlPoint, height * cos[j], width * sin[j]);
             if (radialSegments === 2) {
+                v3copy(normalVector, v);
+                v3normalize(normalVector, normalVector);
                 if (j !== 0 || i % 2 === 0) v3negate(normalVector, normalVector);
             } else {
                 add2AndScale2(normalVector, u, v, width * cos[j], height * sin[j]);
             }
-            Vec3.normalize(normalVector, normalVector);
+            v3normalize(normalVector, normalVector);
 
-            ChunkedArray.add3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
-            ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+            caAdd3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
+            caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
         }
     }
 
     for (let i = 0; i < linearSegments; ++i) {
         for (let j = 0; j < radialSegments; ++j) {
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + i * radialSegments + (j + 1) % radialSegments,
                 vertexCount + (i + 1) * radialSegments + (j + 1) % radialSegments,
                 vertexCount + i * radialSegments + j
             );
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + (i + 1) * radialSegments + (j + 1) % radialSegments,
                 vertexCount + (i + 1) * radialSegments + j,
@@ -93,13 +102,13 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
     if (startCap) {
         const offset = 0;
         const centerVertex = vertices.elementCount;
-        Vec3.fromArray(u, normalVectors, offset);
-        Vec3.fromArray(v, binormalVectors, offset);
-        Vec3.fromArray(controlPoint, controlPoints, offset);
-        Vec3.cross(normalVector, v, u);
+        v3fromArray(u, normalVectors, offset);
+        v3fromArray(v, binormalVectors, offset);
+        v3fromArray(controlPoint, controlPoints, offset);
+        v3cross(normalVector, v, u);
 
-        ChunkedArray.add3(vertices, controlPoint[0], controlPoint[1], controlPoint[2]);
-        ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+        caAdd3(vertices, controlPoint[0], controlPoint[1], controlPoint[2]);
+        caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
 
         const width = widthValues[0];
         const height = heightValues[0];
@@ -108,10 +117,10 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
         for (let i = 0; i < radialSegments; ++i) {
             add3AndScale2(surfacePoint, u, v, controlPoint, height * cos[i], width * sin[i]);
 
-            ChunkedArray.add3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
-            ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+            caAdd3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
+            caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
 
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + (i + 1) % radialSegments,
                 vertexCount + i,
@@ -123,13 +132,13 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
     if (endCap) {
         const offset = linearSegments * 3;
         const centerVertex = vertices.elementCount;
-        Vec3.fromArray(u, normalVectors, offset);
-        Vec3.fromArray(v, binormalVectors, offset);
-        Vec3.fromArray(controlPoint, controlPoints, offset);
-        Vec3.cross(normalVector, u, v);
+        v3fromArray(u, normalVectors, offset);
+        v3fromArray(v, binormalVectors, offset);
+        v3fromArray(controlPoint, controlPoints, offset);
+        v3cross(normalVector, u, v);
 
-        ChunkedArray.add3(vertices, controlPoint[0], controlPoint[1], controlPoint[2]);
-        ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+        caAdd3(vertices, controlPoint[0], controlPoint[1], controlPoint[2]);
+        caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
 
         const width = widthValues[linearSegments];
         const height = heightValues[linearSegments];
@@ -138,10 +147,10 @@ export function addTube(state: MeshBuilder.State, controlPoints: ArrayLike<numbe
         for (let i = 0; i < radialSegments; ++i) {
             add3AndScale2(surfacePoint, u, v, controlPoint, height * cos[i], width * sin[i]);
 
-            ChunkedArray.add3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
-            ChunkedArray.add3(normals, normalVector[0], normalVector[1], normalVector[2]);
+            caAdd3(vertices, surfacePoint[0], surfacePoint[1], surfacePoint[2]);
+            caAdd3(normals, normalVector[0], normalVector[1], normalVector[2]);
 
-            ChunkedArray.add3(
+            caAdd3(
                 indices,
                 vertexCount + i,
                 vertexCount + (i + 1) % radialSegments,

+ 50 - 40
src/mol-geo/geometry/mesh/mesh-builder.ts

@@ -12,12 +12,22 @@ import { Cage } from '../../../mol-geo/primitive/cage';
 import { addSphere } from './builder/sphere';
 import { addCylinder } from './builder/cylinder';
 
-const tmpV = Vec3.zero();
-const tmpMat3 = Mat3.zero();
-const tmpVecA = Vec3.zero();
-const tmpVecB = Vec3.zero();
-const tmpVecC = Vec3.zero();
-const tmpVecD = Vec3.zero();
+const tmpV = Vec3();
+const tmpMat3 = Mat3();
+const tmpVecA = Vec3();
+const tmpVecB = Vec3();
+const tmpVecC = Vec3();
+const tmpVecD = Vec3();
+
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const v3fromArray = Vec3.fromArray;
+const v3triangleNormal = Vec3.triangleNormal;
+const v3copy = Vec3.copy;
+const v3transformMat4 = Vec3.transformMat4;
+const v3transformMat3 = Vec3.transformMat3;
+const mat3directionTransform = Mat3.directionTransform;
+const caAdd3 = ChunkedArray.add3;
+const caAdd = ChunkedArray.add;
 
 export namespace MeshBuilder {
     export interface State {
@@ -45,36 +55,36 @@ export namespace MeshBuilder {
         const offset = vertices.elementCount;
 
         // positions
-        ChunkedArray.add3(vertices, a[0], a[1], a[2]);
-        ChunkedArray.add3(vertices, b[0], b[1], b[2]);
-        ChunkedArray.add3(vertices, c[0], c[1], c[2]);
+        caAdd3(vertices, a[0], a[1], a[2]);
+        caAdd3(vertices, b[0], b[1], b[2]);
+        caAdd3(vertices, c[0], c[1], c[2]);
 
-        Vec3.triangleNormal(tmpV, a, b, c);
+        v3triangleNormal(tmpV, a, b, c);
         for (let i = 0; i < 3; ++i) {
-            ChunkedArray.add3(normals, tmpV[0], tmpV[1], tmpV[2]);  // normal
-            ChunkedArray.add(groups, currentGroup);  // group
+            caAdd3(normals, tmpV[0], tmpV[1], tmpV[2]);  // normal
+            caAdd(groups, currentGroup);  // group
         }
-        ChunkedArray.add3(indices, offset, offset + 1, offset + 2);
+        caAdd3(indices, offset, offset + 1, offset + 2);
     }
 
     export function addTriangleStrip(state: State, vertices: ArrayLike<number>, indices: ArrayLike<number>) {
-        Vec3.fromArray(tmpVecC, vertices, indices[0] * 3);
-        Vec3.fromArray(tmpVecD, vertices, indices[1] * 3);
+        v3fromArray(tmpVecC, vertices, indices[0] * 3);
+        v3fromArray(tmpVecD, vertices, indices[1] * 3);
         for (let i = 2, il = indices.length; i < il; i += 2) {
-            Vec3.copy(tmpVecA, tmpVecC);
-            Vec3.copy(tmpVecB, tmpVecD);
-            Vec3.fromArray(tmpVecC, vertices, indices[i] * 3);
-            Vec3.fromArray(tmpVecD, vertices, indices[i + 1] * 3);
+            v3copy(tmpVecA, tmpVecC);
+            v3copy(tmpVecB, tmpVecD);
+            v3fromArray(tmpVecC, vertices, indices[i] * 3);
+            v3fromArray(tmpVecD, vertices, indices[i + 1] * 3);
             addTriangle(state, tmpVecA, tmpVecB, tmpVecC);
             addTriangle(state, tmpVecB, tmpVecD, tmpVecC);
         }
     }
 
     export function addTriangleFan(state: State, vertices: ArrayLike<number>, indices: ArrayLike<number>) {
-        Vec3.fromArray(tmpVecA, vertices, indices[0] * 3);
+        v3fromArray(tmpVecA, vertices, indices[0] * 3);
         for (let i = 2, il = indices.length; i < il; ++i) {
-            Vec3.fromArray(tmpVecB, vertices, indices[i - 1] * 3);
-            Vec3.fromArray(tmpVecC, vertices, indices[i] * 3);
+            v3fromArray(tmpVecB, vertices, indices[i - 1] * 3);
+            v3fromArray(tmpVecC, vertices, indices[i] * 3);
             addTriangle(state, tmpVecA, tmpVecC, tmpVecB);
         }
     }
@@ -83,19 +93,19 @@ export namespace MeshBuilder {
         const { vertices: va, normals: na, indices: ia } = primitive;
         const { vertices, normals, indices, groups, currentGroup } = state;
         const offset = vertices.elementCount;
-        const n = Mat3.directionTransform(tmpMat3, t);
+        const n = mat3directionTransform(tmpMat3, t);
         for (let i = 0, il = va.length; i < il; i += 3) {
             // position
-            Vec3.transformMat4(tmpV, Vec3.fromArray(tmpV, va, i), t);
-            ChunkedArray.add3(vertices, tmpV[0], tmpV[1], tmpV[2]);
+            v3transformMat4(tmpV, v3fromArray(tmpV, va, i), t);
+            caAdd3(vertices, tmpV[0], tmpV[1], tmpV[2]);
             // normal
-            Vec3.transformMat3(tmpV, Vec3.fromArray(tmpV, na, i), n);
-            ChunkedArray.add3(normals, tmpV[0], tmpV[1], tmpV[2]);
+            v3transformMat3(tmpV, v3fromArray(tmpV, na, i), n);
+            caAdd3(normals, tmpV[0], tmpV[1], tmpV[2]);
             // group
-            ChunkedArray.add(groups, currentGroup);
+            caAdd(groups, currentGroup);
         }
         for (let i = 0, il = ia.length; i < il; i += 3) {
-            ChunkedArray.add3(indices, ia[i] + offset, ia[i + 1] + offset, ia[i + 2] + offset);
+            caAdd3(indices, ia[i] + offset, ia[i + 1] + offset, ia[i + 2] + offset);
         }
     }
 
@@ -104,19 +114,19 @@ export namespace MeshBuilder {
         const { vertices: va, normals: na, indices: ia } = primitive;
         const { vertices, normals, indices, groups, currentGroup } = state;
         const offset = vertices.elementCount;
-        const n = Mat3.directionTransform(tmpMat3, t);
+        const n = mat3directionTransform(tmpMat3, t);
         for (let i = 0, il = va.length; i < il; i += 3) {
             // position
-            Vec3.transformMat4(tmpV, Vec3.fromArray(tmpV, va, i), t);
-            ChunkedArray.add3(vertices, tmpV[0], tmpV[1], tmpV[2]);
+            v3transformMat4(tmpV, v3fromArray(tmpV, va, i), t);
+            caAdd3(vertices, tmpV[0], tmpV[1], tmpV[2]);
             // normal
-            Vec3.transformMat3(tmpV, Vec3.fromArray(tmpV, na, i), n);
-            ChunkedArray.add3(normals, -tmpV[0], -tmpV[1], -tmpV[2]);
+            v3transformMat3(tmpV, v3fromArray(tmpV, na, i), n);
+            caAdd3(normals, -tmpV[0], -tmpV[1], -tmpV[2]);
             // group
-            ChunkedArray.add(groups, currentGroup);
+            caAdd(groups, currentGroup);
         }
         for (let i = 0, il = ia.length; i < il; i += 3) {
-            ChunkedArray.add3(indices, ia[i + 2] + offset, ia[i + 1] + offset, ia[i] + offset);
+            caAdd3(indices, ia[i + 2] + offset, ia[i + 1] + offset, ia[i] + offset);
         }
     }
 
@@ -124,10 +134,10 @@ export namespace MeshBuilder {
         const { vertices: va, edges: ea } = cage;
         const cylinderProps = { radiusTop: radius, radiusBottom: radius, radialSegments };
         for (let i = 0, il = ea.length; i < il; i += 2) {
-            Vec3.fromArray(tmpVecA, va, ea[i] * 3);
-            Vec3.fromArray(tmpVecB, va, ea[i + 1] * 3);
-            Vec3.transformMat4(tmpVecA, tmpVecA, t);
-            Vec3.transformMat4(tmpVecB, tmpVecB, t);
+            v3fromArray(tmpVecA, va, ea[i] * 3);
+            v3fromArray(tmpVecB, va, ea[i + 1] * 3);
+            v3transformMat4(tmpVecA, tmpVecA, t);
+            v3transformMat4(tmpVecB, tmpVecB, t);
             addSphere(state, tmpVecA, radius, detail);
             addSphere(state, tmpVecB, radius, detail);
             addCylinder(state, tmpVecA, tmpVecB, 1, cylinderProps);

+ 6 - 2
src/mol-geo/geometry/points/points-builder.ts

@@ -7,6 +7,10 @@
 import { ChunkedArray } from '../../../mol-data/util';
 import { Points } from './points';
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const caAdd3 = ChunkedArray.add3;
+const caAdd = ChunkedArray.add;
+
 export interface PointsBuilder {
     add(x: number, y: number, z: number, group: number): void
     getPoints(): Points
@@ -19,8 +23,8 @@ export namespace PointsBuilder {
 
         return {
             add: (x: number, y: number, z: number, group: number) => {
-                ChunkedArray.add3(centers, x, y, z);
-                ChunkedArray.add(groups, group);
+                caAdd3(centers, x, y, z);
+                caAdd(groups, group);
             },
             getPoints: () => {
                 const cb = ChunkedArray.compact(centers, true) as Float32Array;

+ 10 - 5
src/mol-geo/geometry/spheres/spheres-builder.ts

@@ -19,6 +19,11 @@ const quadIndices = new Uint16Array([
     1, 3, 2
 ]);
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const caAdd3 = ChunkedArray.add3;
+const caAdd2 = ChunkedArray.add2;
+const caAdd = ChunkedArray.add;
+
 export interface SpheresBuilder {
     add(x: number, y: number, z: number, group: number): void
     getSpheres(): Spheres
@@ -37,12 +42,12 @@ export namespace SpheresBuilder {
             add: (x: number, y: number, z: number, group: number) => {
                 const offset = centers.elementCount;
                 for (let i = 0; i < 4; ++i) {
-                    ChunkedArray.add3(centers, x, y, z);
-                    ChunkedArray.add2(mappings, quadMapping[i * 2], quadMapping[i * 2 + 1]);
-                    ChunkedArray.add(groups, group);
+                    caAdd3(centers, x, y, z);
+                    caAdd2(mappings, quadMapping[i * 2], quadMapping[i * 2 + 1]);
+                    caAdd(groups, group);
                 }
-                ChunkedArray.add3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
-                ChunkedArray.add3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
+                caAdd3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
+                caAdd3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
             },
             getSpheres: () => {
                 const cb = ChunkedArray.compact(centers, true) as Float32Array;

+ 32 - 27
src/mol-geo/geometry/text/text-builder.ts

@@ -14,6 +14,11 @@ const quadIndices = new Uint16Array([
     1, 3, 2
 ]);
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const caAdd3 = ChunkedArray.add3;
+const caAdd2 = ChunkedArray.add2;
+const caAdd = ChunkedArray.add;
+
 export interface TextBuilder {
     add(str: string, x: number, y: number, z: number, depth: number, scale: number, group: number): void
     getText(): Text
@@ -38,9 +43,9 @@ export namespace TextBuilder {
         const outline = fontAtlas.buffer / fontAtlas.lineHeight;
 
         const add = (x: number, y: number, z: number, depth: number, group: number) => {
-            ChunkedArray.add3(centers, x, y, z);
-            ChunkedArray.add(depths, depth);
-            ChunkedArray.add(groups, group);
+            caAdd3(centers, x, y, z);
+            caAdd(depths, depth);
+            caAdd(groups, group);
         };
 
         return {
@@ -117,18 +122,18 @@ export namespace TextBuilder {
 
                 // background
                 if (background) {
-                    ChunkedArray.add2(mappings, xLeft, yTop); // top left
-                    ChunkedArray.add2(mappings, xLeft, yBottom); // bottom left
-                    ChunkedArray.add2(mappings, xRight, yTop); // top right
-                    ChunkedArray.add2(mappings, xRight, yBottom); // bottom right
+                    caAdd2(mappings, xLeft, yTop); // top left
+                    caAdd2(mappings, xLeft, yBottom); // bottom left
+                    caAdd2(mappings, xRight, yTop); // top right
+                    caAdd2(mappings, xRight, yBottom); // bottom right
 
                     const offset = centers.elementCount;
                     for (let i = 0; i < 4; ++i) {
-                        ChunkedArray.add2(tcoords, 10, 10);
+                        caAdd2(tcoords, 10, 10);
                         add(x, y, z, depth, group);
                     }
-                    ChunkedArray.add3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
-                    ChunkedArray.add3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
+                    caAdd3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
+                    caAdd3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
                 }
 
                 if (tether) {
@@ -234,18 +239,18 @@ export namespace TextBuilder {
                         default:
                             throw new Error('unsupported attachment');
                     }
-                    ChunkedArray.add2(mappings, xTip, yTip); // tip
-                    ChunkedArray.add2(mappings, xBaseA, yBaseA); // base A
-                    ChunkedArray.add2(mappings, xBaseB, yBaseB); // base B
-                    ChunkedArray.add2(mappings, xBaseCenter, yBaseCenter); // base center
+                    caAdd2(mappings, xTip, yTip); // tip
+                    caAdd2(mappings, xBaseA, yBaseA); // base A
+                    caAdd2(mappings, xBaseB, yBaseB); // base B
+                    caAdd2(mappings, xBaseCenter, yBaseCenter); // base center
 
                     const offset = centers.elementCount;
                     for (let i = 0; i < 4; ++i) {
-                        ChunkedArray.add2(tcoords, 10, 10);
+                        caAdd2(tcoords, 10, 10);
                         add(x, y, z, depth, group);
                     }
-                    ChunkedArray.add3(indices, offset, offset + 1, offset + 3);
-                    ChunkedArray.add3(indices, offset, offset + 3, offset + 2);
+                    caAdd3(indices, offset, offset + 1, offset + 3);
+                    caAdd3(indices, offset, offset + 3, offset + 2);
                 }
 
                 xShift += outline;
@@ -260,25 +265,25 @@ export namespace TextBuilder {
                     const top = (c.nh - yShift) * scale;
                     const bottom = (-yShift) * scale;
 
-                    ChunkedArray.add2(mappings, left, top);
-                    ChunkedArray.add2(mappings, left, bottom);
-                    ChunkedArray.add2(mappings, right, top);
-                    ChunkedArray.add2(mappings, right, bottom);
+                    caAdd2(mappings, left, top);
+                    caAdd2(mappings, left, bottom);
+                    caAdd2(mappings, right, top);
+                    caAdd2(mappings, right, bottom);
 
                     const texWidth = fontAtlas.texture.width;
                     const texHeight = fontAtlas.texture.height;
 
-                    ChunkedArray.add2(tcoords, c.x / texWidth, c.y / texHeight); // top left
-                    ChunkedArray.add2(tcoords, c.x / texWidth, (c.y + c.h) / texHeight); // bottom left
-                    ChunkedArray.add2(tcoords, (c.x + c.w) / texWidth, c.y / texHeight); // top right
-                    ChunkedArray.add2(tcoords, (c.x + c.w) / texWidth, (c.y + c.h) / texHeight); // bottom right
+                    caAdd2(tcoords, c.x / texWidth, c.y / texHeight); // top left
+                    caAdd2(tcoords, c.x / texWidth, (c.y + c.h) / texHeight); // bottom left
+                    caAdd2(tcoords, (c.x + c.w) / texWidth, c.y / texHeight); // top right
+                    caAdd2(tcoords, (c.x + c.w) / texWidth, (c.y + c.h) / texHeight); // bottom right
 
                     xadvance += c.nw - 2 * outline;
 
                     const offset = centers.elementCount;
                     for (let i = 0; i < 4; ++i) add(x, y, z, depth, group);
-                    ChunkedArray.add3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
-                    ChunkedArray.add3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
+                    caAdd3(indices, offset + quadIndices[0], offset + quadIndices[1], offset + quadIndices[2]);
+                    caAdd3(indices, offset + quadIndices[3], offset + quadIndices[4], offset + quadIndices[5]);
                 }
             },
             getText: () => {

+ 17 - 10
src/mol-repr/structure/visual/util/link.ts

@@ -79,6 +79,13 @@ export enum LinkStyle {
     Disk = 4
 }
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const v3scale = Vec3.scale;
+const v3add = Vec3.add;
+const v3sub = Vec3.sub;
+const v3setMagnitude = Vec3.setMagnitude;
+const v3dot = Vec3.dot;
+
 /**
  * Each edge is included twice to allow for coloring/picking
  * the half closer to the first vertex, i.e. vertex a.
@@ -124,7 +131,7 @@ export function createLinkCylinderMesh(ctx: VisualContext, linkBuilder: LinkBuil
             const absOffset = (linkRadius - multiRadius) * linkSpacing;
 
             calculateShiftDir(vShift, va, vb, referencePosition ? referencePosition(edgeIndex) : null);
-            Vec3.setMagnitude(vShift, vShift, absOffset);
+            v3setMagnitude(vShift, vShift, absOffset);
 
             cylinderProps.radiusTop = cylinderProps.radiusBottom = multiRadius;
             cylinderProps.topCap = cylinderProps.bottomCap = linkCap;
@@ -132,12 +139,12 @@ export function createLinkCylinderMesh(ctx: VisualContext, linkBuilder: LinkBuil
             if (order === 3) addCylinder(builderState, va, vb, 0.5, cylinderProps);
             addDoubleCylinder(builderState, va, vb, 0.5, vShift, cylinderProps);
         } else if (linkStyle === LinkStyle.Disk) {
-            Vec3.scale(tmpV12, Vec3.sub(tmpV12, vb, va), 0.475);
-            Vec3.add(va, va, tmpV12);
-            Vec3.sub(vb, vb, tmpV12);
+            v3scale(tmpV12, v3sub(tmpV12, vb, va), 0.475);
+            v3add(va, va, tmpV12);
+            v3sub(vb, vb, tmpV12);
 
             cylinderProps.radiusTop = cylinderProps.radiusBottom = linkRadius;
-            if (Vec3.dot(tmpV12, up) > 0) {
+            if (v3dot(tmpV12, up) > 0) {
                 cylinderProps.topCap = false;
                 cylinderProps.bottomCap = linkCap;
             } else {
@@ -179,7 +186,7 @@ export function createLinkLines(ctx: VisualContext, linkBuilder: LinkBuilderProp
         if (ignore && ignore(edgeIndex)) continue;
 
         position(va, vb, edgeIndex);
-        Vec3.scale(vb, Vec3.add(vb, va, vb), 0.5);
+        v3scale(vb, v3add(vb, va, vb), 0.5);
 
         // TODO use line width?
         const linkStyle = style ? style(edgeIndex) : LinkStyle.Solid;
@@ -192,15 +199,15 @@ export function createLinkLines(ctx: VisualContext, linkBuilder: LinkBuilderProp
             const absOffset = (1 - multiRadius) * linkSpacing;
 
             calculateShiftDir(vShift, va, vb, referencePosition ? referencePosition(edgeIndex) : null);
-            Vec3.setMagnitude(vShift, vShift, absOffset);
+            v3setMagnitude(vShift, vShift, absOffset);
 
             if (order === 3) builder.add(va[0], va[1], va[2], vb[0], vb[1], vb[2], edgeIndex);
             builder.add(va[0] + vShift[0], va[1] + vShift[1], va[2] + vShift[2], vb[0] + vShift[0], vb[1] + vShift[1], vb[2] + vShift[2], edgeIndex);
             builder.add(va[0] - vShift[0], va[1] - vShift[1], va[2] - vShift[2], vb[0] - vShift[0], vb[1] - vShift[1], vb[2] - vShift[2], edgeIndex);
         } else if (linkStyle === LinkStyle.Disk) {
-            Vec3.scale(tmpV12, Vec3.sub(tmpV12, vb, va), 0.475);
-            Vec3.add(va, va, tmpV12);
-            Vec3.sub(vb, vb, tmpV12);
+            v3scale(tmpV12, v3sub(tmpV12, vb, va), 0.475);
+            v3add(va, va, tmpV12);
+            v3sub(vb, vb, tmpV12);
 
             // TODO what to do here?
             builder.add(va[0], va[1], va[2], vb[0], vb[1], vb[2], edgeIndex);

+ 37 - 25
src/mol-repr/structure/visual/util/polymer/curve-segment.ts

@@ -1,5 +1,5 @@
 /**
- * Copyright (c) 2018-2019 mol* contributors, licensed under MIT, See LICENSE file for more info.
+ * Copyright (c) 2018-2020 mol* contributors, licensed under MIT, See LICENSE file for more info.
  *
  * @author Alexander Rose <alexander.rose@weirdbyte.de>
  */
@@ -8,6 +8,18 @@ import { Vec3 } from '../../../../../mol-math/linear-algebra';
 import { NumberArray } from '../../../../../mol-util/type-helpers';
 import { lerp } from '../../../../../mol-math/interpolate';
 
+// avoiding namespace lookup improved performance in Chrome (Aug 2020)
+const v3fromArray = Vec3.fromArray;
+const v3toArray = Vec3.toArray;
+const v3normalize = Vec3.normalize;
+const v3sub = Vec3.sub;
+const v3spline = Vec3.spline;
+const v3slerp = Vec3.slerp;
+const v3copy = Vec3.copy;
+const v3cross = Vec3.cross;
+const v3orthogonalize = Vec3.orthogonalize;
+const v3matchDirection = Vec3.matchDirection;
+
 export interface CurveSegmentState {
     curvePoints: NumberArray,
     tangentVectors: NumberArray,
@@ -43,9 +55,9 @@ export function interpolateCurveSegment(state: CurveSegmentState, controls: Curv
     interpolateNormals(state, controls);
 }
 
-const tanA = Vec3.zero();
-const tanB = Vec3.zero();
-const curvePoint = Vec3.zero();
+const tanA = Vec3();
+const tanB = Vec3();
+const curvePoint = Vec3();
 
 export function interpolatePointsAndTangents(state: CurveSegmentState, controls: CurveSegmentControls, tension: number, shift: number) {
     const { curvePoints, tangentVectors, linearSegments } = state;
@@ -60,18 +72,18 @@ export function interpolatePointsAndTangents(state: CurveSegmentState, controls:
         const t = j * 1.0 / linearSegments;
         if (t < shift1) {
             const te = lerp(tensionBeg, tension, t);
-            Vec3.spline(curvePoint, p0, p1, p2, p3, t + shift, te);
-            Vec3.spline(tanA, p0, p1, p2, p3, t + shift + 0.01, tensionBeg);
-            Vec3.spline(tanB, p0, p1, p2, p3, t + shift - 0.01, tensionBeg);
+            v3spline(curvePoint, p0, p1, p2, p3, t + shift, te);
+            v3spline(tanA, p0, p1, p2, p3, t + shift + 0.01, tensionBeg);
+            v3spline(tanB, p0, p1, p2, p3, t + shift - 0.01, tensionBeg);
         } else {
             const te = lerp(tension, tensionEnd, t);
-            Vec3.spline(curvePoint, p1, p2, p3, p4, t - shift1, te);
-            Vec3.spline(tanA, p1, p2, p3, p4, t - shift1 + 0.01, te);
-            Vec3.spline(tanB, p1, p2, p3, p4, t - shift1 - 0.01, te);
+            v3spline(curvePoint, p1, p2, p3, p4, t - shift1, te);
+            v3spline(tanA, p1, p2, p3, p4, t - shift1 + 0.01, te);
+            v3spline(tanB, p1, p2, p3, p4, t - shift1 - 0.01, te);
         }
-        Vec3.toArray(curvePoint, curvePoints, j * 3);
-        Vec3.normalize(tangentVec, Vec3.sub(tangentVec, tanA, tanB));
-        Vec3.toArray(tangentVec, tangentVectors, j * 3);
+        v3toArray(curvePoint, curvePoints, j * 3);
+        v3normalize(tangentVec, v3sub(tangentVec, tanA, tanB));
+        v3toArray(tangentVec, tangentVectors, j * 3);
     }
 }
 
@@ -95,27 +107,27 @@ export function interpolateNormals(state: CurveSegmentState, controls: CurveSegm
 
     const n = curvePoints.length / 3;
 
-    Vec3.fromArray(firstTangentVec, tangentVectors, 0);
-    Vec3.fromArray(lastTangentVec, tangentVectors, (n - 1) * 3);
+    v3fromArray(firstTangentVec, tangentVectors, 0);
+    v3fromArray(lastTangentVec, tangentVectors, (n - 1) * 3);
 
-    Vec3.orthogonalize(firstNormalVec, firstTangentVec, firstDirection);
-    Vec3.orthogonalize(lastNormalVec, lastTangentVec, lastDirection);
-    Vec3.matchDirection(lastNormalVec, lastNormalVec, firstNormalVec);
+    v3orthogonalize(firstNormalVec, firstTangentVec, firstDirection);
+    v3orthogonalize(lastNormalVec, lastTangentVec, lastDirection);
+    v3matchDirection(lastNormalVec, lastNormalVec, firstNormalVec);
 
-    Vec3.copy(prevNormal, firstNormalVec);
+    v3copy(prevNormal, firstNormalVec);
 
     for (let i = 0; i < n; ++i) {
         const t = i === 0 ? 0 : 1 / (n - i);
 
-        Vec3.fromArray(tangentVec, tangentVectors, i * 3);
+        v3fromArray(tangentVec, tangentVectors, i * 3);
 
-        Vec3.orthogonalize(normalVec, tangentVec, Vec3.slerp(tmpNormal, prevNormal, lastNormalVec, t));
-        Vec3.toArray(normalVec, normalVectors, i * 3);
+        v3orthogonalize(normalVec, tangentVec, v3slerp(tmpNormal, prevNormal, lastNormalVec, t));
+        v3toArray(normalVec, normalVectors, i * 3);
 
-        Vec3.copy(prevNormal, normalVec);
+        v3copy(prevNormal, normalVec);
 
-        Vec3.normalize(binormalVec, Vec3.cross(binormalVec, tangentVec, normalVec));
-        Vec3.toArray(binormalVec, binormalVectors, i * 3);
+        v3normalize(binormalVec, v3cross(binormalVec, tangentVec, normalVec));
+        v3toArray(binormalVec, binormalVectors, i * 3);
     }
 }