-
Notifications
You must be signed in to change notification settings - Fork 34
/
index.js
132 lines (110 loc) · 3.71 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
var inherits = require('inherits');
var getNormals = require('polyline-normals');
var VERTS_PER_POINT = 2;
module.exports = function createLineMesh (THREE) {
function LineMesh (path, opt) {
if (!(this instanceof LineMesh)) {
return new LineMesh(path, opt);
}
THREE.BufferGeometry.call(this);
if (Array.isArray(path)) {
opt = opt || {};
} else if (typeof path === 'object') {
opt = path;
path = [];
}
opt = opt || {};
this.addAttribute('position', new THREE.BufferAttribute(undefined, 3));
this.addAttribute('lineNormal', new THREE.BufferAttribute(undefined, 2));
this.addAttribute('lineMiter', new THREE.BufferAttribute(undefined, 1));
if (opt.distances) {
this.addAttribute('lineDistance', new THREE.BufferAttribute(undefined, 1));
}
if (typeof this.setIndex === 'function') {
this.setIndex(new THREE.BufferAttribute(undefined, 1));
} else {
this.addAttribute('index', new THREE.BufferAttribute(undefined, 1));
}
this.update(path, opt.closed);
}
inherits(LineMesh, THREE.BufferGeometry);
LineMesh.prototype.update = function (path, closed) {
path = path || [];
var normals = getNormals(path, closed);
if (closed) {
path = path.slice();
path.push(path[0]);
normals.push(normals[0]);
}
var attrPosition = this.getAttribute('position');
var attrNormal = this.getAttribute('lineNormal');
var attrMiter = this.getAttribute('lineMiter');
var attrDistance = this.getAttribute('lineDistance');
var attrIndex = typeof this.getIndex === 'function' ? this.getIndex() : this.getAttribute('index');
var indexCount = Math.max(0, (path.length - 1) * 6);
if (!attrPosition.array ||
(path.length !== attrPosition.array.length / 3 / VERTS_PER_POINT)) {
var count = path.length * VERTS_PER_POINT;
attrPosition.array = new Float32Array(count * 3);
attrNormal.array = new Float32Array(count * 2);
attrMiter.array = new Float32Array(count);
attrIndex.array = new Uint16Array(indexCount);
if (attrDistance) {
attrDistance.array = new Float32Array(count);
}
}
if (undefined !== attrPosition.count) {
attrPosition.count = count;
}
attrPosition.needsUpdate = true;
if (undefined !== attrNormal.count) {
attrNormal.count = count;
}
attrNormal.needsUpdate = true;
if (undefined !== attrMiter.count) {
attrMiter.count = count;
}
attrMiter.needsUpdate = true;
if (undefined !== attrIndex.count) {
attrIndex.count = indexCount;
}
attrIndex.needsUpdate = true;
if (attrDistance) {
if (undefined !== attrDistance.count) {
attrDistance.count = count;
}
attrDistance.needsUpdate = true;
}
var index = 0;
var c = 0;
var dIndex = 0;
var indexArray = attrIndex.array;
path.forEach(function (point, pointIndex, list) {
var i = index;
indexArray[c++] = i + 0;
indexArray[c++] = i + 1;
indexArray[c++] = i + 2;
indexArray[c++] = i + 2;
indexArray[c++] = i + 1;
indexArray[c++] = i + 3;
attrPosition.setXYZ(index++, point[0], point[1], 0);
attrPosition.setXYZ(index++, point[0], point[1], 0);
if (attrDistance) {
var d = pointIndex / (list.length - 1);
attrDistance.setX(dIndex++, d);
attrDistance.setX(dIndex++, d);
}
});
var nIndex = 0;
var mIndex = 0;
normals.forEach(function (n) {
var norm = n[0];
var miter = n[1];
attrNormal.setXY(nIndex++, norm[0], norm[1]);
attrNormal.setXY(nIndex++, norm[0], norm[1]);
attrMiter.setX(mIndex++, -miter);
attrMiter.setX(mIndex++, miter);
});
};
return LineMesh;
};