165 lines
8.1 KiB
JavaScript
165 lines
8.1 KiB
JavaScript
shadow$provide.module$node_modules$pixi_DOT_js$lib$rendering$renderers$gl$geometry$GlGeometrySystem = function(global, require, module, exports) {
|
|
global = require("module$node_modules$pixi_DOT_js$lib$extensions$Extensions");
|
|
var GCManagedHash = require("module$node_modules$pixi_DOT_js$lib$utils$data$GCManagedHash"), getAttributeInfoFromFormat = require("module$node_modules$pixi_DOT_js$lib$rendering$renderers$shared$geometry$utils$getAttributeInfoFromFormat"), ensureAttributes = require("module$node_modules$pixi_DOT_js$lib$rendering$renderers$gl$shader$program$ensureAttributes"), getGlTypeFromFormat = require("module$node_modules$pixi_DOT_js$lib$rendering$renderers$gl$geometry$utils$getGlTypeFromFormat");
|
|
"use strict";
|
|
const topologyToGlMap = {"point-list":0, "line-list":1, "line-strip":3, "triangle-list":4, "triangle-strip":5};
|
|
class GlGeometryGpuData {
|
|
constructor() {
|
|
this.vaoCache = Object.create(null);
|
|
}
|
|
destroy() {
|
|
this.vaoCache = Object.create(null);
|
|
}
|
|
}
|
|
class GlGeometrySystem {
|
|
constructor(renderer) {
|
|
this._renderer = renderer;
|
|
this._activeVao = this._activeGeometry = null;
|
|
this.hasInstance = this.hasVao = !0;
|
|
this._managedGeometries = new GCManagedHash.GCManagedHash({renderer, type:"resource", onUnload:this.onGeometryUnload.bind(this), name:"glGeometry"});
|
|
}
|
|
contextChange() {
|
|
const gl = this.gl = this._renderer.gl;
|
|
if (!this._renderer.context.supports.vertexArrayObject) {
|
|
throw Error("[PixiJS] Vertex Array Objects are not supported on this device");
|
|
}
|
|
this.destroyAll(!0);
|
|
const nativeVaoExtension = this._renderer.context.extensions.vertexArrayObject;
|
|
nativeVaoExtension && (gl.createVertexArray = () => nativeVaoExtension.createVertexArrayOES(), gl.bindVertexArray = vao => nativeVaoExtension.bindVertexArrayOES(vao), gl.deleteVertexArray = vao => nativeVaoExtension.deleteVertexArrayOES(vao));
|
|
const nativeInstancedExtension = this._renderer.context.extensions.vertexAttribDivisorANGLE;
|
|
nativeInstancedExtension && (gl.drawArraysInstanced = (a, b, c, d) => {
|
|
nativeInstancedExtension.drawArraysInstancedANGLE(a, b, c, d);
|
|
}, gl.drawElementsInstanced = (a, b, c, d, e) => {
|
|
nativeInstancedExtension.drawElementsInstancedANGLE(a, b, c, d, e);
|
|
}, gl.vertexAttribDivisor = (a, b) => nativeInstancedExtension.vertexAttribDivisorANGLE(a, b));
|
|
this._activeVao = this._activeGeometry = null;
|
|
}
|
|
bind(geometry, program) {
|
|
const gl = this.gl;
|
|
this._activeGeometry = geometry;
|
|
geometry = this.getVao(geometry, program);
|
|
this._activeVao !== geometry && (this._activeVao = geometry, gl.bindVertexArray(geometry));
|
|
this.updateBuffers();
|
|
}
|
|
resetState() {
|
|
this.unbind();
|
|
}
|
|
updateBuffers() {
|
|
const geometry = this._activeGeometry, bufferSystem = this._renderer.buffer;
|
|
for (let i = 0; i < geometry.buffers.length; i++) {
|
|
bufferSystem.updateBuffer(geometry.buffers[i]);
|
|
}
|
|
geometry._gcLastUsed = this._renderer.gc.now;
|
|
}
|
|
checkCompatibility(geometry, program) {
|
|
geometry = geometry.attributes;
|
|
program = program._attributeData;
|
|
for (const j in program) {
|
|
if (!geometry[j]) {
|
|
throw Error(`shader and geometry incompatible, geometry missing the "${j}" attribute`);
|
|
}
|
|
}
|
|
}
|
|
getSignature(geometry, program) {
|
|
const attribs = geometry.attributes;
|
|
program = program._attributeData;
|
|
geometry = ["g", geometry.uid];
|
|
for (const i in attribs) {
|
|
program[i] && geometry.push(i, program[i].location);
|
|
}
|
|
return geometry.join("-");
|
|
}
|
|
getVao(geometry, program) {
|
|
return geometry._gpuData[this._renderer.uid]?.vaoCache[program._key] || this.initGeometryVao(geometry, program);
|
|
}
|
|
initGeometryVao(geometry, program, _incRefCount) {
|
|
_incRefCount = this._renderer.gl;
|
|
const bufferSystem = this._renderer.buffer;
|
|
this._renderer.shader._getProgramData(program);
|
|
this.checkCompatibility(geometry, program);
|
|
const signature = this.getSignature(geometry, program);
|
|
var gpuData = geometry._gpuData[this._renderer.uid];
|
|
gpuData || (gpuData = new GlGeometryGpuData(), geometry._gpuData[this._renderer.uid] = gpuData, this._managedGeometries.add(geometry));
|
|
gpuData = gpuData.vaoCache;
|
|
let vao = gpuData[signature];
|
|
if (vao) {
|
|
return gpuData[program._key] = vao;
|
|
}
|
|
ensureAttributes.ensureAttributes(geometry, program._attributeData);
|
|
const buffers = geometry.buffers;
|
|
vao = _incRefCount.createVertexArray();
|
|
_incRefCount.bindVertexArray(vao);
|
|
for (let i = 0; i < buffers.length; i++) {
|
|
bufferSystem.bind(buffers[i]);
|
|
}
|
|
this.activateVao(geometry, program);
|
|
gpuData[program._key] = vao;
|
|
gpuData[signature] = vao;
|
|
_incRefCount.bindVertexArray(null);
|
|
return vao;
|
|
}
|
|
onGeometryUnload(geometry, contextLost = !1) {
|
|
if (geometry = geometry._gpuData[this._renderer.uid]) {
|
|
if (geometry = geometry.vaoCache, !contextLost) {
|
|
for (const i in geometry) {
|
|
this._activeVao !== geometry[i] && this.resetState(), this.gl.deleteVertexArray(geometry[i]);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
destroyAll(contextLost = !1) {
|
|
this._managedGeometries.removeAll(contextLost);
|
|
}
|
|
activateVao(geometry, program) {
|
|
const gl = this._renderer.gl, bufferSystem = this._renderer.buffer, attributes = geometry.attributes;
|
|
geometry.indexBuffer && bufferSystem.bind(geometry.indexBuffer);
|
|
geometry = null;
|
|
for (const j in attributes) {
|
|
const attribute = attributes[j];
|
|
var buffer = attribute.buffer, glBuffer = bufferSystem.getGlBuffer(buffer);
|
|
const programAttrib = program._attributeData[j];
|
|
if (programAttrib) {
|
|
geometry !== glBuffer && (bufferSystem.bind(buffer), geometry = glBuffer);
|
|
buffer = programAttrib.location;
|
|
gl.enableVertexAttribArray(buffer);
|
|
glBuffer = getAttributeInfoFromFormat.getAttributeInfoFromFormat(attribute.format);
|
|
const type = getGlTypeFromFormat.getGlTypeFromFormat(attribute.format);
|
|
"int" === programAttrib.format?.substring(1, 4) ? gl.vertexAttribIPointer(buffer, glBuffer.size, type, attribute.stride, attribute.offset) : gl.vertexAttribPointer(buffer, glBuffer.size, type, glBuffer.normalised, attribute.stride, attribute.offset);
|
|
if (attribute.instance) {
|
|
if (this.hasInstance) {
|
|
gl.vertexAttribDivisor(buffer, attribute.divisor ?? 1);
|
|
} else {
|
|
throw Error("geometry error, GPU Instancing is not supported on this device");
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
draw(topology, size, start, instanceCount) {
|
|
const {gl} = this._renderer, geometry = this._activeGeometry;
|
|
topology = topologyToGlMap[topology || geometry.topology];
|
|
instanceCount ?? (instanceCount = geometry.instanceCount);
|
|
if (geometry.indexBuffer) {
|
|
const byteSize = geometry.indexBuffer.data.BYTES_PER_ELEMENT, glType = 2 === byteSize ? gl.UNSIGNED_SHORT : gl.UNSIGNED_INT;
|
|
1 !== instanceCount ? gl.drawElementsInstanced(topology, size || geometry.indexBuffer.data.length, glType, (start || 0) * byteSize, instanceCount) : gl.drawElements(topology, size || geometry.indexBuffer.data.length, glType, (start || 0) * byteSize);
|
|
} else {
|
|
1 !== instanceCount ? gl.drawArraysInstanced(topology, start || 0, size || geometry.getSize(), instanceCount) : gl.drawArrays(topology, start || 0, size || geometry.getSize());
|
|
}
|
|
return this;
|
|
}
|
|
unbind() {
|
|
this.gl.bindVertexArray(null);
|
|
this._activeGeometry = this._activeVao = null;
|
|
}
|
|
destroy() {
|
|
this._managedGeometries.destroy();
|
|
this._activeGeometry = this._activeVao = this.gl = this._renderer = null;
|
|
}
|
|
}
|
|
GlGeometrySystem.extension = {type:[global.ExtensionType.WebGLSystem], name:"geometry"};
|
|
exports.GlGeometryGpuData = GlGeometryGpuData;
|
|
exports.GlGeometrySystem = GlGeometrySystem;
|
|
};
|
|
|
|
//# sourceMappingURL=module$node_modules$pixi_DOT_js$lib$rendering$renderers$gl$geometry$GlGeometrySystem.js.map
|