@webex/ladon-ts 4.0.0 → 4.2.1

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.
@@ -1,83 +1,92 @@
1
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
- return new (P || (P = Promise))(function (resolve, reject) {
4
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
- step((generator = generator.apply(thisArg, _arguments || [])).next());
8
- });
9
- };
10
- import { LocalGenerator, NullGenerator, WorkerGenerator, } from './generator';
11
- import { BlurRenderer, PassthroughRenderer, ReplacementRenderer, } from './renderer';
12
- export class Pipeline {
13
- constructor(input_canvas, output_canvas, config) {
14
- this.input_canvas = input_canvas;
15
- this.output_canvas = output_canvas;
16
- this.config = config;
17
- this.loaded = false;
18
- const input_ctx = this.input_canvas.getContext('2d', {
19
- alpha: false,
20
- });
21
- if (!input_ctx) {
22
- throw new Error('[ladon-ts] - error getting input context 2d');
23
- }
24
- this.input_ctx = input_ctx;
25
- }
26
- onFrame() {
27
- return __awaiter(this, void 0, void 0, function* () {
28
- if (!this.generator || !this.renderer) {
29
- throw new Error('[ladon-ts] - pipeline is not loaded.');
30
- }
31
- const raw_image_data = this.input_ctx.getImageData(0, 0, this.config.input.width, this.config.input.height).data;
32
- const mask = yield this.generator.getMask(raw_image_data);
33
- yield this.renderer.render(raw_image_data, mask);
34
- yield this.generator.postRender(raw_image_data);
35
- });
36
- }
37
- isLoaded() {
38
- return this.loaded;
39
- }
40
- load() {
41
- return __awaiter(this, void 0, void 0, function* () {
42
- switch (this.config.render.type) {
43
- case 'blur':
44
- this.renderer = new BlurRenderer(this.output_canvas, this.config);
45
- break;
46
- case 'passthrough':
47
- this.renderer = new PassthroughRenderer(this.output_canvas, this.config);
48
- break;
49
- case 'replacement':
50
- this.renderer = new ReplacementRenderer(this.output_canvas, this.config);
51
- break;
52
- default:
53
- throw new Error('[ladon-ts] - renderer not implemented.');
54
- }
55
- yield this.renderer.load();
56
- if (this.config.render.type === 'passthrough') {
57
- // automatically disable model evaluation when the renderer is set to passthrough
58
- // Note: this may change when gestures are detected (model eval will be a dependency for more than rendering)
59
- this.generator = new NullGenerator(this.config);
60
- }
61
- else {
62
- switch (this.config.mask.generator) {
63
- case 'local':
64
- this.generator = new LocalGenerator(this.config);
65
- break;
66
- case 'worker':
67
- this.generator = new WorkerGenerator(this.config);
68
- break;
69
- default:
70
- throw new Error('[ladon-ts] - generator not implemented.');
71
- }
72
- }
73
- yield this.generator.load();
74
- this.loaded = true;
75
- });
76
- }
77
- destroy() {
78
- var _a, _b;
79
- (_a = this.generator) === null || _a === void 0 ? void 0 : _a.destroy();
80
- (_b = this.renderer) === null || _b === void 0 ? void 0 : _b.destroy();
81
- }
82
- }
83
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicGlwZWxpbmUuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvbGliL3BpcGVsaW5lLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7OztBQUNBLE9BQU8sRUFDSCxjQUFjLEVBRWQsYUFBYSxFQUNiLGVBQWUsR0FDbEIsTUFBTSxhQUFhLENBQUM7QUFDckIsT0FBTyxFQUNILFlBQVksRUFFWixtQkFBbUIsRUFDbkIsbUJBQW1CLEdBQ3RCLE1BQU0sWUFBWSxDQUFDO0FBU3BCLE1BQU0sT0FBTyxRQUFRO0lBT2pCLFlBQ1ksWUFBK0IsRUFDL0IsYUFBZ0MsRUFDeEIsTUFBc0I7UUFGOUIsaUJBQVksR0FBWixZQUFZLENBQW1CO1FBQy9CLGtCQUFhLEdBQWIsYUFBYSxDQUFtQjtRQUN4QixXQUFNLEdBQU4sTUFBTSxDQUFnQjtRQVBsQyxXQUFNLEdBQUcsS0FBSyxDQUFDO1FBU25CLE1BQU0sU0FBUyxHQUFHLElBQUksQ0FBQyxZQUFZLENBQUMsVUFBVSxDQUFDLElBQUksRUFBRTtZQUNqRCxLQUFLLEVBQUUsS0FBSztTQUNmLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxTQUFTLEVBQUU7WUFDWixNQUFNLElBQUksS0FBSyxDQUFDLDZDQUE2QyxDQUFDLENBQUM7U0FDbEU7UUFDRCxJQUFJLENBQUMsU0FBUyxHQUFHLFNBQVMsQ0FBQztJQUMvQixDQUFDO0lBRVksT0FBTzs7WUFDaEIsSUFBSSxDQUFDLElBQUksQ0FBQyxTQUFTLElBQUksQ0FBQyxJQUFJLENBQUMsUUFBUSxFQUFFO2dCQUNuQyxNQUFNLElBQUksS0FBSyxDQUFDLHNDQUFzQyxDQUFDLENBQUM7YUFDM0Q7WUFFRCxNQUFNLGNBQWMsR0FBRyxJQUFJLENBQUMsU0FBUyxDQUFDLFlBQVksQ0FDOUMsQ0FBQyxFQUNELENBQUMsRUFDRCxJQUFJLENBQUMsTUFBTSxDQUFDLEtBQUssQ0FBQyxLQUFLLEVBQ3ZCLElBQUksQ0FBQyxNQUFNLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FDM0IsQ0FBQyxJQUFJLENBQUM7WUFFUCxNQUFNLElBQUksR0FBRyxNQUFNLElBQUksQ0FBQyxTQUFTLENBQUMsT0FBTyxDQUFDLGNBQWMsQ0FBQyxDQUFDO1lBRTFELE1BQU0sSUFBSSxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsY0FBYyxFQUFFLElBQUksQ0FBQyxDQUFDO1lBQ2pELE1BQU0sSUFBSSxDQUFDLFNBQVMsQ0FBQyxVQUFVLENBQUMsY0FBYyxDQUFDLENBQUM7UUFDcEQsQ0FBQztLQUFBO0lBRU0sUUFBUTtRQUNYLE9BQU8sSUFBSSxDQUFDLE1BQU0sQ0FBQztJQUN2QixDQUFDO0lBRVksSUFBSTs7WUFDYixRQUFRLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLElBQUksRUFBRTtnQkFDN0IsS0FBSyxNQUFNO29CQUNQLElBQUksQ0FBQyxRQUFRLEdBQUcsSUFBSSxZQUFZLENBQzVCLElBQUksQ0FBQyxhQUFhLEVBQ2xCLElBQUksQ0FBQyxNQUFNLENBQ2QsQ0FBQztvQkFDRixNQUFNO2dCQUNWLEtBQUssYUFBYTtvQkFDZCxJQUFJLENBQUMsUUFBUSxHQUFHLElBQUksbUJBQW1CLENBQ25DLElBQUksQ0FBQyxhQUFhLEVBQ2xCLElBQUksQ0FBQyxNQUFNLENBQ2QsQ0FBQztvQkFDRixNQUFNO2dCQUNWLEtBQUssYUFBYTtvQkFDZCxJQUFJLENBQUMsUUFBUSxHQUFHLElBQUksbUJBQW1CLENBQ25DLElBQUksQ0FBQyxhQUFhLEVBQ2xCLElBQUksQ0FBQyxNQUFNLENBQ2QsQ0FBQztvQkFDRixNQUFNO2dCQUNWO29CQUNJLE1BQU0sSUFBSSxLQUFLLENBQUMsd0NBQXdDLENBQUMsQ0FBQzthQUNqRTtZQUVELE1BQU0sSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUUzQixJQUFJLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLElBQUksS0FBSyxhQUFhLEVBQUU7Z0JBQzNDLGlGQUFpRjtnQkFDakYsNkdBQTZHO2dCQUM3RyxJQUFJLENBQUMsU0FBUyxHQUFHLElBQUksYUFBYSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQzthQUNuRDtpQkFBTTtnQkFDSCxRQUFRLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLFNBQVMsRUFBRTtvQkFDaEMsS0FBSyxPQUFPO3dCQUNSLElBQUksQ0FBQyxTQUFTLEdBQUcsSUFBSSxjQUFjLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO3dCQUNqRCxNQUFNO29CQUNWLEtBQUssUUFBUTt3QkFDVCxJQUFJLENBQUMsU0FBUyxHQUFHLElBQUksZUFBZSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQzt3QkFDbEQsTUFBTTtvQkFDVjt3QkFDSSxNQUFNLElBQUksS0FBSyxDQUFDLHlDQUF5QyxDQUFDLENBQUM7aUJBQ2xFO2FBQ0o7WUFFRCxNQUFNLElBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxFQUFFLENBQUM7WUFFNUIsSUFBSSxDQUFDLE1BQU0sR0FBRyxJQUFJLENBQUM7UUFDdkIsQ0FBQztLQUFBO0lBRU0sT0FBTzs7UUFDVixNQUFBLElBQUksQ0FBQyxTQUFTLDBDQUFFLE9BQU8sRUFBRSxDQUFDO1FBQzFCLE1BQUEsSUFBSSxDQUFDLFFBQVEsMENBQUUsT0FBTyxFQUFFLENBQUM7SUFDN0IsQ0FBQztDQUNKIn0=
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { LocalGenerator, NullGenerator, WorkerGenerator } from './generator';
11
+ import { BlurRenderer, PassthroughRenderer, ReplacementRenderer } from './renderer';
12
+ import { resizeImage } from './util';
13
+ export class Pipeline {
14
+ constructor(input_canvas, output_canvas, config) {
15
+ this.input_canvas = input_canvas;
16
+ this.output_canvas = output_canvas;
17
+ this.config = config;
18
+ this.loaded = false;
19
+ const input_ctx = this.input_canvas.getContext('2d', {
20
+ alpha: false,
21
+ willReadFrequently: true,
22
+ });
23
+ if (!input_ctx) {
24
+ throw new Error('[ladon-ts] - error getting input context 2d');
25
+ }
26
+ this.input_ctx = input_ctx;
27
+ }
28
+ onFrame() {
29
+ return __awaiter(this, void 0, void 0, function* () {
30
+ if (!this.generator || !this.renderer) {
31
+ throw new Error('[ladon-ts] - pipeline is not loaded.');
32
+ }
33
+ const rawImageData = this.input_ctx.getImageData(0, 0, this.config.input.width, this.config.input.height).data;
34
+ let maskImageData = rawImageData;
35
+ // Resize the image data if the model expects a fixed size input (e.g., tiny model).
36
+ if (this.config.mask.input_size.width !== this.config.input.width) {
37
+ maskImageData = resizeImage(rawImageData, this.config.input.width, this.config.input.height, this.config.mask.input_size.width, this.config.mask.input_size.height);
38
+ }
39
+ const mask = yield this.generator.getMask(maskImageData);
40
+ // Render the full size video image in the background with the mask on top.
41
+ yield this.renderer.render(rawImageData, mask);
42
+ // Cleanup the mask data.
43
+ yield this.generator.postRender(maskImageData);
44
+ });
45
+ }
46
+ isLoaded() {
47
+ return this.loaded;
48
+ }
49
+ load() {
50
+ return __awaiter(this, void 0, void 0, function* () {
51
+ switch (this.config.render.type) {
52
+ case 'blur':
53
+ this.renderer = new BlurRenderer(this.output_canvas, this.config);
54
+ break;
55
+ case 'passthrough':
56
+ this.renderer = new PassthroughRenderer(this.output_canvas, this.config);
57
+ break;
58
+ case 'replacement':
59
+ this.renderer = new ReplacementRenderer(this.output_canvas, this.config);
60
+ break;
61
+ default:
62
+ throw new Error('[ladon-ts] - renderer not implemented.');
63
+ }
64
+ yield this.renderer.load();
65
+ if (this.config.render.type === 'passthrough') {
66
+ // automatically disable model evaluation when the renderer is set to passthrough
67
+ // Note: this may change when gestures are detected (model eval will be a dependency for more than rendering)
68
+ this.generator = new NullGenerator(this.config);
69
+ }
70
+ else {
71
+ switch (this.config.mask.generator) {
72
+ case 'local':
73
+ this.generator = new LocalGenerator(this.config);
74
+ break;
75
+ case 'worker':
76
+ this.generator = new WorkerGenerator(this.config);
77
+ break;
78
+ default:
79
+ throw new Error('[ladon-ts] - generator not implemented.');
80
+ }
81
+ }
82
+ yield this.generator.load();
83
+ this.loaded = true;
84
+ });
85
+ }
86
+ destroy() {
87
+ var _a, _b;
88
+ (_a = this.generator) === null || _a === void 0 ? void 0 : _a.destroy();
89
+ (_b = this.renderer) === null || _b === void 0 ? void 0 : _b.destroy();
90
+ }
91
+ }
92
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicGlwZWxpbmUuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvbGliL3BpcGVsaW5lLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7OztBQUNBLE9BQU8sRUFBRSxjQUFjLEVBQWlCLGFBQWEsRUFBRSxlQUFlLEVBQUUsTUFBTSxhQUFhLENBQUM7QUFDNUYsT0FBTyxFQUFFLFlBQVksRUFBaUIsbUJBQW1CLEVBQUUsbUJBQW1CLEVBQUUsTUFBTSxZQUFZLENBQUM7QUFDbkcsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLFFBQVEsQ0FBQztBQVNyQyxNQUFNLE9BQU8sUUFBUTtJQU9qQixZQUNZLFlBQStCLEVBQy9CLGFBQWdDLEVBQ3hCLE1BQXNCO1FBRjlCLGlCQUFZLEdBQVosWUFBWSxDQUFtQjtRQUMvQixrQkFBYSxHQUFiLGFBQWEsQ0FBbUI7UUFDeEIsV0FBTSxHQUFOLE1BQU0sQ0FBZ0I7UUFQbEMsV0FBTSxHQUFHLEtBQUssQ0FBQztRQVNuQixNQUFNLFNBQVMsR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLFVBQVUsQ0FBQyxJQUFJLEVBQUU7WUFDakQsS0FBSyxFQUFFLEtBQUs7WUFDWixrQkFBa0IsRUFBRSxJQUFJO1NBQzNCLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxTQUFTLEVBQUU7WUFDWixNQUFNLElBQUksS0FBSyxDQUFDLDZDQUE2QyxDQUFDLENBQUM7U0FDbEU7UUFDRCxJQUFJLENBQUMsU0FBUyxHQUFHLFNBQVMsQ0FBQztJQUMvQixDQUFDO0lBRVksT0FBTzs7WUFDaEIsSUFBSSxDQUFDLElBQUksQ0FBQyxTQUFTLElBQUksQ0FBQyxJQUFJLENBQUMsUUFBUSxFQUFFO2dCQUNuQyxNQUFNLElBQUksS0FBSyxDQUFDLHNDQUFzQyxDQUFDLENBQUM7YUFDM0Q7WUFFRCxNQUFNLFlBQVksR0FBRyxJQUFJLENBQUMsU0FBUyxDQUFDLFlBQVksQ0FDNUMsQ0FBQyxFQUNELENBQUMsRUFDRCxJQUFJ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
@@ -0,0 +1,21 @@
1
+ import { PipelineConfig } from '../config';
2
+ import { MaskResult } from '../generator';
3
+ import { LadonRenderer } from './ladon-renderer';
4
+ import { WebGLRenderer } from './webgl-renderer';
5
+ export declare class BlurRenderer extends WebGLRenderer implements LadonRenderer {
6
+ output_canvas: HTMLCanvasElement;
7
+ readonly config: PipelineConfig;
8
+ private program_1;
9
+ private program_2;
10
+ private framebuffer;
11
+ private transfer_texture;
12
+ private u_blur;
13
+ private fragment_shader_common;
14
+ private fragment_shader_pass_1_src;
15
+ fragment_shader_pass_2_src: string;
16
+ constructor(output_canvas: HTMLCanvasElement, config: PipelineConfig);
17
+ render(input: Uint8ClampedArray, mask: MaskResult): Promise<void>;
18
+ load(): Promise<void>;
19
+ destroy(): void;
20
+ private getBlurKernel;
21
+ }
@@ -0,0 +1,190 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { compileShader, linkProgram } from '../util';
11
+ import { WebGLRenderer } from './webgl-renderer';
12
+ export class BlurRenderer extends WebGLRenderer {
13
+ constructor(output_canvas, config) {
14
+ super(output_canvas, config);
15
+ this.output_canvas = output_canvas;
16
+ this.config = config;
17
+ this.fragment_shader_common = `#version 300 es
18
+ precision highp float;
19
+
20
+ #define KERNEL_SIZE ${this.config.render.kernel_size}
21
+ #define HORIZONTAL vec2(1.0, 0.0)
22
+ #define VERTICAL vec2(0.0, 1.0)
23
+ #define EPSILON 0.00001
24
+
25
+ out vec4 outColor;
26
+
27
+ uniform sampler2D u_image;
28
+ uniform float u_kernel[KERNEL_SIZE];
29
+ uniform sampler2D u_mask;
30
+ uniform vec2 u_resolution;
31
+
32
+
33
+ float get_mask(vec2 st) {
34
+ return clamp(texture(u_mask, st).r, 0.0, 1.0);
35
+ }
36
+
37
+ float get_inv_mask(vec2 st) {
38
+ return 1.0 - get_mask(st);
39
+ }
40
+
41
+ vec4 get_offset_mul(sampler2D src, vec2 uv, float weight) {
42
+ if (uv.x < 0.0 || uv.x > 1.0 || uv.y < 0.0 || uv.y > 1.0) {
43
+ return vec4(vec3(0.0), weight);
44
+ }
45
+
46
+ // 4th channel is masked weight value
47
+ return vec4(vec3(texture(src, uv).rgb * get_inv_mask(uv) * weight), get_mask(uv) * weight);
48
+ }
49
+
50
+ vec3 blur(sampler2D src, vec2 uv, vec2 direction) {
51
+ vec4 result = vec4(0.0);
52
+
53
+ vec2 step = (direction / u_resolution);
54
+ int offset = (KERNEL_SIZE - 1) / 2;
55
+
56
+ for (int i = 0; i < KERNEL_SIZE; i++) {
57
+ vec2 offset = step * float(i - offset);
58
+ result += get_offset_mul(src, uv + offset, u_kernel[i]);
59
+ }
60
+
61
+ if (abs(result.a - 1.0) < EPSILON) {
62
+ return vec3(0.0);
63
+ }
64
+
65
+ // redistribute weights from masked areas
66
+ return result.rgb * (1.0 + (result.a / (1.0 - result.a)));
67
+ }
68
+ `;
69
+ this.fragment_shader_pass_1_src = this.fragment_shader_common +
70
+ `
71
+ void main() {
72
+ vec2 st = gl_FragCoord.xy / u_resolution;
73
+
74
+ outColor = vec4(blur(u_image, st, HORIZONTAL) * get_inv_mask(st), 1.0);
75
+ }
76
+ `;
77
+ this.fragment_shader_pass_2_src = this.fragment_shader_common +
78
+ `
79
+ uniform sampler2D u_blur;
80
+
81
+
82
+ void main() {
83
+ ${this.getUVCalculation()}
84
+
85
+ vec3 blurred = blur(u_blur, st, VERTICAL);
86
+ vec3 image = texture(u_image, st).rgb;
87
+ float mask = texture(u_mask, st).r;
88
+
89
+ outColor = vec4(blurred * (1.0 - mask) + image * mask, 1.0);
90
+ }
91
+ `;
92
+ if (this.config.render.kernel_size % 2 === 0) {
93
+ throw new Error('[ladon-ts] - kernel_size must be odd');
94
+ }
95
+ // program pass 1 setup
96
+ {
97
+ const vertex_shader = compileShader(this.gl, this.gl.VERTEX_SHADER, this.vertex_shader_src);
98
+ const fragment_shader = compileShader(this.gl, this.gl.FRAGMENT_SHADER, this.fragment_shader_pass_1_src);
99
+ this.program_1 = linkProgram(this.gl, vertex_shader, fragment_shader);
100
+ this.gl.useProgram(this.program_1);
101
+ const framebuffer = this.gl.createFramebuffer();
102
+ if (!framebuffer) {
103
+ throw new Error('[ladon-ts] - error creating framebuffer');
104
+ }
105
+ this.framebuffer = framebuffer;
106
+ const transfer_texture = this.gl.createTexture();
107
+ if (!transfer_texture) {
108
+ throw new Error('[ladon-ts] - error creating output texture');
109
+ }
110
+ this.transfer_texture = transfer_texture;
111
+ this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, this.framebuffer);
112
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.transfer_texture);
113
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MIN_FILTER, this.gl.LINEAR);
114
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_S, this.gl.CLAMP_TO_EDGE);
115
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_T, this.gl.CLAMP_TO_EDGE);
116
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.RGBA, this.config.input.width, this.config.input.height, 0, this.gl.RGBA, this.gl.UNSIGNED_BYTE, null);
117
+ this.gl.framebufferTexture2D(this.gl.FRAMEBUFFER, this.gl.COLOR_ATTACHMENT0, this.gl.TEXTURE_2D, this.transfer_texture, 0);
118
+ this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, null);
119
+ this.setSharedUniforms(this.program_1);
120
+ const u_kernel = this.gl.getUniformLocation(this.program_1, 'u_kernel');
121
+ if (!u_kernel) {
122
+ throw new Error('[ladon-ts] - error finding "u_kernel" uniform');
123
+ }
124
+ this.gl.uniform1fv(u_kernel, this.getBlurKernel());
125
+ }
126
+ // program pass 2 setup
127
+ {
128
+ const vertex_shader = compileShader(this.gl, this.gl.VERTEX_SHADER, this.vertex_shader_src);
129
+ const fragment_shader = compileShader(this.gl, this.gl.FRAGMENT_SHADER, this.fragment_shader_pass_2_src);
130
+ this.program_2 = linkProgram(this.gl, vertex_shader, fragment_shader);
131
+ this.gl.useProgram(this.program_2);
132
+ const u_blur = this.gl.getUniformLocation(this.program_2, 'u_blur');
133
+ if (!u_blur) {
134
+ throw new Error('[ladon-ts] - error finding "u_blur" uniform');
135
+ }
136
+ this.u_blur = u_blur;
137
+ this.gl.activeTexture(this.gl.TEXTURE2);
138
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.transfer_texture);
139
+ this.gl.uniform1i(this.u_blur, 2);
140
+ this.setSharedUniforms(this.program_2);
141
+ const u_kernel = this.gl.getUniformLocation(this.program_2, 'u_kernel');
142
+ if (!u_kernel) {
143
+ throw new Error('[ladon-ts] - error finding "u_kernel" uniform');
144
+ }
145
+ this.gl.uniform1fv(u_kernel, this.getBlurKernel());
146
+ }
147
+ }
148
+ render(input, mask) {
149
+ return __awaiter(this, void 0, void 0, function* () {
150
+ this.uploadVideoStream(input);
151
+ if (mask.warm) {
152
+ this.gl.activeTexture(this.gl.TEXTURE1);
153
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.mask_texture);
154
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.R32F, this.config.mask.output_size.width, this.config.mask.output_size.height, 0, this.gl.RED, this.gl.FLOAT, mask.data);
155
+ }
156
+ // program pass 1 - blur in one direction & output to framebuffer
157
+ this.gl.useProgram(this.program_1);
158
+ this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, this.framebuffer);
159
+ this.gl.drawArrays(this.gl.TRIANGLES, 0, this.verts.length / 3);
160
+ this.gl.bindFramebuffer(this.gl.FRAMEBUFFER, null);
161
+ // program pass 2 - blur in other direction & draw to screen
162
+ this.gl.useProgram(this.program_2);
163
+ this.gl.drawArrays(this.gl.TRIANGLES, 0, this.verts.length / 3);
164
+ this.postDraw();
165
+ });
166
+ }
167
+ load() {
168
+ return __awaiter(this, void 0, void 0, function* () {
169
+ // empty
170
+ });
171
+ }
172
+ destroy() {
173
+ // empty
174
+ }
175
+ getBlurKernel() {
176
+ const kernel = [];
177
+ let sum = 0;
178
+ for (let i = 0; i < this.config.render.kernel_size; i++) {
179
+ let w = i - (this.config.render.kernel_size - 1) / 2;
180
+ w = Math.exp(-(Math.pow(w, 2)) / Math.pow(this.config.render.sigma, 2));
181
+ kernel.push(w);
182
+ sum += w;
183
+ }
184
+ for (let i = 0; i < this.config.render.kernel_size; i++) {
185
+ kernel[i] = kernel[i] / sum;
186
+ }
187
+ return new Float32Array(kernel);
188
+ }
189
+ }
190
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYmx1ci1yZW5kZXJlci5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9saWIvcmVuZGVyZXIvYmx1ci1yZW5kZXJlci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7QUFFQSxPQUFPLEVBQUUsYUFBYSxFQUFFLFdBQVcsRUFBRSxNQUFNLFNBQVMsQ0FBQztBQUdyRCxPQUFPLEVBQUUsYUFBYSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFFakQsTUFBTSxPQUFPLFlBQWEsU0FBUSxhQUFhO0lBeUYzQyxZQUFtQixhQUFnQyxFQUFrQixNQUFzQjtRQUN2RixLQUFLLENBQUMsYUFBYSxFQUFFLE1BQU0sQ0FBQyxDQUFDO1FBRGQsa0JBQWEsR0FBYixhQUFhLENBQW1CO1FBQWtCLFdBQU0sR0FBTixNQUFNLENBQWdCO1FBaEZuRiwyQkFBc0IsR0FBRzs7OzBCQUdWLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBcUIsQ0FBQyxXQUFXOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Q0FnRHZFLENBQUM7UUFFVSwrQkFBMEIsR0FDOUIsSUFBSSxDQUFDLHNCQUFzQjtZQUMzQjs7Ozs7O0NBTVAsQ0FBQztRQUVTLCtCQUEwQixHQUM3QixJQUFJLENBQUMsc0JBQXNCO1lBQzNCOzs7OztNQUtGLElBQUksQ0FBQyxnQkFBZ0IsRUFBRTs7Ozs7Ozs7Q0FRNUIsQ0FBQztRQUtNLElBQUssSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUFxQixDQUFDLFdBQVcsR0FBRyxDQUFDLEtBQUssQ0FBQyxFQUFFO1lBQzFELE1BQU0sSUFBSSxLQUFLLENBQUMsc0NBQXNDLENBQUMsQ0FBQztTQUMzRDtRQUVELHVCQUF1QjtRQUN2QjtZQUNJLE1BQU0sYUFBYSxHQUFHLGFBQWEsQ0FDL0IsSUFBSSxDQUFDLEVBQUUsRUFDUCxJQUFJLENBQUMsRUFBRSxDQUFDLGFBQWEsRUFDckIsSUFBSSxDQUFDLGlCQUFp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
@@ -0,0 +1,6 @@
1
+ import { MaskResult } from '../generator';
2
+ export interface LadonRenderer {
3
+ render(input: Uint8ClampedArray, mask: MaskResult): Promise<void>;
4
+ load(): Promise<void>;
5
+ destroy(): void;
6
+ }
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibGFkb24tcmVuZGVyZXIuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvbGliL3JlbmRlcmVyL2xhZG9uLXJlbmRlcmVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiIifQ==
@@ -0,0 +1,14 @@
1
+ import { PipelineConfig } from '../config';
2
+ import { MaskResult } from '../generator';
3
+ import { LadonRenderer } from './ladon-renderer';
4
+ import { WebGLRenderer } from './webgl-renderer';
5
+ export declare class PassthroughRenderer extends WebGLRenderer implements LadonRenderer {
6
+ output_canvas: HTMLCanvasElement;
7
+ readonly config: PipelineConfig;
8
+ private program;
9
+ private fragment_shader;
10
+ constructor(output_canvas: HTMLCanvasElement, config: PipelineConfig);
11
+ render(input: Uint8ClampedArray, _: MaskResult): Promise<void>;
12
+ load(): Promise<void>;
13
+ destroy(): void;
14
+ }
@@ -0,0 +1,57 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { compileShader, linkProgram } from '../util';
11
+ import { WebGLRenderer } from './webgl-renderer';
12
+ export class PassthroughRenderer extends WebGLRenderer {
13
+ constructor(output_canvas, config) {
14
+ super(output_canvas, config);
15
+ this.output_canvas = output_canvas;
16
+ this.config = config;
17
+ this.fragment_shader = `#version 300 es
18
+ precision highp float;
19
+
20
+ out vec4 outColor;
21
+
22
+ uniform sampler2D u_image;
23
+ uniform vec2 u_resolution;
24
+
25
+
26
+ void main() {
27
+ ${this.getUVCalculation()}
28
+
29
+ outColor = vec4(texture(u_image, st).rgb, 1.0);
30
+ }
31
+ `;
32
+ const vertex_shader = compileShader(this.gl, this.gl.VERTEX_SHADER, this.vertex_shader_src);
33
+ const fragment_shader = compileShader(this.gl, this.gl.FRAGMENT_SHADER, this.fragment_shader);
34
+ this.program = linkProgram(this.gl, vertex_shader, fragment_shader);
35
+ this.gl.useProgram(this.program);
36
+ this.setSharedUniforms(this.program);
37
+ }
38
+ render(input,
39
+ /* eslint-disable-next-line @typescript-eslint/no-unused-vars */
40
+ _) {
41
+ return __awaiter(this, void 0, void 0, function* () {
42
+ this.uploadVideoStream(input);
43
+ this.gl.useProgram(this.program);
44
+ this.gl.drawArrays(this.gl.TRIANGLES, 0, this.verts.length / 3);
45
+ this.postDraw();
46
+ });
47
+ }
48
+ load() {
49
+ return __awaiter(this, void 0, void 0, function* () {
50
+ // empty
51
+ });
52
+ }
53
+ destroy() {
54
+ // empty
55
+ }
56
+ }
57
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicGFzc3Rocm91Z2gtcmVuZGVyZXIuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvbGliL3JlbmRlcmVyL3Bhc3N0aHJvdWdoLXJlbmRlcmVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7OztBQUVBLE9BQU8sRUFBRSxhQUFhLEVBQUUsV0FBVyxFQUFFLE1BQU0sU0FBUyxDQUFDO0FBR3JELE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSxrQkFBa0IsQ0FBQztBQUVqRCxNQUFNLE9BQU8sbUJBQW9CLFNBQVEsYUFBYTtJQW1CbEQsWUFBbUIsYUFBZ0MsRUFBa0IsTUFBc0I7UUFDdkYsS0FBSyxDQUFDLGFBQWEsRUFBRSxNQUFNLENBQUMsQ0FBQztRQURkLGtCQUFhLEdBQWIsYUFBYSxDQUFtQjtRQUFrQixXQUFNLEdBQU4sTUFBTSxDQUFnQjtRQWhCbkYsb0JBQWUsR0FBRzs7Ozs7Ozs7OztNQVV4QixJQUFJLENBQUMsZ0JBQWdCLEVBQUU7Ozs7Q0FJNUIsQ0FBQztRQUtNLE1BQU0sYUFBYSxHQUFHLGFBQWEsQ0FBQyxJQUFJLENBQUMsRUFBRSxFQUFFLElBQUksQ0FBQyxFQUFFLENBQUMsYUFBYSxFQUFFLElBQUksQ0FBQyxpQkFBaUIsQ0FBQyxDQUFDO1FBQzVGLE1BQU0sZUFBZSxHQUFHLGFBQWEsQ0FDakMsSUFBSSxDQUFDLEVBQUUsRUFDUCxJQUFJLENBQUMsRUFBRSxDQUFDLGVBQWUsRUFDdkIsSUFBSSxDQUFDLGVBQWUsQ0FDdkIsQ0FBQztRQUVGLElBQUksQ0FBQyxPQUFPLEdBQUcsV0FBVyxDQUFDLElBQUksQ0FBQyxFQUFFLEVBQUUsYUFBYSxFQUFFLGVBQWUsQ0FBQyxDQUFDO1FBQ3BFLElBQUksQ0FBQyxFQUFFLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztRQUVqQyxJQUFJLENBQUMsaUJBQWlCLENBQUMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxDQUFDO0lBQ3pDLENBQUM7SUFFWSxNQUFNLENBQ2YsS0FBd0I7SUFDeEIsZ0VBQWdFO0lBQ2hFLENBQWE7O1lBRWIsSUFBSSxDQUFDLGlCQUFpQixDQUFDLEtBQUssQ0FBQyxDQUFDO1lBRTlCLElBQUksQ0FBQyxFQUFFLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxPQUFPLENBQUMsQ0FBQztZQUVqQyxJQUFJLENBQUMsRUFBRSxDQUFDLFVBQVUsQ0FBQyxJQUFJLENBQUMsRUFBRSxDQUFDLFNBQVMsRUFBRSxDQUFDLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxNQUFNLEdBQUcsQ0FBQyxDQUFDLENBQUM7WUFFaEUsSUFBSSxDQUFDLFFBQVEsRUFBRSxDQUFDO1FBQ3BCLENBQUM7S0FBQTtJQUVZLElBQUk7O1lBQ2IsUUFBUTtRQUNaLENBQUM7S0FBQTtJQUVNLE9BQU87UUFDVixRQUFRO0lBQ1osQ0FBQztDQUNKIn0=
@@ -0,0 +1,16 @@
1
+ import { PipelineConfig } from '../config';
2
+ import { MaskResult } from '../generator';
3
+ import { LadonRenderer } from './ladon-renderer';
4
+ import { WebGLRenderer } from './webgl-renderer';
5
+ export declare class ReplacementRenderer extends WebGLRenderer implements LadonRenderer {
6
+ output_canvas: HTMLCanvasElement;
7
+ readonly config: PipelineConfig;
8
+ private program;
9
+ private background_canvas_ctx;
10
+ protected background_texture: WebGLTexture;
11
+ private fragment_shader;
12
+ constructor(output_canvas: HTMLCanvasElement, config: PipelineConfig);
13
+ render(input: Uint8ClampedArray, mask: MaskResult): Promise<void>;
14
+ load(): Promise<void>;
15
+ destroy(): void;
16
+ }
@@ -0,0 +1,103 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { compileShader, linkProgram } from '../util';
11
+ import { WebGLRenderer } from './webgl-renderer';
12
+ export class ReplacementRenderer extends WebGLRenderer {
13
+ constructor(output_canvas, config) {
14
+ super(output_canvas, config);
15
+ this.output_canvas = output_canvas;
16
+ this.config = config;
17
+ this.fragment_shader = `#version 300 es
18
+ precision highp float;
19
+
20
+ out vec4 outColor;
21
+
22
+ uniform sampler2D u_background;
23
+ uniform sampler2D u_image;
24
+ uniform sampler2D u_mask;
25
+ uniform vec2 u_resolution;
26
+
27
+
28
+ float get_mask(vec2 st) {
29
+ return clamp(texture(u_mask, st).r, 0.0, 1.0);
30
+ }
31
+
32
+ float get_inv_mask(vec2 st) {
33
+ return 1.0 - get_mask(st);
34
+ }
35
+
36
+ void main() {
37
+ ${this.getUVCalculation()}
38
+
39
+ outColor = vec4(texture(u_background, st).rgb * get_inv_mask(st) + texture(u_image, st).rgb * get_mask(st), 1.0);
40
+ }
41
+ `;
42
+ const background_canvas_ctx = this.config.render.background.getContext('2d');
43
+ if (!background_canvas_ctx) {
44
+ throw new Error('[ladon-ts] - could not get background canvas context 2d');
45
+ }
46
+ this.background_canvas_ctx = background_canvas_ctx;
47
+ const background_data = this.background_canvas_ctx.getImageData(0, 0, this.config.render.background.width, this.config.render.background.height).data;
48
+ if (this.config.render.kernel_size % 2 === 0) {
49
+ throw new Error('[ladon-ts] - kernel_size must be odd');
50
+ }
51
+ const vertex_shader = compileShader(this.gl, this.gl.VERTEX_SHADER, this.vertex_shader_src);
52
+ const fragment_shader = compileShader(this.gl, this.gl.FRAGMENT_SHADER, this.fragment_shader);
53
+ this.program = linkProgram(this.gl, vertex_shader, fragment_shader);
54
+ this.gl.useProgram(this.program);
55
+ this.setSharedUniforms(this.program);
56
+ const background_texture = this.gl.createTexture();
57
+ if (!background_texture) {
58
+ throw new Error('[ladon-ts] - error creating input texture');
59
+ }
60
+ this.background_texture = background_texture;
61
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.background_texture);
62
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_MIN_FILTER, this.gl.LINEAR);
63
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_S, this.gl.CLAMP_TO_EDGE);
64
+ this.gl.texParameteri(this.gl.TEXTURE_2D, this.gl.TEXTURE_WRAP_T, this.gl.CLAMP_TO_EDGE);
65
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.RGBA, this.config.render.background.width, this.config.render.background.height, 0, this.gl.RGBA, this.gl.UNSIGNED_BYTE, background_data);
66
+ this.gl.bindTexture(this.gl.TEXTURE_2D, null);
67
+ const u_background = this.gl.getUniformLocation(this.program, 'u_background');
68
+ if (!u_background) {
69
+ throw new Error('[ladon-ts] - error finding "u_background" uniform');
70
+ }
71
+ this.gl.activeTexture(this.gl.TEXTURE2);
72
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.background_texture);
73
+ this.gl.uniform1i(u_background, 2);
74
+ }
75
+ render(input, mask) {
76
+ return __awaiter(this, void 0, void 0, function* () {
77
+ this.uploadVideoStream(input);
78
+ if (mask.warm) {
79
+ this.gl.activeTexture(this.gl.TEXTURE1);
80
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.mask_texture);
81
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.R32F, this.config.input.width, this.config.input.height, 0, this.gl.RED, this.gl.FLOAT, mask.data);
82
+ }
83
+ if (!this.config.render.static) {
84
+ const background_data = this.background_canvas_ctx.getImageData(0, 0, this.config.render.background.width, this.config.render.background.height).data;
85
+ this.gl.activeTexture(this.gl.TEXTURE2);
86
+ this.gl.bindTexture(this.gl.TEXTURE_2D, this.background_texture);
87
+ this.gl.texImage2D(this.gl.TEXTURE_2D, 0, this.gl.RGBA, this.config.input.width, this.config.input.height, 0, this.gl.RGBA, this.gl.UNSIGNED_BYTE, background_data);
88
+ }
89
+ this.gl.useProgram(this.program);
90
+ this.gl.drawArrays(this.gl.TRIANGLES, 0, this.verts.length / 3);
91
+ this.postDraw();
92
+ });
93
+ }
94
+ load() {
95
+ return __awaiter(this, void 0, void 0, function* () {
96
+ // empty
97
+ });
98
+ }
99
+ destroy() {
100
+ // empty
101
+ }
102
+ }
103
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVwbGFjZW1lbnQtcmVuZGVyZXIuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvbGliL3JlbmRlcmVyL3JlcGxhY2VtZW50LXJlbmRlcmVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7OztBQUVBLE9BQU8sRUFBRSxhQUFhLEVBQUUsV0FBVyxFQUFFLE1BQU0sU0FBUyxDQUFDO0FBR3JELE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSxrQkFBa0IsQ0FBQztBQUVqRCxNQUFNLE9BQU8sbUJBQW9CLFNBQVEsYUFBYTtJQWdDbEQsWUFBbUIsYUFBZ0MsRUFBa0IsTUFBc0I7UUFDdkYsS0FBSyxDQUFDLGFBQWEsRUFBRSxNQUFNLENBQUMsQ0FBQztRQURkLGtCQUFhLEdBQWIsYUFBYSxDQUFtQjtRQUFrQixXQUFNLEdBQU4sTUFBTSxDQUFnQjtRQTFCbkYsb0JBQWUsR0FBRzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7TUFvQnhCLElBQUksQ0FBQyxnQkFBZ0IsRUFBRTs7OztDQUk1QixDQUFDO1FBS00sTUFBTSxxQkFBcUIsR0FDdkIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUNmLENBQUMsVUFBVSxDQUFDLFVBQVUsQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUM5QixJQUFJLENBQUMscUJBQXFCLEVBQUU7WUFDeEIsTUFBTSxJQUFJLEtBQUssQ0FBQyx5REFBeUQsQ0FBQyxDQUFDO1NBQzlFO1FBQ0QsSUFBSSxDQUFDLHFCQUFxQixHQUFHLHFCQUFxQixDQUFDO1FBQ25ELE1BQU0sZUFBZSxHQUFHLElBQUksQ0FBQyxxQkFBcUIsQ0FBQyxZQUFZLENBQzNELENBQUMsRUFDRCxDQUFDLEVBQ0EsSUFBSSxDQUFDLE1BQU0sQ0FBQyxNQUE0QixDQUFDLFVBQVUsQ0FBQyxLQUFLLEVBQ3pELElBQUksQ0FBQyxNQUFNLENBQUMsTUFBNEIsQ0FBQyxVQUFVLENBQUMsTUFBTSxDQUM5RCxDQUFDLElBQUksQ0FBQztRQUVQLElBQUss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