@luma.gl/webgl 9.2.6 → 9.3.0-alpha.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/adapter/converters/device-parameters.d.ts +1 -1
- package/dist/adapter/converters/device-parameters.d.ts.map +1 -1
- package/dist/adapter/converters/device-parameters.js +4 -1
- package/dist/adapter/converters/device-parameters.js.map +1 -1
- package/dist/adapter/converters/sampler-parameters.d.ts +1 -1
- package/dist/adapter/converters/sampler-parameters.d.ts.map +1 -1
- package/dist/adapter/converters/sampler-parameters.js +1 -1
- package/dist/adapter/converters/sampler-parameters.js.map +1 -1
- package/dist/adapter/converters/shader-formats.d.ts +1 -64
- package/dist/adapter/converters/shader-formats.d.ts.map +1 -1
- package/dist/adapter/converters/shader-formats.js +1 -64
- package/dist/adapter/converters/shader-formats.js.map +1 -1
- package/dist/adapter/converters/webgl-shadertypes.d.ts +1 -3
- package/dist/adapter/converters/webgl-shadertypes.d.ts.map +1 -1
- package/dist/adapter/converters/webgl-shadertypes.js +1 -6
- package/dist/adapter/converters/webgl-shadertypes.js.map +1 -1
- package/dist/adapter/converters/webgl-texture-table.d.ts +8 -4
- package/dist/adapter/converters/webgl-texture-table.d.ts.map +1 -1
- package/dist/adapter/converters/webgl-texture-table.js +122 -58
- package/dist/adapter/converters/webgl-texture-table.js.map +1 -1
- package/dist/adapter/converters/webgl-vertex-formats.d.ts +1 -1
- package/dist/adapter/converters/webgl-vertex-formats.d.ts.map +1 -1
- package/dist/adapter/converters/webgl-vertex-formats.js +1 -1
- package/dist/adapter/converters/webgl-vertex-formats.js.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-features.d.ts +1 -1
- package/dist/adapter/device-helpers/webgl-device-features.d.ts.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-features.js +1 -2
- package/dist/adapter/device-helpers/webgl-device-features.js.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-info.d.ts +1 -1
- package/dist/adapter/device-helpers/webgl-device-info.d.ts.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-info.js +6 -1
- package/dist/adapter/device-helpers/webgl-device-info.js.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-limits.d.ts +1 -1
- package/dist/adapter/device-helpers/webgl-device-limits.d.ts.map +1 -1
- package/dist/adapter/device-helpers/webgl-device-limits.js +1 -1
- package/dist/adapter/device-helpers/webgl-device-limits.js.map +1 -1
- package/dist/adapter/helpers/format-utils.d.ts +1 -1
- package/dist/adapter/helpers/format-utils.d.ts.map +1 -1
- package/dist/adapter/helpers/format-utils.js +1 -1
- package/dist/adapter/helpers/format-utils.js.map +1 -1
- package/dist/adapter/helpers/get-shader-layout-from-glsl.js +36 -22
- package/dist/adapter/helpers/get-shader-layout-from-glsl.js.map +1 -1
- package/dist/adapter/helpers/parse-shader-compiler-log.d.ts +1 -1
- package/dist/adapter/helpers/parse-shader-compiler-log.d.ts.map +1 -1
- package/dist/adapter/helpers/parse-shader-compiler-log.js +20 -0
- package/dist/adapter/helpers/parse-shader-compiler-log.js.map +1 -1
- package/dist/adapter/helpers/set-uniform.d.ts +1 -1
- package/dist/adapter/helpers/set-uniform.d.ts.map +1 -1
- package/dist/adapter/helpers/set-uniform.js +1 -1
- package/dist/adapter/helpers/set-uniform.js.map +1 -1
- package/dist/adapter/helpers/webgl-texture-utils.d.ts +1 -1
- package/dist/adapter/helpers/webgl-texture-utils.d.ts.map +1 -1
- package/dist/adapter/helpers/webgl-texture-utils.js +4 -4
- package/dist/adapter/helpers/webgl-texture-utils.js.map +1 -1
- package/dist/adapter/helpers/webgl-topology-utils.d.ts +1 -1
- package/dist/adapter/helpers/webgl-topology-utils.d.ts.map +1 -1
- package/dist/adapter/helpers/webgl-topology-utils.js +1 -1
- package/dist/adapter/helpers/webgl-topology-utils.js.map +1 -1
- package/dist/adapter/resources/webgl-buffer.d.ts +1 -1
- package/dist/adapter/resources/webgl-buffer.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-buffer.js +20 -5
- package/dist/adapter/resources/webgl-buffer.js.map +1 -1
- package/dist/adapter/resources/webgl-command-buffer.d.ts +3 -4
- package/dist/adapter/resources/webgl-command-buffer.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-command-buffer.js +29 -39
- package/dist/adapter/resources/webgl-command-buffer.js.map +1 -1
- package/dist/adapter/resources/webgl-command-encoder.d.ts +6 -5
- package/dist/adapter/resources/webgl-command-encoder.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-command-encoder.js +23 -8
- package/dist/adapter/resources/webgl-command-encoder.js.map +1 -1
- package/dist/adapter/resources/webgl-fence.d.ts +14 -0
- package/dist/adapter/resources/webgl-fence.d.ts.map +1 -0
- package/dist/adapter/resources/webgl-fence.js +49 -0
- package/dist/adapter/resources/webgl-fence.js.map +1 -0
- package/dist/adapter/resources/webgl-framebuffer.d.ts +3 -1
- package/dist/adapter/resources/webgl-framebuffer.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-framebuffer.js +10 -1
- package/dist/adapter/resources/webgl-framebuffer.js.map +1 -1
- package/dist/adapter/resources/webgl-query-set.d.ts +37 -31
- package/dist/adapter/resources/webgl-query-set.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-query-set.js +247 -96
- package/dist/adapter/resources/webgl-query-set.js.map +1 -1
- package/dist/adapter/resources/webgl-render-pass.d.ts +1 -1
- package/dist/adapter/resources/webgl-render-pass.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-render-pass.js +28 -11
- package/dist/adapter/resources/webgl-render-pass.js.map +1 -1
- package/dist/adapter/resources/webgl-render-pipeline.d.ts +17 -21
- package/dist/adapter/resources/webgl-render-pipeline.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-render-pipeline.js +70 -169
- package/dist/adapter/resources/webgl-render-pipeline.js.map +1 -1
- package/dist/adapter/resources/webgl-sampler.d.ts +1 -1
- package/dist/adapter/resources/webgl-sampler.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-sampler.js +1 -1
- package/dist/adapter/resources/webgl-sampler.js.map +1 -1
- package/dist/adapter/resources/webgl-shader.d.ts +1 -1
- package/dist/adapter/resources/webgl-shader.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-shader.js +15 -8
- package/dist/adapter/resources/webgl-shader.js.map +1 -1
- package/dist/adapter/resources/webgl-shared-render-pipeline.d.ts +24 -0
- package/dist/adapter/resources/webgl-shared-render-pipeline.d.ts.map +1 -0
- package/dist/adapter/resources/webgl-shared-render-pipeline.js +155 -0
- package/dist/adapter/resources/webgl-shared-render-pipeline.js.map +1 -0
- package/dist/adapter/resources/webgl-texture.d.ts +42 -4
- package/dist/adapter/resources/webgl-texture.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-texture.js +286 -62
- package/dist/adapter/resources/webgl-texture.js.map +1 -1
- package/dist/adapter/resources/webgl-transform-feedback.js +6 -6
- package/dist/adapter/resources/webgl-transform-feedback.js.map +1 -1
- package/dist/adapter/resources/webgl-vertex-array.d.ts +2 -2
- package/dist/adapter/resources/webgl-vertex-array.d.ts.map +1 -1
- package/dist/adapter/resources/webgl-vertex-array.js +1 -1
- package/dist/adapter/resources/webgl-vertex-array.js.map +1 -1
- package/dist/adapter/webgl-adapter.d.ts.map +1 -1
- package/dist/adapter/webgl-adapter.js +22 -23
- package/dist/adapter/webgl-adapter.js.map +1 -1
- package/dist/adapter/webgl-canvas-context.d.ts +2 -2
- package/dist/adapter/webgl-canvas-context.d.ts.map +1 -1
- package/dist/adapter/webgl-canvas-context.js +16 -6
- package/dist/adapter/webgl-canvas-context.js.map +1 -1
- package/dist/adapter/webgl-device.d.ts +10 -5
- package/dist/adapter/webgl-device.d.ts.map +1 -1
- package/dist/adapter/webgl-device.js +75 -28
- package/dist/adapter/webgl-device.js.map +1 -1
- package/dist/adapter/webgl-presentation-context.d.ts +21 -0
- package/dist/adapter/webgl-presentation-context.d.ts.map +1 -0
- package/dist/adapter/webgl-presentation-context.js +64 -0
- package/dist/adapter/webgl-presentation-context.js.map +1 -0
- package/dist/constants/index.d.ts +3 -0
- package/dist/constants/index.d.ts.map +1 -0
- package/dist/constants/index.js +5 -0
- package/dist/constants/index.js.map +1 -0
- package/dist/constants/webgl-constants.d.ts +822 -0
- package/dist/constants/webgl-constants.d.ts.map +1 -0
- package/dist/constants/webgl-constants.js +928 -0
- package/dist/constants/webgl-constants.js.map +1 -0
- package/dist/constants/webgl-types.d.ts +480 -0
- package/dist/constants/webgl-types.d.ts.map +1 -0
- package/dist/constants/webgl-types.js +6 -0
- package/dist/constants/webgl-types.js.map +1 -0
- package/dist/context/debug/spector.d.ts.map +1 -1
- package/dist/context/debug/spector.js +4 -4
- package/dist/context/debug/spector.js.map +1 -1
- package/dist/context/debug/webgl-developer-tools.js +7 -7
- package/dist/context/debug/webgl-developer-tools.js.map +1 -1
- package/dist/context/helpers/create-browser-context.d.ts.map +1 -1
- package/dist/context/helpers/create-browser-context.js +46 -36
- package/dist/context/helpers/create-browser-context.js.map +1 -1
- package/dist/context/helpers/webgl-context-data.d.ts +5 -1
- package/dist/context/helpers/webgl-context-data.d.ts.map +1 -1
- package/dist/context/helpers/webgl-context-data.js +9 -10
- package/dist/context/helpers/webgl-context-data.js.map +1 -1
- package/dist/context/helpers/webgl-extensions.d.ts +1 -1
- package/dist/context/helpers/webgl-extensions.d.ts.map +1 -1
- package/dist/context/parameters/unified-parameter-api.d.ts +2 -2
- package/dist/context/parameters/unified-parameter-api.d.ts.map +1 -1
- package/dist/context/parameters/unified-parameter-api.js +2 -2
- package/dist/context/parameters/unified-parameter-api.js.map +1 -1
- package/dist/context/parameters/webgl-parameter-tables.d.ts +1 -1
- package/dist/context/parameters/webgl-parameter-tables.d.ts.map +1 -1
- package/dist/context/parameters/webgl-parameter-tables.js +1 -1
- package/dist/context/parameters/webgl-parameter-tables.js.map +1 -1
- package/dist/context/polyfills/polyfill-webgl1-extensions.js +1 -1
- package/dist/context/polyfills/polyfill-webgl1-extensions.js.map +1 -1
- package/dist/context/state-tracker/webgl-state-tracker.js +2 -2
- package/dist/context/state-tracker/webgl-state-tracker.js.map +1 -1
- package/dist/dist.dev.js +1897 -999
- package/dist/dist.min.js +2 -2
- package/dist/index.cjs +3 -5255
- package/dist/index.cjs.map +4 -4
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -0
- package/dist/index.js.map +1 -1
- package/dist/utils/fill-array.js +1 -1
- package/dist/utils/fill-array.js.map +1 -1
- package/dist/webgl-constants.d.ts +2 -0
- package/dist/webgl-constants.d.ts.map +1 -0
- package/dist/webgl-constants.js +5 -0
- package/dist/webgl-constants.js.map +1 -0
- package/dist/webgl-types.d.ts +2 -0
- package/dist/webgl-types.d.ts.map +1 -0
- package/dist/{types.js → webgl-types.js} +1 -1
- package/dist/webgl-types.js.map +1 -0
- package/package.json +19 -5
- package/src/adapter/converters/device-parameters.ts +6 -2
- package/src/adapter/converters/sampler-parameters.ts +1 -1
- package/src/adapter/converters/shader-formats.ts +1 -66
- package/src/adapter/converters/webgl-shadertypes.ts +1 -9
- package/src/adapter/converters/webgl-texture-table.ts +160 -68
- package/src/adapter/converters/webgl-vertex-formats.ts +1 -1
- package/src/adapter/device-helpers/webgl-device-features.ts +2 -3
- package/src/adapter/device-helpers/webgl-device-info.ts +7 -1
- package/src/adapter/device-helpers/webgl-device-limits.ts +1 -1
- package/src/adapter/helpers/format-utils.ts +1 -1
- package/src/adapter/helpers/get-shader-layout-from-glsl.ts +44 -24
- package/src/adapter/helpers/parse-shader-compiler-log.ts +23 -1
- package/src/adapter/helpers/set-uniform.ts +1 -1
- package/src/adapter/helpers/webgl-texture-utils.ts +4 -4
- package/src/adapter/helpers/webgl-topology-utils.ts +1 -1
- package/src/adapter/resources/webgl-buffer.ts +17 -5
- package/src/adapter/resources/webgl-command-buffer.ts +44 -48
- package/src/adapter/resources/webgl-command-encoder.ts +28 -11
- package/src/adapter/resources/webgl-fence.ts +55 -0
- package/src/adapter/resources/webgl-framebuffer.ts +12 -1
- package/src/adapter/resources/webgl-query-set.ts +295 -101
- package/src/adapter/resources/webgl-render-pass.ts +30 -13
- package/src/adapter/resources/webgl-render-pipeline.ts +102 -198
- package/src/adapter/resources/webgl-sampler.ts +1 -1
- package/src/adapter/resources/webgl-shader.ts +15 -8
- package/src/adapter/resources/webgl-shared-render-pipeline.ts +211 -0
- package/src/adapter/resources/webgl-texture.ts +455 -81
- package/src/adapter/resources/webgl-transform-feedback.ts +6 -6
- package/src/adapter/resources/webgl-vertex-array.ts +1 -1
- package/src/adapter/webgl-adapter.ts +26 -24
- package/src/adapter/webgl-canvas-context.ts +19 -8
- package/src/adapter/webgl-device.ts +91 -35
- package/src/adapter/webgl-presentation-context.ts +93 -0
- package/src/constants/index.d.ts.map +1 -0
- package/src/constants/index.js.map +1 -0
- package/src/constants/index.ts +31 -0
- package/src/constants/webgl-constants.d.ts.map +1 -0
- package/src/constants/webgl-constants.js.map +1 -0
- package/src/constants/webgl-constants.ts +1051 -0
- package/src/constants/webgl-types.d.ts.map +1 -0
- package/src/constants/webgl-types.js.map +1 -0
- package/src/constants/webgl-types.ts +813 -0
- package/src/context/debug/spector.ts +4 -4
- package/src/context/debug/webgl-developer-tools.ts +16 -7
- package/src/context/helpers/create-browser-context.ts +54 -43
- package/src/context/helpers/webgl-context-data.ts +17 -11
- package/src/context/helpers/webgl-extensions.ts +1 -1
- package/src/context/parameters/unified-parameter-api.ts +3 -3
- package/src/context/parameters/webgl-parameter-tables.ts +1 -1
- package/src/context/polyfills/polyfill-webgl1-extensions.ts +1 -1
- package/src/context/state-tracker/webgl-state-tracker.ts +2 -2
- package/src/index.ts +27 -0
- package/src/utils/fill-array.ts +1 -1
- package/src/webgl-constants.d.ts.map +1 -0
- package/src/webgl-constants.js.map +1 -0
- package/src/webgl-constants.ts +5 -0
- package/src/webgl-types.d.ts.map +1 -0
- package/src/webgl-types.js.map +1 -0
- package/src/webgl-types.ts +29 -0
- package/dist/types.d.ts +0 -11
- package/dist/types.d.ts.map +0 -1
- package/dist/types.js.map +0 -1
- package/src/types.ts +0 -14
|
@@ -1,175 +1,369 @@
|
|
|
1
|
-
// WebGL2
|
|
1
|
+
// WebGL2 QuerySet (also handles disjoint timer extensions)
|
|
2
2
|
import {QuerySet, QuerySetProps} from '@luma.gl/core';
|
|
3
|
-
import {GL} from '@luma.gl/constants';
|
|
3
|
+
import {GL} from '@luma.gl/webgl/constants';
|
|
4
4
|
import {WebGLDevice} from '../webgl-device';
|
|
5
5
|
|
|
6
|
+
type WebGLPendingQuery = {
|
|
7
|
+
handle: WebGLQuery;
|
|
8
|
+
promise: Promise<bigint> | null;
|
|
9
|
+
result: bigint | null;
|
|
10
|
+
disjoint: boolean;
|
|
11
|
+
cancelled: boolean;
|
|
12
|
+
pollRequestId: number | null;
|
|
13
|
+
resolve: ((value: bigint) => void) | null;
|
|
14
|
+
reject: ((error: Error) => void) | null;
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
type WebGLTimestampPair = {
|
|
18
|
+
activeQuery: WebGLPendingQuery | null;
|
|
19
|
+
completedQueries: WebGLPendingQuery[];
|
|
20
|
+
};
|
|
21
|
+
|
|
6
22
|
/**
|
|
7
23
|
* Asynchronous queries for different kinds of information
|
|
8
24
|
*/
|
|
9
25
|
export class WEBGLQuerySet extends QuerySet {
|
|
10
26
|
readonly device: WebGLDevice;
|
|
11
|
-
readonly handle: WebGLQuery;
|
|
27
|
+
readonly handle: WebGLQuery | null;
|
|
12
28
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
29
|
+
protected _timestampPairs: WebGLTimestampPair[] = [];
|
|
30
|
+
protected _pendingReads: Set<WebGLPendingQuery> = new Set();
|
|
31
|
+
protected _occlusionQuery: WebGLPendingQuery | null = null;
|
|
32
|
+
protected _occlusionActive = false;
|
|
16
33
|
|
|
17
34
|
override get [Symbol.toStringTag](): string {
|
|
18
|
-
return '
|
|
35
|
+
return 'QuerySet';
|
|
19
36
|
}
|
|
20
37
|
|
|
21
|
-
// Create a query class
|
|
22
38
|
constructor(device: WebGLDevice, props: QuerySetProps) {
|
|
23
39
|
super(device, props);
|
|
24
40
|
this.device = device;
|
|
25
41
|
|
|
26
|
-
if (props.
|
|
27
|
-
|
|
42
|
+
if (props.type === 'timestamp') {
|
|
43
|
+
if (props.count < 2) {
|
|
44
|
+
throw new Error('Timestamp QuerySet requires at least two query slots');
|
|
45
|
+
}
|
|
46
|
+
this._timestampPairs = new Array(Math.ceil(props.count / 2))
|
|
47
|
+
.fill(null)
|
|
48
|
+
.map(() => ({activeQuery: null, completedQueries: []}));
|
|
49
|
+
this.handle = null;
|
|
50
|
+
} else {
|
|
51
|
+
if (props.count > 1) {
|
|
52
|
+
throw new Error('WebGL occlusion QuerySet can only have one value');
|
|
53
|
+
}
|
|
54
|
+
const handle = this.device.gl.createQuery();
|
|
55
|
+
if (!handle) {
|
|
56
|
+
throw new Error('WebGL query not supported');
|
|
57
|
+
}
|
|
58
|
+
this.handle = handle;
|
|
28
59
|
}
|
|
29
60
|
|
|
30
|
-
const handle = this.device.gl.createQuery();
|
|
31
|
-
if (!handle) {
|
|
32
|
-
throw new Error('WebGL query not supported');
|
|
33
|
-
}
|
|
34
|
-
this.handle = handle;
|
|
35
61
|
Object.seal(this);
|
|
36
62
|
}
|
|
37
63
|
|
|
38
|
-
override destroy() {
|
|
39
|
-
|
|
40
|
-
|
|
64
|
+
override destroy(): void {
|
|
65
|
+
if (this.destroyed) {
|
|
66
|
+
return;
|
|
67
|
+
}
|
|
41
68
|
|
|
42
|
-
|
|
69
|
+
if (this.handle) {
|
|
70
|
+
this.device.gl.deleteQuery(this.handle);
|
|
71
|
+
}
|
|
43
72
|
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
73
|
+
for (const pair of this._timestampPairs) {
|
|
74
|
+
if (pair.activeQuery) {
|
|
75
|
+
this._cancelPendingQuery(pair.activeQuery);
|
|
76
|
+
this.device.gl.deleteQuery(pair.activeQuery.handle);
|
|
77
|
+
}
|
|
78
|
+
for (const query of pair.completedQueries) {
|
|
79
|
+
this._cancelPendingQuery(query);
|
|
80
|
+
this.device.gl.deleteQuery(query.handle);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
52
83
|
|
|
53
|
-
|
|
54
|
-
|
|
84
|
+
if (this._occlusionQuery) {
|
|
85
|
+
this._cancelPendingQuery(this._occlusionQuery);
|
|
86
|
+
this.device.gl.deleteQuery(this._occlusionQuery.handle);
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
for (const query of Array.from(this._pendingReads)) {
|
|
90
|
+
this._cancelPendingQuery(query);
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
this.destroyResource();
|
|
55
94
|
}
|
|
56
95
|
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
96
|
+
isResultAvailable(queryIndex?: number): boolean {
|
|
97
|
+
if (this.props.type === 'timestamp') {
|
|
98
|
+
if (queryIndex === undefined) {
|
|
99
|
+
return this._timestampPairs.some((_, pairIndex) =>
|
|
100
|
+
this._isTimestampPairAvailable(pairIndex)
|
|
101
|
+
);
|
|
102
|
+
}
|
|
103
|
+
return this._isTimestampPairAvailable(this._getTimestampPairIndex(queryIndex));
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
if (!this._occlusionQuery) {
|
|
107
|
+
return false;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
return this._pollQueryAvailability(this._occlusionQuery);
|
|
62
111
|
}
|
|
63
112
|
|
|
64
|
-
|
|
65
|
-
|
|
113
|
+
async readResults(options?: {firstQuery?: number; queryCount?: number}): Promise<bigint[]> {
|
|
114
|
+
const firstQuery = options?.firstQuery || 0;
|
|
115
|
+
const queryCount = options?.queryCount || this.props.count - firstQuery;
|
|
116
|
+
this._validateRange(firstQuery, queryCount);
|
|
117
|
+
|
|
118
|
+
if (this.props.type === 'timestamp') {
|
|
119
|
+
const results = new Array<bigint>(queryCount).fill(0n);
|
|
120
|
+
const startPairIndex = Math.floor(firstQuery / 2);
|
|
121
|
+
const endPairIndex = Math.floor((firstQuery + queryCount - 1) / 2);
|
|
122
|
+
|
|
123
|
+
for (let pairIndex = startPairIndex; pairIndex <= endPairIndex; pairIndex++) {
|
|
124
|
+
const duration = await this._consumeTimestampPairResult(pairIndex);
|
|
125
|
+
const beginSlot = pairIndex * 2;
|
|
126
|
+
const endSlot = beginSlot + 1;
|
|
127
|
+
|
|
128
|
+
if (beginSlot >= firstQuery && beginSlot < firstQuery + queryCount) {
|
|
129
|
+
results[beginSlot - firstQuery] = 0n;
|
|
130
|
+
}
|
|
131
|
+
if (endSlot >= firstQuery && endSlot < firstQuery + queryCount) {
|
|
132
|
+
results[endSlot - firstQuery] = duration;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
return results;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
if (!this._occlusionQuery) {
|
|
140
|
+
throw new Error('Occlusion query has not been started');
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
return [await this._consumeQueryResult(this._occlusionQuery)];
|
|
66
144
|
}
|
|
67
145
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
146
|
+
async readTimestampDuration(beginIndex: number, endIndex: number): Promise<number> {
|
|
147
|
+
if (this.props.type !== 'timestamp') {
|
|
148
|
+
throw new Error('Timestamp durations require a timestamp QuerySet');
|
|
149
|
+
}
|
|
150
|
+
if (beginIndex < 0 || endIndex >= this.props.count || endIndex <= beginIndex) {
|
|
151
|
+
throw new Error('Timestamp duration range is out of bounds');
|
|
152
|
+
}
|
|
153
|
+
if (beginIndex % 2 !== 0 || endIndex !== beginIndex + 1) {
|
|
154
|
+
throw new Error('WebGL timestamp durations require adjacent even/odd query indices');
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const result = await this._consumeTimestampPairResult(this._getTimestampPairIndex(beginIndex));
|
|
158
|
+
return Number(result) / 1e6;
|
|
71
159
|
}
|
|
72
160
|
|
|
73
|
-
|
|
74
|
-
this.
|
|
161
|
+
beginOcclusionQuery(): void {
|
|
162
|
+
if (this.props.type !== 'occlusion') {
|
|
163
|
+
throw new Error('Occlusion queries require an occlusion QuerySet');
|
|
164
|
+
}
|
|
165
|
+
if (!this.handle) {
|
|
166
|
+
throw new Error('WebGL occlusion query is not available');
|
|
167
|
+
}
|
|
168
|
+
if (this._occlusionActive) {
|
|
169
|
+
throw new Error('Occlusion query is already active');
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
this.device.gl.beginQuery(GL.ANY_SAMPLES_PASSED, this.handle);
|
|
173
|
+
this._occlusionQuery = {
|
|
174
|
+
handle: this.handle,
|
|
175
|
+
promise: null,
|
|
176
|
+
result: null,
|
|
177
|
+
disjoint: false,
|
|
178
|
+
cancelled: false,
|
|
179
|
+
pollRequestId: null,
|
|
180
|
+
resolve: null,
|
|
181
|
+
reject: null
|
|
182
|
+
};
|
|
183
|
+
this._occlusionActive = true;
|
|
75
184
|
}
|
|
76
185
|
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
186
|
+
endOcclusionQuery(): void {
|
|
187
|
+
if (!this._occlusionActive) {
|
|
188
|
+
throw new Error('Occlusion query is not active');
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
this.device.gl.endQuery(GL.ANY_SAMPLES_PASSED);
|
|
192
|
+
this._occlusionActive = false;
|
|
80
193
|
}
|
|
81
194
|
|
|
82
|
-
|
|
195
|
+
writeTimestamp(queryIndex: number): void {
|
|
196
|
+
if (this.props.type !== 'timestamp') {
|
|
197
|
+
throw new Error('Timestamp writes require a timestamp QuerySet');
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
const pairIndex = this._getTimestampPairIndex(queryIndex);
|
|
201
|
+
const pair = this._timestampPairs[pairIndex];
|
|
202
|
+
|
|
203
|
+
if (queryIndex % 2 === 0) {
|
|
204
|
+
if (pair.activeQuery) {
|
|
205
|
+
throw new Error('Timestamp query pair is already active');
|
|
206
|
+
}
|
|
83
207
|
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
208
|
+
const handle = this.device.gl.createQuery();
|
|
209
|
+
if (!handle) {
|
|
210
|
+
throw new Error('WebGL query not supported');
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
const query: WebGLPendingQuery = {
|
|
214
|
+
handle,
|
|
215
|
+
promise: null,
|
|
216
|
+
result: null,
|
|
217
|
+
disjoint: false,
|
|
218
|
+
cancelled: false,
|
|
219
|
+
pollRequestId: null,
|
|
220
|
+
resolve: null,
|
|
221
|
+
reject: null
|
|
222
|
+
};
|
|
223
|
+
|
|
224
|
+
this.device.gl.beginQuery(GL.TIME_ELAPSED_EXT, handle);
|
|
225
|
+
pair.activeQuery = query;
|
|
94
226
|
return;
|
|
95
227
|
}
|
|
96
228
|
|
|
97
|
-
|
|
98
|
-
|
|
229
|
+
if (!pair.activeQuery) {
|
|
230
|
+
throw new Error('Timestamp query pair was ended before it was started');
|
|
231
|
+
}
|
|
99
232
|
|
|
100
|
-
|
|
233
|
+
this.device.gl.endQuery(GL.TIME_ELAPSED_EXT);
|
|
234
|
+
pair.completedQueries.push(pair.activeQuery);
|
|
235
|
+
pair.activeQuery = null;
|
|
101
236
|
}
|
|
102
237
|
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
if (this._queryPending) {
|
|
107
|
-
return;
|
|
238
|
+
protected _validateRange(firstQuery: number, queryCount: number): void {
|
|
239
|
+
if (firstQuery < 0 || queryCount < 0 || firstQuery + queryCount > this.props.count) {
|
|
240
|
+
throw new Error('Query read range is out of bounds');
|
|
108
241
|
}
|
|
242
|
+
}
|
|
109
243
|
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
this._queryPending = true;
|
|
244
|
+
protected _getTimestampPairIndex(queryIndex: number): number {
|
|
245
|
+
if (queryIndex < 0 || queryIndex >= this.props.count) {
|
|
246
|
+
throw new Error('Query index is out of bounds');
|
|
114
247
|
}
|
|
115
|
-
|
|
248
|
+
|
|
249
|
+
return Math.floor(queryIndex / 2);
|
|
116
250
|
}
|
|
117
251
|
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
if (!
|
|
252
|
+
protected _isTimestampPairAvailable(pairIndex: number): boolean {
|
|
253
|
+
const pair = this._timestampPairs[pairIndex];
|
|
254
|
+
if (!pair || pair.completedQueries.length === 0) {
|
|
121
255
|
return false;
|
|
122
256
|
}
|
|
123
257
|
|
|
258
|
+
return this._pollQueryAvailability(pair.completedQueries[0]);
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
protected _pollQueryAvailability(query: WebGLPendingQuery): boolean {
|
|
262
|
+
if (query.cancelled || this.destroyed) {
|
|
263
|
+
query.result = 0n;
|
|
264
|
+
return true;
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
if (query.result !== null || query.disjoint) {
|
|
268
|
+
return true;
|
|
269
|
+
}
|
|
270
|
+
|
|
124
271
|
const resultAvailable = this.device.gl.getQueryParameter(
|
|
125
|
-
|
|
272
|
+
query.handle,
|
|
126
273
|
GL.QUERY_RESULT_AVAILABLE
|
|
127
274
|
);
|
|
128
|
-
if (resultAvailable) {
|
|
129
|
-
|
|
275
|
+
if (!resultAvailable) {
|
|
276
|
+
return false;
|
|
130
277
|
}
|
|
131
|
-
return resultAvailable;
|
|
132
|
-
}
|
|
133
278
|
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
279
|
+
const isDisjoint = Boolean(this.device.gl.getParameter(GL.GPU_DISJOINT_EXT));
|
|
280
|
+
query.disjoint = isDisjoint;
|
|
281
|
+
query.result = isDisjoint
|
|
282
|
+
? 0n
|
|
283
|
+
: BigInt(this.device.gl.getQueryParameter(query.handle, GL.QUERY_RESULT));
|
|
284
|
+
return true;
|
|
137
285
|
}
|
|
138
286
|
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
287
|
+
protected async _consumeTimestampPairResult(pairIndex: number): Promise<bigint> {
|
|
288
|
+
const pair = this._timestampPairs[pairIndex];
|
|
289
|
+
if (!pair || pair.completedQueries.length === 0) {
|
|
290
|
+
throw new Error('Timestamp query pair has no completed result');
|
|
291
|
+
}
|
|
143
292
|
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
293
|
+
const query = pair.completedQueries.shift()!;
|
|
294
|
+
|
|
295
|
+
try {
|
|
296
|
+
return await this._consumeQueryResult(query);
|
|
297
|
+
} finally {
|
|
298
|
+
this.device.gl.deleteQuery(query.handle);
|
|
299
|
+
}
|
|
147
300
|
}
|
|
148
301
|
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
return this._pollingPromise;
|
|
302
|
+
protected _consumeQueryResult(query: WebGLPendingQuery): Promise<bigint> {
|
|
303
|
+
if (query.promise) {
|
|
304
|
+
return query.promise;
|
|
153
305
|
}
|
|
154
306
|
|
|
155
|
-
|
|
307
|
+
this._pendingReads.add(query);
|
|
308
|
+
query.promise = new Promise((resolve, reject) => {
|
|
309
|
+
query.resolve = resolve;
|
|
310
|
+
query.reject = reject;
|
|
156
311
|
|
|
157
|
-
this._pollingPromise = new Promise((resolve, reject) => {
|
|
158
312
|
const poll = () => {
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
313
|
+
query.pollRequestId = null;
|
|
314
|
+
|
|
315
|
+
if (query.cancelled || this.destroyed) {
|
|
316
|
+
this._pendingReads.delete(query);
|
|
317
|
+
query.promise = null;
|
|
318
|
+
query.resolve = null;
|
|
319
|
+
query.reject = null;
|
|
320
|
+
resolve(0n);
|
|
321
|
+
return;
|
|
322
|
+
}
|
|
323
|
+
|
|
324
|
+
if (!this._pollQueryAvailability(query)) {
|
|
325
|
+
query.pollRequestId = this._requestAnimationFrame(poll);
|
|
326
|
+
return;
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
this._pendingReads.delete(query);
|
|
330
|
+
query.promise = null;
|
|
331
|
+
query.resolve = null;
|
|
332
|
+
query.reject = null;
|
|
333
|
+
if (query.disjoint) {
|
|
334
|
+
reject(new Error('GPU timestamp query was invalidated by a disjoint event'));
|
|
165
335
|
} else {
|
|
166
|
-
|
|
336
|
+
resolve(query.result || 0n);
|
|
167
337
|
}
|
|
168
338
|
};
|
|
169
339
|
|
|
170
|
-
|
|
340
|
+
poll();
|
|
171
341
|
});
|
|
172
342
|
|
|
173
|
-
return
|
|
343
|
+
return query.promise;
|
|
344
|
+
}
|
|
345
|
+
|
|
346
|
+
protected _cancelPendingQuery(query: WebGLPendingQuery): void {
|
|
347
|
+
this._pendingReads.delete(query);
|
|
348
|
+
query.cancelled = true;
|
|
349
|
+
if (query.pollRequestId !== null) {
|
|
350
|
+
this._cancelAnimationFrame(query.pollRequestId);
|
|
351
|
+
query.pollRequestId = null;
|
|
352
|
+
}
|
|
353
|
+
if (query.resolve) {
|
|
354
|
+
const resolve = query.resolve;
|
|
355
|
+
query.promise = null;
|
|
356
|
+
query.resolve = null;
|
|
357
|
+
query.reject = null;
|
|
358
|
+
resolve(0n);
|
|
359
|
+
}
|
|
360
|
+
}
|
|
361
|
+
|
|
362
|
+
protected _requestAnimationFrame(callback: FrameRequestCallback): number {
|
|
363
|
+
return requestAnimationFrame(callback);
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
protected _cancelAnimationFrame(requestId: number): void {
|
|
367
|
+
cancelAnimationFrame(requestId);
|
|
174
368
|
}
|
|
175
369
|
}
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
import {NumericArray, NumberArray4} from '@math.gl/types';
|
|
6
6
|
import {RenderPass, RenderPassProps, RenderPassParameters} from '@luma.gl/core';
|
|
7
7
|
import {WebGLDevice} from '../webgl-device';
|
|
8
|
-
import {GL, GLParameters} from '@luma.gl/constants';
|
|
8
|
+
import {GL, GLParameters} from '@luma.gl/webgl/constants';
|
|
9
9
|
import {withGLParameters} from '../../context/state-tracker/with-parameters';
|
|
10
10
|
import {setGLParameters} from '../../context/parameters/unified-parameter-api';
|
|
11
11
|
import {WEBGLQuerySet} from './webgl-query-set';
|
|
@@ -23,13 +23,21 @@ export class WEBGLRenderPass extends RenderPass {
|
|
|
23
23
|
constructor(device: WebGLDevice, props: RenderPassProps) {
|
|
24
24
|
super(device, props);
|
|
25
25
|
this.device = device;
|
|
26
|
+
const webglFramebuffer = this.props.framebuffer as WEBGLFramebuffer | null;
|
|
27
|
+
const isDefaultFramebuffer = !webglFramebuffer || webglFramebuffer.handle === null;
|
|
28
|
+
|
|
29
|
+
if (isDefaultFramebuffer) {
|
|
30
|
+
// Treat an explicit wrapper around the default framebuffer the same as the
|
|
31
|
+
// implicit default path so draw buffer and viewport state stay valid.
|
|
32
|
+
device.getDefaultCanvasContext()._resizeDrawingBufferIfNeeded();
|
|
33
|
+
}
|
|
26
34
|
|
|
27
35
|
// If no viewport is provided, apply reasonably defaults
|
|
28
36
|
let viewport: NumberArray4 | undefined;
|
|
29
37
|
if (!props?.parameters?.viewport) {
|
|
30
|
-
if (
|
|
38
|
+
if (!isDefaultFramebuffer) {
|
|
31
39
|
// Set the viewport to the size of the framebuffer
|
|
32
|
-
const {width, height} =
|
|
40
|
+
const {width, height} = webglFramebuffer;
|
|
33
41
|
viewport = [0, 0, width, height];
|
|
34
42
|
} else {
|
|
35
43
|
// Instead of using our own book-keeping, we can just read the values from the WebGL context
|
|
@@ -43,24 +51,36 @@ export class WEBGLRenderPass extends RenderPass {
|
|
|
43
51
|
this.setParameters({viewport, ...this.props.parameters});
|
|
44
52
|
|
|
45
53
|
// Specify mapping of draw buffer locations to color attachments
|
|
46
|
-
const webglFramebuffer = this.props.framebuffer as WEBGLFramebuffer;
|
|
47
54
|
// Default framebuffers can only be set to GL.BACK or GL.NONE
|
|
48
|
-
if (
|
|
49
|
-
const drawBuffers =
|
|
50
|
-
(_, i) => GL.COLOR_ATTACHMENT0 + i
|
|
51
|
-
);
|
|
55
|
+
if (!isDefaultFramebuffer) {
|
|
56
|
+
const drawBuffers = webglFramebuffer.colorAttachments.map((_, i) => GL.COLOR_ATTACHMENT0 + i);
|
|
52
57
|
this.device.gl.drawBuffers(drawBuffers);
|
|
53
58
|
} else {
|
|
59
|
+
// Default framebuffer only supports GL.BACK/GL.NONE draw buffers, even when
|
|
60
|
+
// passed through an explicit framebuffer wrapper.
|
|
54
61
|
this.device.gl.drawBuffers([GL.BACK]);
|
|
55
62
|
}
|
|
56
63
|
|
|
57
64
|
// Hack - for now WebGL draws in "immediate mode" (instead of queueing the operations)...
|
|
58
65
|
this.clear();
|
|
66
|
+
|
|
67
|
+
if (this.props.timestampQuerySet && this.props.beginTimestampIndex !== undefined) {
|
|
68
|
+
const webglQuerySet = this.props.timestampQuerySet as WEBGLQuerySet;
|
|
69
|
+
webglQuerySet.writeTimestamp(this.props.beginTimestampIndex);
|
|
70
|
+
}
|
|
59
71
|
}
|
|
60
72
|
|
|
61
73
|
end(): void {
|
|
74
|
+
if (this.destroyed) {
|
|
75
|
+
return;
|
|
76
|
+
}
|
|
77
|
+
if (this.props.timestampQuerySet && this.props.endTimestampIndex !== undefined) {
|
|
78
|
+
const webglQuerySet = this.props.timestampQuerySet as WEBGLQuerySet;
|
|
79
|
+
webglQuerySet.writeTimestamp(this.props.endTimestampIndex);
|
|
80
|
+
}
|
|
62
81
|
this.device.popState();
|
|
63
82
|
// should add commands to CommandEncoder.
|
|
83
|
+
this.destroy();
|
|
64
84
|
}
|
|
65
85
|
|
|
66
86
|
pushDebugGroup(groupLabel: string): void {}
|
|
@@ -110,12 +130,9 @@ export class WEBGLRenderPass extends RenderPass {
|
|
|
110
130
|
if (parameters.blendConstant) {
|
|
111
131
|
glParameters.blendColor = parameters.blendConstant;
|
|
112
132
|
}
|
|
113
|
-
if (parameters.stencilReference) {
|
|
114
|
-
// eslint-disable-next-line no-console
|
|
115
|
-
console.warn('RenderPassParameters.stencilReference not yet implemented in WebGL');
|
|
116
|
-
// parameters.stencilFunc = [func, ref, mask];
|
|
117
|
-
// Does this work?
|
|
133
|
+
if (parameters.stencilReference !== undefined) {
|
|
118
134
|
glParameters[GL.STENCIL_REF] = parameters.stencilReference;
|
|
135
|
+
glParameters[GL.STENCIL_BACK_REF] = parameters.stencilReference;
|
|
119
136
|
}
|
|
120
137
|
|
|
121
138
|
if ('colorMask' in parameters) {
|