UNPKG

6.5 kBJavaScriptView Raw
1'use strict';
2
3Object.defineProperty(exports, '__esModule', { value: true });
4
5var constants = require('@pixi/constants');
6var runner = require('@pixi/runner');
7var utils = require('@pixi/utils');
8var Attribute = require('./Attribute.js');
9var Buffer = require('./Buffer.js');
10var interleaveTypedArrays = require('./utils/interleaveTypedArrays.js');
11
12const byteSizeMap = { 5126: 4, 5123: 2, 5121: 1 };
13let UID = 0;
14const map = {
15 Float32Array,
16 Uint32Array,
17 Int32Array,
18 Uint8Array,
19 Uint16Array
20};
21class Geometry {
22 constructor(buffers = [], attributes = {}) {
23 this.buffers = buffers;
24 this.indexBuffer = null;
25 this.attributes = attributes;
26 this.glVertexArrayObjects = {};
27 this.id = UID++;
28 this.instanced = false;
29 this.instanceCount = 1;
30 this.disposeRunner = new runner.Runner("disposeGeometry");
31 this.refCount = 0;
32 }
33 addAttribute(id, buffer, size = 0, normalized = false, type, stride, start, instance = false) {
34 if (!buffer) {
35 throw new Error("You must pass a buffer when creating an attribute");
36 }
37 if (!(buffer instanceof Buffer.Buffer)) {
38 if (buffer instanceof Array) {
39 buffer = new Float32Array(buffer);
40 }
41 buffer = new Buffer.Buffer(buffer);
42 }
43 const ids = id.split("|");
44 if (ids.length > 1) {
45 for (let i = 0; i < ids.length; i++) {
46 this.addAttribute(ids[i], buffer, size, normalized, type);
47 }
48 return this;
49 }
50 let bufferIndex = this.buffers.indexOf(buffer);
51 if (bufferIndex === -1) {
52 this.buffers.push(buffer);
53 bufferIndex = this.buffers.length - 1;
54 }
55 this.attributes[id] = new Attribute.Attribute(bufferIndex, size, normalized, type, stride, start, instance);
56 this.instanced = this.instanced || instance;
57 return this;
58 }
59 getAttribute(id) {
60 return this.attributes[id];
61 }
62 getBuffer(id) {
63 return this.buffers[this.getAttribute(id).buffer];
64 }
65 addIndex(buffer) {
66 if (!(buffer instanceof Buffer.Buffer)) {
67 if (buffer instanceof Array) {
68 buffer = new Uint16Array(buffer);
69 }
70 buffer = new Buffer.Buffer(buffer);
71 }
72 buffer.type = constants.BUFFER_TYPE.ELEMENT_ARRAY_BUFFER;
73 this.indexBuffer = buffer;
74 if (!this.buffers.includes(buffer)) {
75 this.buffers.push(buffer);
76 }
77 return this;
78 }
79 getIndex() {
80 return this.indexBuffer;
81 }
82 interleave() {
83 if (this.buffers.length === 1 || this.buffers.length === 2 && this.indexBuffer)
84 return this;
85 const arrays = [];
86 const sizes = [];
87 const interleavedBuffer = new Buffer.Buffer();
88 let i;
89 for (i in this.attributes) {
90 const attribute = this.attributes[i];
91 const buffer = this.buffers[attribute.buffer];
92 arrays.push(buffer.data);
93 sizes.push(attribute.size * byteSizeMap[attribute.type] / 4);
94 attribute.buffer = 0;
95 }
96 interleavedBuffer.data = interleaveTypedArrays.interleaveTypedArrays(arrays, sizes);
97 for (i = 0; i < this.buffers.length; i++) {
98 if (this.buffers[i] !== this.indexBuffer) {
99 this.buffers[i].destroy();
100 }
101 }
102 this.buffers = [interleavedBuffer];
103 if (this.indexBuffer) {
104 this.buffers.push(this.indexBuffer);
105 }
106 return this;
107 }
108 getSize() {
109 for (const i in this.attributes) {
110 const attribute = this.attributes[i];
111 const buffer = this.buffers[attribute.buffer];
112 return buffer.data.length / (attribute.stride / 4 || attribute.size);
113 }
114 return 0;
115 }
116 dispose() {
117 this.disposeRunner.emit(this, false);
118 }
119 destroy() {
120 this.dispose();
121 this.buffers = null;
122 this.indexBuffer = null;
123 this.attributes = null;
124 }
125 clone() {
126 const geometry = new Geometry();
127 for (let i = 0; i < this.buffers.length; i++) {
128 geometry.buffers[i] = new Buffer.Buffer(this.buffers[i].data.slice(0));
129 }
130 for (const i in this.attributes) {
131 const attrib = this.attributes[i];
132 geometry.attributes[i] = new Attribute.Attribute(attrib.buffer, attrib.size, attrib.normalized, attrib.type, attrib.stride, attrib.start, attrib.instance);
133 }
134 if (this.indexBuffer) {
135 geometry.indexBuffer = geometry.buffers[this.buffers.indexOf(this.indexBuffer)];
136 geometry.indexBuffer.type = constants.BUFFER_TYPE.ELEMENT_ARRAY_BUFFER;
137 }
138 return geometry;
139 }
140 static merge(geometries) {
141 const geometryOut = new Geometry();
142 const arrays = [];
143 const sizes = [];
144 const offsets = [];
145 let geometry;
146 for (let i = 0; i < geometries.length; i++) {
147 geometry = geometries[i];
148 for (let j = 0; j < geometry.buffers.length; j++) {
149 sizes[j] = sizes[j] || 0;
150 sizes[j] += geometry.buffers[j].data.length;
151 offsets[j] = 0;
152 }
153 }
154 for (let i = 0; i < geometry.buffers.length; i++) {
155 arrays[i] = new map[utils.getBufferType(geometry.buffers[i].data)](sizes[i]);
156 geometryOut.buffers[i] = new Buffer.Buffer(arrays[i]);
157 }
158 for (let i = 0; i < geometries.length; i++) {
159 geometry = geometries[i];
160 for (let j = 0; j < geometry.buffers.length; j++) {
161 arrays[j].set(geometry.buffers[j].data, offsets[j]);
162 offsets[j] += geometry.buffers[j].data.length;
163 }
164 }
165 geometryOut.attributes = geometry.attributes;
166 if (geometry.indexBuffer) {
167 geometryOut.indexBuffer = geometryOut.buffers[geometry.buffers.indexOf(geometry.indexBuffer)];
168 geometryOut.indexBuffer.type = constants.BUFFER_TYPE.ELEMENT_ARRAY_BUFFER;
169 let offset = 0;
170 let stride = 0;
171 let offset2 = 0;
172 let bufferIndexToCount = 0;
173 for (let i = 0; i < geometry.buffers.length; i++) {
174 if (geometry.buffers[i] !== geometry.indexBuffer) {
175 bufferIndexToCount = i;
176 break;
177 }
178 }
179 for (const i in geometry.attributes) {
180 const attribute = geometry.attributes[i];
181 if ((attribute.buffer | 0) === bufferIndexToCount) {
182 stride += attribute.size * byteSizeMap[attribute.type] / 4;
183 }
184 }
185 for (let i = 0; i < geometries.length; i++) {
186 const indexBufferData = geometries[i].indexBuffer.data;
187 for (let j = 0; j < indexBufferData.length; j++) {
188 geometryOut.indexBuffer.data[j + offset2] += offset;
189 }
190 offset += geometries[i].buffers[bufferIndexToCount].data.length / stride;
191 offset2 += indexBufferData.length;
192 }
193 }
194 return geometryOut;
195 }
196}
197
198exports.Geometry = Geometry;
199//# sourceMappingURL=Geometry.js.map