@zappar/zappar-cv 3.0.1-alpha.17 → 3.0.1-alpha.19

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/README.md CHANGED
@@ -18,8 +18,8 @@ npm i @zappar/zappar-cv
18
18
 
19
19
  You can use our CDN from within your HTML:
20
20
  ```
21
- <script src="https://libs.zappar.com/zappar-cv/3.0.1-alpha.17/zappar-cv.js"></script>
21
+ <script src="https://libs.zappar.com/zappar-cv/3.0.1-alpha.19/zappar-cv.js"></script>
22
22
  ```
23
23
 
24
24
  Or you can download and host our standalone JavaScript bundle:
25
- [https://libs.zappar.com/zappar-cv/3.0.1-alpha.17/zappar-cv.zip](https://libs.zappar.com/zappar-cv/3.0.1-alpha.17/zappar-cv.zip)
25
+ [https://libs.zappar.com/zappar-cv/3.0.1-alpha.19/zappar-cv.zip](https://libs.zappar.com/zappar-cv/3.0.1-alpha.19/zappar-cv.zip)
package/lib/drawaxis.js CHANGED
@@ -16,9 +16,9 @@ function generate(gl) {
16
16
  if (!vbo)
17
17
  throw new Error("Unable to create buffer object");
18
18
  let coords = [
19
- 0, 0, 0, 1, 0, 0,
20
- 0, 0, 0, 0, 1, 0,
21
- 0, 0, 0, 0, 0, 1
19
+ 0, 0, 0, 0.1, 0, 0,
20
+ 0, 0, 0, 0, 0.1, 0,
21
+ 0, 0, 0, 0, 0, 0.1
22
22
  ];
23
23
  gl.bindBuffer(gl.ARRAY_BUFFER, vbo);
24
24
  gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(coords), gl.STATIC_DRAW);
@@ -58,7 +58,7 @@ export function drawAxis(gl, projectionMatrix, cameraMatrix, targetMatrix) {
58
58
  gl.bindBuffer(gl.ARRAY_BUFFER, uvbo);
59
59
  gl.vertexAttribPointer(shader.attr_color, 4, gl.FLOAT, false, 4 * 4, 0);
60
60
  gl.enableVertexAttribArray(shader.attr_color);
61
- gl.lineWidth(10);
61
+ gl.lineWidth(2);
62
62
  gl.drawArrays(gl.LINES, 0, 6);
63
63
  gl.disableVertexAttribArray(shader.attr_position);
64
64
  gl.disableVertexAttribArray(shader.attr_color);
@@ -135,38 +135,3 @@ function getShader(gl) {
135
135
  };
136
136
  return shader;
137
137
  }
138
- function loadTexture(gl, url) {
139
- if (texturesByUrl[url])
140
- return texturesByUrl[url];
141
- let texture = gl.createTexture();
142
- if (!texture)
143
- throw new Error("Unable to create texture");
144
- texturesByUrl[url] = texture;
145
- gl.bindTexture(gl.TEXTURE_2D, texture);
146
- // Because images have to be download over the internet
147
- // they might take a moment until they are ready.
148
- // Until then put a single pixel in the texture so we can
149
- // use it immediately. When the image has finished downloading
150
- // we'll update the texture with the contents of the image.
151
- const level = 0;
152
- const internalFormat = gl.RGBA;
153
- const width = 1;
154
- const height = 1;
155
- const border = 0;
156
- const srcFormat = gl.RGBA;
157
- const srcType = gl.UNSIGNED_BYTE;
158
- const pixel = new Uint8Array([0, 0, 255, 255]); // opaque blue
159
- gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, true);
160
- gl.texImage2D(gl.TEXTURE_2D, level, internalFormat, width, height, border, srcFormat, srcType, pixel);
161
- const image = new Image();
162
- image.onload = function () {
163
- gl.bindTexture(gl.TEXTURE_2D, texture);
164
- gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, true);
165
- gl.texImage2D(gl.TEXTURE_2D, level, internalFormat, srcFormat, srcType, image);
166
- gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
167
- gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
168
- gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
169
- };
170
- image.src = url;
171
- return texture;
172
- }
@@ -62,7 +62,7 @@ export interface zappar {
62
62
  pipeline_frame_number(o: zappar_pipeline_t): number;
63
63
  pipeline_camera_model(o: zappar_pipeline_t): Float32Array;
64
64
  pipeline_camera_frame_user_data(o: zappar_pipeline_t): number;
65
- pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean): void;
65
+ pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean, timestampSeconds: number): void;
66
66
  pipeline_camera_frame_camera_attitude(o: zappar_pipeline_t): Float32Array;
67
67
  pipeline_camera_frame_device_attitude(o: zappar_pipeline_t): Float32Array;
68
68
  pipeline_motion_accelerometer_submit(o: zappar_pipeline_t, time: number, x: number, y: number, z: number): void;
@@ -90,7 +90,7 @@ export class zappar_client {
90
90
  throw new Error("This object has been destroyed");
91
91
  return s.current_frame_user_data;
92
92
  },
93
- pipeline_camera_frame_submit: (o, data, width, height, user_data, camera_to_device_transform, camera_model, user_facing) => {
93
+ pipeline_camera_frame_submit: (o, data, width, height, user_data, camera_to_device_transform, camera_model, user_facing, timestampSeconds) => {
94
94
  let s = this._pipeline_state_by_instance.get(o);
95
95
  if (!s)
96
96
  throw new Error("This object has been destroyed");
@@ -103,6 +103,7 @@ export class zappar_client {
103
103
  m.matrix4x4(camera_to_device_transform);
104
104
  m.cameraModel(camera_model);
105
105
  m.bool(user_facing);
106
+ m.float(timestampSeconds);
106
107
  });
107
108
  },
108
109
  pipeline_camera_frame_camera_attitude: (o) => {
@@ -34,7 +34,7 @@ export function getRuntimeObject(mod) {
34
34
  ]);
35
35
  let pipeline_camera_frame_submit_wrapped = mod.cwrap("zappar_pipeline_camera_frame_submit", null, [
36
36
  "number",
37
- "number", "number", "number", "number", "number", "number", "number", "number"
37
+ "number", "number", "number", "number", "number", "number", "number", "number", "number"
38
38
  ]);
39
39
  let pipeline_camera_frame_submit_raw_pointer_wrapped = mod.cwrap("zappar_pipeline_camera_frame_submit_raw_pointer", null, [
40
40
  "number",
@@ -430,7 +430,7 @@ export function getRuntimeObject(mod) {
430
430
  let ret = pipeline_camera_frame_user_data_wrapped(o);
431
431
  return ret;
432
432
  },
433
- pipeline_camera_frame_submit: (o, data, width, height, user_data, camera_to_device_transform, camera_model, user_facing) => {
433
+ pipeline_camera_frame_submit: (o, data, width, height, user_data, camera_to_device_transform, camera_model, user_facing, timestampSeconds) => {
434
434
  if (dataArrayArgLength < data.byteLength) {
435
435
  mod._free(dataArrayArg);
436
436
  dataArrayArgLength = data.byteLength;
@@ -447,10 +447,11 @@ export function getRuntimeObject(mod) {
447
447
  let arg_camera_model = getFloatDataArrayForArgIndex(5, camera_model.byteLength);
448
448
  mod.HEAPF32.set(camera_model, arg_camera_model / 4);
449
449
  let arg_user_facing = user_facing ? 1 : 0;
450
- let ret = pipeline_camera_frame_submit_wrapped(o, arg_data, arg_len_data, arg_width, arg_height, arg_user_data, arg_camera_to_device_transform, arg_camera_model, arg_user_facing);
450
+ let arg_timestampSeconds = timestampSeconds;
451
+ let ret = pipeline_camera_frame_submit_wrapped(o, arg_data, arg_len_data, arg_width, arg_height, arg_user_data, arg_camera_to_device_transform, arg_camera_model, arg_user_facing, arg_timestampSeconds);
451
452
  return ret;
452
453
  },
453
- pipeline_camera_frame_submit_raw_pointer: (o, data, dataLength, format, width, height, user_data, camera_to_device_transform, rotation, camera_model, user_facing, timestamp, halfSample) => {
454
+ pipeline_camera_frame_submit_raw_pointer: (o, data, dataLength, format, width, height, user_data, camera_to_device_transform, rotation, camera_model, user_facing, timestampSeconds, halfSample) => {
454
455
  let arg_data = data;
455
456
  let arg_dataLength = dataLength;
456
457
  let arg_format = format;
@@ -463,9 +464,9 @@ export function getRuntimeObject(mod) {
463
464
  let arg_camera_model = getFloatDataArrayForArgIndex(8, camera_model.byteLength);
464
465
  mod.HEAPF32.set(camera_model, arg_camera_model / 4);
465
466
  let arg_user_facing = user_facing ? 1 : 0;
466
- let arg_timestamp = timestamp;
467
+ let arg_timestampSeconds = timestampSeconds;
467
468
  let arg_halfSample = halfSample ? 1 : 0;
468
- let ret = pipeline_camera_frame_submit_raw_pointer_wrapped(o, arg_data, arg_dataLength, arg_format, arg_width, arg_height, arg_user_data, arg_camera_to_device_transform, arg_rotation, arg_camera_model, arg_user_facing, arg_timestamp, arg_halfSample);
469
+ let ret = pipeline_camera_frame_submit_raw_pointer_wrapped(o, arg_data, arg_dataLength, arg_format, arg_width, arg_height, arg_user_data, arg_camera_to_device_transform, arg_rotation, arg_camera_model, arg_user_facing, arg_timestampSeconds, arg_halfSample);
469
470
  return ret;
470
471
  },
471
472
  pipeline_camera_frame_camera_attitude: (o) => {
@@ -136,8 +136,8 @@ export interface zappar_cwrap {
136
136
  pipeline_frame_number(o: zappar_pipeline_t): number;
137
137
  pipeline_camera_model(o: zappar_pipeline_t): Float32Array;
138
138
  pipeline_camera_frame_user_data(o: zappar_pipeline_t): number;
139
- pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean): void;
140
- pipeline_camera_frame_submit_raw_pointer(o: zappar_pipeline_t, data: number, dataLength: number, format: frame_pixel_format_t, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, rotation: number, camera_model: Float32Array, user_facing: boolean, timestamp: number, halfSample: boolean): void;
139
+ pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean, timestampSeconds: number): void;
140
+ pipeline_camera_frame_submit_raw_pointer(o: zappar_pipeline_t, data: number, dataLength: number, format: frame_pixel_format_t, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, rotation: number, camera_model: Float32Array, user_facing: boolean, timestampSeconds: number, halfSample: boolean): void;
141
141
  pipeline_camera_frame_camera_attitude(o: zappar_pipeline_t): Float32Array;
142
142
  pipeline_camera_frame_device_attitude(o: zappar_pipeline_t): Float32Array;
143
143
  pipeline_motion_accelerometer_submit(o: zappar_pipeline_t, time: number, x: number, y: number, z: number): void;
@@ -75,7 +75,7 @@ export class zappar_server {
75
75
  let obj = this._pipeline_by_instance.get(clientId);
76
76
  if (obj === undefined)
77
77
  return;
78
- this._impl.pipeline_camera_frame_submit(obj, msg.dataWithLength(), msg.int(), msg.int(), msg.int(), msg.matrix4x4(), msg.cameraModel(), msg.bool());
78
+ this._impl.pipeline_camera_frame_submit(obj, msg.dataWithLength(), msg.int(), msg.int(), msg.int(), msg.matrix4x4(), msg.cameraModel(), msg.bool(), msg.float());
79
79
  break;
80
80
  }
81
81
  case 10: {
@@ -91,7 +91,7 @@ export interface zappar {
91
91
  pipeline_camera_pose_with_attitude(o: zappar_pipeline_t, mirror: boolean): Float32Array;
92
92
  pipeline_camera_pose_with_origin(o: zappar_pipeline_t, pose: Float32Array): Float32Array;
93
93
  pipeline_camera_frame_user_data(o: zappar_pipeline_t): number;
94
- pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean): void;
94
+ pipeline_camera_frame_submit(o: zappar_pipeline_t, data: ArrayBuffer, width: number, height: number, user_data: number, camera_to_device_transform: Float32Array, camera_model: Float32Array, user_facing: boolean, timestampSeconds: number): void;
95
95
  pipeline_camera_frame_camera_attitude(o: zappar_pipeline_t): Float32Array;
96
96
  pipeline_camera_frame_device_attitude(o: zappar_pipeline_t): Float32Array;
97
97
  pipeline_camera_frame_user_facing(o: zappar_pipeline_t): boolean;
@@ -25,6 +25,7 @@ export declare class HTMLElementSource extends Source {
25
25
  start(): void;
26
26
  getFrame(currentlyProcessing: boolean): void;
27
27
  private _lastPresentedFrames;
28
+ private _frameTime;
28
29
  private _requestVideoFrameCallback;
29
30
  private _processFrame;
30
31
  uploadGL(): void;
@@ -78,6 +78,7 @@ export class HTMLElementSource extends Source {
78
78
  }
79
79
  }
80
80
  getFrame(currentlyProcessing) {
81
+ var _a;
81
82
  let pipeline = Pipeline.get(this._pipeline);
82
83
  if (!pipeline)
83
84
  return;
@@ -92,7 +93,7 @@ export class HTMLElementSource extends Source {
92
93
  let info = this._processFrame(gl, this._cameraToScreenRotation, currentlyProcessing);
93
94
  if (info) {
94
95
  let token = pipeline.registerToken(info);
95
- pipeline.sendDataToWorker(info.data || new ArrayBuffer(0), token, info.dataWidth, info.dataHeight, info.userFacing, info.cameraToDevice, info.cameraModel);
96
+ pipeline.sendDataToWorker(info.data || new ArrayBuffer(0), token, info.dataWidth, info.dataHeight, info.userFacing, info.cameraToDevice, info.cameraModel, (_a = this._frameTime) !== null && _a !== void 0 ? _a : performance.now());
96
97
  info.data = undefined;
97
98
  }
98
99
  }
@@ -106,6 +107,9 @@ export class HTMLElementSource extends Source {
106
107
  if (!(video === null || video === void 0 ? void 0 : video.requestVideoFrameCallback))
107
108
  return;
108
109
  video.requestVideoFrameCallback((time, metadata) => {
110
+ var _a;
111
+ if (typeof metadata === 'object')
112
+ this._frameTime = ((_a = metadata.captureTime) !== null && _a !== void 0 ? _a : -1) / 1000.0;
109
113
  if (typeof metadata === 'object' && typeof metadata.presentedFrames === 'number') {
110
114
  if (this._lastPresentedFrames === metadata.presentedFrames) {
111
115
  console.log('Avoided identical frame');
@@ -234,7 +234,8 @@ export class MSTPCameraSource extends Source {
234
234
  if (videoTracks.length > 0) {
235
235
  this._isUserFacing = videoTracks[0].getSettings().facingMode === "user";
236
236
  let processor = new MediaStreamTrackProcessor({
237
- track: videoTracks[0]
237
+ track: videoTracks[0],
238
+ maxBufferSize: 1
238
239
  });
239
240
  const str = this._currentStream;
240
241
  yield delay(1000);
package/lib/pipeline.d.ts CHANGED
@@ -78,6 +78,6 @@ export declare class Pipeline {
78
78
  sendCameraProfileToWorker(source: zappar_camera_source_t, profile: camera_profile_t): void;
79
79
  sendCameraToScreenRotationToWorker(rot: number): void;
80
80
  sendImageBitmapToWorker(img: ImageBitmap, rot: number, userFacing: boolean, tokenId: number, cameraModel: Float32Array, cameraToDevice: Float32Array, cp: camera_profile_t): void;
81
- sendDataToWorker(data: ArrayBuffer, token: number, width: number, height: number, userFacing: boolean, cameraToDevice: Float32Array, cameraModel: Float32Array): void;
81
+ sendDataToWorker(data: ArrayBuffer, token: number, width: number, height: number, userFacing: boolean, cameraToDevice: Float32Array, cameraModel: Float32Array, captureTime: number): void;
82
82
  }
83
83
  export declare function applyScreenCounterRotation(info: CameraFrameInfo | undefined, inp: Float32Array): Float32Array;
package/lib/pipeline.js CHANGED
@@ -479,14 +479,15 @@ export class Pipeline {
479
479
  };
480
480
  this._mgr.postOutgoingMessage(msg, [img]);
481
481
  }
482
- sendDataToWorker(data, token, width, height, userFacing, cameraToDevice, cameraModel) {
482
+ sendDataToWorker(data, token, width, height, userFacing, cameraToDevice, cameraModel, captureTime) {
483
483
  let msg = {
484
484
  d: data,
485
485
  p: this._impl,
486
486
  width, height, token, userFacing,
487
487
  c2d: cameraToDevice,
488
488
  cm: cameraModel,
489
- t: "cameraFrameC2S"
489
+ t: "cameraFrameC2S",
490
+ captureTime
490
491
  };
491
492
  this._mgr.postOutgoingMessage(msg, [data]);
492
493
  }
@@ -97,7 +97,7 @@ export class SequenceSource extends Source {
97
97
  // updates will be one frame later
98
98
  this._submitMotionUpdates(pipeline);
99
99
  const token = pipeline.registerToken(info);
100
- pipeline.sendDataToWorker(info.data || new ArrayBuffer(0), token, info.dataWidth, info.dataHeight, info.userFacing, info.cameraToDevice, info.cameraModel);
100
+ pipeline.sendDataToWorker(info.data || new ArrayBuffer(0), token, info.dataWidth, info.dataHeight, info.userFacing, info.cameraToDevice, info.cameraModel, -1);
101
101
  }
102
102
  destroy() {
103
103
  byId.delete(this._impl);
package/lib/version.d.ts CHANGED
@@ -1 +1 @@
1
- export declare const VERSION = "3.0.1-alpha.17";
1
+ export declare const VERSION = "3.0.1-alpha.19";
package/lib/version.js CHANGED
@@ -1 +1 @@
1
- export const VERSION = "3.0.1-alpha.17";
1
+ export const VERSION = "3.0.1-alpha.19";
@@ -53,7 +53,7 @@ export function handleImageBitmap(m, r, server, mgr) {
53
53
  mgr.postOutgoingMessage(msg, [m.i]);
54
54
  let pipeline = server._pipeline_by_instance.get(m.p);
55
55
  if (pipeline) {
56
- r.pipeline_camera_frame_submit(pipeline, pixels, info.dataWidth, info.dataHeight, m.tokenId, m.cameraToDevice, m.cameraModel, info.userFacing);
56
+ r.pipeline_camera_frame_submit(pipeline, pixels, info.dataWidth, info.dataHeight, m.tokenId, m.cameraToDevice, m.cameraModel, info.userFacing, performance.now());
57
57
  r.pipeline_frame_update(pipeline);
58
58
  server.exploreState();
59
59
  }
@@ -64,7 +64,7 @@ export function launchWorkerServer(wasmUrl, module, shouldRecordData) {
64
64
  let pipeline = server._pipeline_by_instance.get(msgt.p);
65
65
  let att;
66
66
  if (pipeline) {
67
- r.pipeline_camera_frame_submit(pipeline, msgt.d, msgt.width, msgt.height, msgt.token, msgt.c2d, msgt.cm, msgt.userFacing);
67
+ r.pipeline_camera_frame_submit(pipeline, msgt.d, msgt.width, msgt.height, msgt.token, msgt.c2d, msgt.cm, msgt.userFacing, msgt.captureTime);
68
68
  r.pipeline_frame_update(pipeline);
69
69
  att = r.pipeline_camera_frame_device_attitude(pipeline);
70
70
  server.exploreState();
@@ -288,7 +288,7 @@ function consumeReader(mod, r, reader, p, userFacing, server, source, workerMess
288
288
  const pipeline = server._pipeline_by_instance.get(p);
289
289
  if (pipeline) {
290
290
  try {
291
- r.pipeline_camera_frame_submit_raw_pointer(pipeline, streamDataBufferPointer, size, framePixelFormatFromFormat(frame.format), width, height, token, cameraToDeviceTransform, latestCameraToScreenRotation, cameraModel, userFacing, (_b = frame.timestamp) !== null && _b !== void 0 ? _b : -1, downSample);
291
+ r.pipeline_camera_frame_submit_raw_pointer(pipeline, streamDataBufferPointer, size, framePixelFormatFromFormat(frame.format), width, height, token, cameraToDeviceTransform, latestCameraToScreenRotation, cameraModel, userFacing, ((_b = frame.timestamp) !== null && _b !== void 0 ? _b : -1) * 1e-6, downSample);
292
292
  handleMessages(mod, workerMessageAPI);
293
293
  if (dataDownloadAPI)
294
294
  handleDataDownload(mod, dataDownloadAPI);
@@ -11,6 +11,7 @@ export interface CameraFrameC2S {
11
11
  token: number;
12
12
  width: number;
13
13
  height: number;
14
+ captureTime: number;
14
15
  }
15
16
  export interface CameraFrameReturnS2C {
16
17
  t: "cameraFrameRecycleS2C";
Binary file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@zappar/zappar-cv",
3
- "version": "3.0.1-alpha.17",
3
+ "version": "3.0.1-alpha.19",
4
4
  "description": "Zappar's core computer vision library, supporting image, face and world tracking.",
5
5
  "main": "lib/index.js",
6
6
  "types": "lib/index.d.ts",