Skip to content

Commit

Permalink
feat: add support for WEBGL_draw_instanced_base_vertex_base_instance …
Browse files Browse the repository at this point in the history
…and drawArrays for WEBGL_multi_draw_instanced_base_vertex_base_instance

- add drawInstancedBase to capabilities
- move multiDrawInstancedBase to capabilities

Related #133
  • Loading branch information
dmnsgn committed Feb 21, 2023
1 parent b515fd7 commit 224ee99
Show file tree
Hide file tree
Showing 2 changed files with 106 additions and 33 deletions.
12 changes: 8 additions & 4 deletions examples/multi-draw-instanced.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
//Requires: WEBGL_multi_draw
//Requires: WEBGL_multi_draw_instanced_base_vertex_base_instance
import createContext from "../index.js";

import { perspective as createCamera, orbiter as createOrbiter } from "pex-cam";
Expand All @@ -12,6 +10,12 @@ import basicFrag from "./shaders/basic.frag.js";

const ctx = createContext({ pixelRatio: devicePixelRatio });

if (!ctx.capabilities.multiDrawInstancedBase) {
const message = `Unsupported extension "WEBGL_multi_draw_instanced_base_vertex_base_instance"`;
document.body.textContent = message;
throw new Error(message);
}

const CellsConstructor = Uint16Array;

const sphereGeometry = sphere({ radius: 0.2 });
Expand Down Expand Up @@ -114,8 +118,8 @@ void main () {
counts,
offsets,
instanceCounts,
baseVertices: baseVertices,
baseInstances: baseInstances,
baseVertices,
baseInstances,
},
uniforms: {
uProjectionMatrix: camera.projectionMatrix,
Expand Down
127 changes: 98 additions & 29 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,12 @@ function createContext(options = {}) {
: !!gl.getExtension("WEBGL_color_buffer_float"),
colorBufferHalfFloat: !!gl.getExtension("EXT_color_buffer_half_float"),
multiDraw: !!gl.getExtension("WEBGL_multi_draw"),
drawInstancedBase: !!gl.getExtension(
"WEBGL_draw_instanced_base_vertex_base_instance"
),
multiDrawInstancedBase: !!gl.getExtension(
"WEBGL_multi_draw_instanced_base_vertex_base_instance"
),
},
/**
* Getter for `gl.drawingBufferWidth`
Expand Down Expand Up @@ -1081,6 +1087,7 @@ function createContext(options = {}) {

const primitive = cmd.pipeline.primitive;

// Draw elements/arrays, instanced, base, multi-draw
if (cmd.indices || cmd.vertexArray?.indices) {
// TODO: is that always correct
const count = cmd.count || this.state.indexBuffer.length;
Expand All @@ -1093,18 +1100,16 @@ function createContext(options = {}) {

if (instanced) {
if (cmd.multiDraw && ctx.capabilities.multiDraw) {
const ext = gl.getExtension("WEBGL_multi_draw");

if (cmd.multiDraw.baseVertices && cmd.multiDraw.baseInstances) {
const baseVertexBaseInstanceExt = gl.getExtension(
if (
cmd.multiDraw.baseVertices &&
cmd.multiDraw.baseInstances &&
ctx.capabilities.multiDrawInstancedBase
) {
const ext = gl.getExtension(
"WEBGL_multi_draw_instanced_base_vertex_base_instance"
);
if (!baseVertexBaseInstanceExt) {
throw new Error(
"WEBGL_multi_draw_instanced_base_vertex_base_instance not supported"
);
}
baseVertexBaseInstanceExt.multiDrawElementsInstancedBaseVertexBaseInstanceWEBGL(

ext.multiDrawElementsInstancedBaseVertexBaseInstanceWEBGL(
primitive,
cmd.multiDraw.counts,
cmd.multiDraw.countsOffset || 0,
Expand All @@ -1120,6 +1125,8 @@ function createContext(options = {}) {
cmd.multiDraw.counts.length
);
} else {
const ext = gl.getExtension("WEBGL_multi_draw");

ext.multiDrawElementsInstancedWEBGL(
primitive,
cmd.multiDraw.counts,
Expand All @@ -1133,13 +1140,32 @@ function createContext(options = {}) {
);
}
} else {
gl.drawElementsInstanced(
primitive,
count,
type,
offset,
cmd.instances
);
if (
Number.isFinite(cmd.baseVertex) &&
Number.isFinite(cmd.baseInstance) &&
ctx.capabilities.drawInstancedBase
) {
const ext = gl.getExtension(
"WEBGL_draw_instanced_base_vertex_base_instance"
);
ext.drawElementsInstancedBaseVertexBaseInstanceWEBGL(
primitive,
count,
type,
offset,
cmd.instances,
cmd.baseVertex,
cmd.baseInstance
);
} else {
gl.drawElementsInstanced(
primitive,
count,
type,
offset,
cmd.instances
);
}
}
} else {
if (cmd.multiDraw && ctx.capabilities.multiDraw) {
Expand All @@ -1161,19 +1187,62 @@ function createContext(options = {}) {
const first = 0;
if (instanced) {
if (cmd.multiDraw && ctx.capabilities.multiDraw) {
const ext = gl.getExtension("WEBGL_multi_draw");
ext.multiDrawArraysInstancedWEBGL(
primitive,
cmd.multiDraw.firsts,
cmd.multiDraw.firstsOffset || 0,
cmd.multiDraw.counts,
cmd.multiDraw.countsOffset || 0,
cmd.multiDraw.instanceCounts,
cmd.multiDraw.instanceCountsOffset || 0,
cmd.multiDraw.firsts.length
);
if (
cmd.multiDraw.baseInstances &&
ctx.capabilities.multiDrawInstancedBase
) {
const ext = gl.getExtension(
"WEBGL_multi_draw_instanced_base_vertex_base_instance"
);

ext.multiDrawArraysInstancedBaseInstanceWEBGL(
primitive,
cmd.multiDraw.firsts,
cmd.multiDraw.firstsOffset || 0,
cmd.multiDraw.counts,
cmd.multiDraw.countsOffset || 0,
cmd.multiDraw.instanceCounts,
cmd.multiDraw.instanceCountsOffset || 0,
cmd.multiDraw.baseInstances,
cmd.multiDraw.baseInstancesOffset || 0,
cmd.multiDraw.firsts.length
);
} else {
const ext = gl.getExtension("WEBGL_multi_draw");
ext.multiDrawArraysInstancedWEBGL(
primitive,
cmd.multiDraw.firsts,
cmd.multiDraw.firstsOffset || 0,
cmd.multiDraw.counts,
cmd.multiDraw.countsOffset || 0,
cmd.multiDraw.instanceCounts,
cmd.multiDraw.instanceCountsOffset || 0,
cmd.multiDraw.firsts.length
);
}
} else {
gl.drawArraysInstanced(primitive, first, cmd.count, cmd.instances);
if (
Number.isFinite(cmd.baseInstance) &&
ctx.capabilities.drawInstancedBase
) {
const ext = gl.getExtension(
"WEBGL_draw_instanced_base_vertex_base_instance"
);
ext.drawArraysInstancedBaseInstanceWEBGL(
primitive,
first,
cmd.count,
cmd.instances,
cmd.baseInstance
);
} else {
gl.drawArraysInstanced(
primitive,
first,
cmd.count,
cmd.instances
);
}
}
} else {
if (cmd.multiDraw && ctx.capabilities.multiDraw) {
Expand Down

0 comments on commit 224ee99

Please sign in to comment.