-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathwgl-fast.js
77 lines (75 loc) · 2.44 KB
/
wgl-fast.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
export function GLContext(gl) {
return Object.assign(gl, GLContext.prototype);
}
const contextMap = new WeakMap();
function contextGet(gl) {
return (
contextMap.get(gl) ||
contextMap.set(gl, { __proto__: Object.getPrototypeOf(gl) }).get(gl)
);
}
// optimize getAttribLocation, getUniformLocation
Object.assign(GLContext.prototype, {
linkProgram(prog) {
const PROG = contextGet(prog);
Object.assign(PROG, {
getAttribLocation: undefined,
getUniformLocation: undefined,
});
return contextGet(this).linkProgram.call(this, prog);
},
...Object.fromEntries(
["getAttribLocation", "getUniformLocation"].map((method) => [
method,
function (prog, name) {
const PROG = contextGet(prog);
const dict = PROG[method] || (PROG[method] = Object.create(null));
const loc = dict[name];
return loc !== undefined
? loc
: (dict[name] = contextGet(this)[method].call(this, prog, name));
},
])
),
});
// optimize texImage2D by texSubImage2D
Object.assign(GLContext.prototype, {
bindTexture(target, value) {
const GL = contextGet(this);
GL.lastTexture = value;
return GL.bindTexture.call(this, target, value);
},
texImage2D(target, level, internalformat, ...args) {
const lastArg = args[args.length - 1];
const [width, height, border, format, type, source] =
args.length > 3
? args
: [
lastArg.naturalWidth || lastArg.videoWidth || lastArg.width,
lastArg.naturalHeight || lastArg.videoHeight || lastArg.height,
0,
...args,
];
const GL = contextGet(this),
TEX = contextGet(GL.lastTexture);
let dirty =
TEX.source !== source || TEX.width !== width || TEX.height !== height;
if (dirty) {
[TEX.source, TEX.width, TEX.height] = [source, width, height];
if (source && source.srcObject) TEX.cooldown = performance.now() + 100; // chrome: image isn't available when stream starts
}
if (performance.now() > TEX.cooldown)
(TEX.cooldown = undefined), (dirty = true);
if (TEX.cooldown === undefined)
return dirty
? GL.texImage2D.call(this, target, level, internalformat, ...args)
: GL.texSubImage2D.call(
this,
target,
level,
0 /*xoffset*/,
0 /*yoffset*/,
...(args.length == 3 ? args : [width, height, format, type, source])
);
},
});