@wemap/camera 3.2.5 → 3.2.8
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/debug/dist/index.html +2 -1
- package/debug/dist/qr-code-scanner.html +115 -0
- package/index.js +6 -1
- package/package.json +3 -3
- package/src/Camera.js +25 -13
- package/src/QrCodeScanner.js +149 -0
- package/src/SharedCameras.js +57 -0
- package/src/CameraLogger.js +0 -120
package/debug/dist/index.html
CHANGED
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
|
|
4
|
+
<head>
|
|
5
|
+
<meta charset="UTF-8">
|
|
6
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
7
|
+
<title>Camera</title>
|
|
8
|
+
|
|
9
|
+
<script src="/js/camera-lib.js"></script>
|
|
10
|
+
|
|
11
|
+
<style type="text/css">
|
|
12
|
+
html,
|
|
13
|
+
body {
|
|
14
|
+
height: 100%;
|
|
15
|
+
margin: 0px;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
#camera-container {
|
|
19
|
+
width: 100%;
|
|
20
|
+
height: 100%;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
#controls {
|
|
24
|
+
position: absolute;
|
|
25
|
+
bottom: 0;
|
|
26
|
+
z-index: 2;
|
|
27
|
+
margin: 5px;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
#controls>div {
|
|
31
|
+
background: #ffffffaa;
|
|
32
|
+
padding-left: 10px;
|
|
33
|
+
padding-right: 10px;
|
|
34
|
+
min-width: 100px;
|
|
35
|
+
display: inline-block;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
#scan-result {
|
|
39
|
+
position: absolute;
|
|
40
|
+
border: 1px solid black;
|
|
41
|
+
background: white;
|
|
42
|
+
top: 0;
|
|
43
|
+
width: 150px;
|
|
44
|
+
left: 50%;
|
|
45
|
+
transform: translate(-50%, 0%);
|
|
46
|
+
z-index: 2;
|
|
47
|
+
text-align: center;
|
|
48
|
+
line-height: 30px;
|
|
49
|
+
vertical-align: middle;
|
|
50
|
+
}
|
|
51
|
+
</style>
|
|
52
|
+
</head>
|
|
53
|
+
|
|
54
|
+
<body>
|
|
55
|
+
|
|
56
|
+
<div id="camera-container"></div>
|
|
57
|
+
<div id="scan-result">Waiting</div>
|
|
58
|
+
<div id="controls">
|
|
59
|
+
<div id="camera-handler">
|
|
60
|
+
<div class="title">Camera</div>
|
|
61
|
+
<button id="start-camera">Start</button>
|
|
62
|
+
<button id="stop-camera" disabled>Stop</button>
|
|
63
|
+
</div>
|
|
64
|
+
<div id="qrcode-handler">
|
|
65
|
+
<div class="title">Scanner</div>
|
|
66
|
+
<button id="start-scanner">Start</button>
|
|
67
|
+
<button id="stop-scanner" disabled>Stop</button>
|
|
68
|
+
</div>
|
|
69
|
+
</div>
|
|
70
|
+
|
|
71
|
+
|
|
72
|
+
<script>
|
|
73
|
+
/* global Camera, QrCodeScanner */
|
|
74
|
+
|
|
75
|
+
const cameraContainer = document.getElementById('camera-container');
|
|
76
|
+
const scanResultContainer = document.getElementById('scan-result');
|
|
77
|
+
const startCameraButton = document.getElementById('start-camera');
|
|
78
|
+
const stopCameraButton = document.getElementById('stop-camera');
|
|
79
|
+
const startScannerButton = document.getElementById('start-scanner');
|
|
80
|
+
const stopScannerButton = document.getElementById('stop-scanner');
|
|
81
|
+
|
|
82
|
+
const camera = new Camera(cameraContainer);
|
|
83
|
+
const qrCodeScanner = new QrCodeScanner(camera);
|
|
84
|
+
qrCodeScanner.on('scan', str => (scanResultContainer.innerHTML = str));
|
|
85
|
+
|
|
86
|
+
|
|
87
|
+
startCameraButton.addEventListener('click', () => {
|
|
88
|
+
camera.start();
|
|
89
|
+
startCameraButton.disabled = true;
|
|
90
|
+
stopCameraButton.disabled = false;
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
stopCameraButton.addEventListener('click', () => {
|
|
94
|
+
camera.stop();
|
|
95
|
+
startCameraButton.disabled = false;
|
|
96
|
+
stopCameraButton.disabled = true;
|
|
97
|
+
});
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
startScannerButton.addEventListener('click', () => {
|
|
101
|
+
qrCodeScanner.start();
|
|
102
|
+
startScannerButton.disabled = true;
|
|
103
|
+
stopScannerButton.disabled = false;
|
|
104
|
+
});
|
|
105
|
+
|
|
106
|
+
stopScannerButton.addEventListener('click', () => {
|
|
107
|
+
qrCodeScanner.stop();
|
|
108
|
+
startScannerButton.disabled = false;
|
|
109
|
+
stopScannerButton.disabled = true;
|
|
110
|
+
scanResultContainer.innerHTML = 'Waiting';
|
|
111
|
+
});
|
|
112
|
+
</script>
|
|
113
|
+
</body>
|
|
114
|
+
|
|
115
|
+
</html>
|
package/index.js
CHANGED
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
import { BarcodeFormat } from '@zxing/library';
|
|
1
2
|
import Camera from './src/Camera.js';
|
|
3
|
+
import QrCodeScanner from './src/QrCodeScanner.js';
|
|
4
|
+
import SharedCameras from './src/SharedCameras.js';
|
|
2
5
|
|
|
3
|
-
export {
|
|
6
|
+
export {
|
|
7
|
+
BarcodeFormat, Camera, QrCodeScanner, SharedCameras
|
|
8
|
+
};
|
package/package.json
CHANGED
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
"directory": "packages/camera"
|
|
12
12
|
},
|
|
13
13
|
"name": "@wemap/camera",
|
|
14
|
-
"version": "3.2.
|
|
14
|
+
"version": "3.2.8",
|
|
15
15
|
"bugs": {
|
|
16
16
|
"url": "https://github.com/wemap/wemap-modules-js/issues"
|
|
17
17
|
},
|
|
@@ -23,9 +23,9 @@
|
|
|
23
23
|
],
|
|
24
24
|
"license": "ISC",
|
|
25
25
|
"dependencies": {
|
|
26
|
-
"@
|
|
26
|
+
"@zxing/library": "^0.17.1",
|
|
27
27
|
"events": "^3.1.0"
|
|
28
28
|
},
|
|
29
29
|
"type": "module",
|
|
30
|
-
"gitHead": "
|
|
30
|
+
"gitHead": "fb5e61f42479a69332c2e3e6922bd15e4d3ee3f3"
|
|
31
31
|
}
|
package/src/Camera.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import EventEmitter from 'events';
|
|
2
2
|
|
|
3
|
-
import
|
|
3
|
+
import SharedCameras from './SharedCameras.js';
|
|
4
4
|
|
|
5
5
|
const GENERIC_HARDWARE_VERTICAL_FOV = 60;
|
|
6
6
|
|
|
@@ -31,16 +31,20 @@ class Camera extends EventEmitter {
|
|
|
31
31
|
|
|
32
32
|
fov = null;
|
|
33
33
|
|
|
34
|
-
|
|
34
|
+
_isStarted = false;
|
|
35
35
|
|
|
36
36
|
_hardwareVerticalFov = GENERIC_HARDWARE_VERTICAL_FOV;
|
|
37
37
|
_resizeOnWindowChange;
|
|
38
38
|
|
|
39
|
-
|
|
40
|
-
|
|
39
|
+
/**
|
|
40
|
+
* @param {Node} container
|
|
41
|
+
* @param {boolean} resizeOnWindowChange
|
|
42
|
+
*/
|
|
41
43
|
constructor(container, resizeOnWindowChange = false) {
|
|
42
44
|
super();
|
|
43
45
|
|
|
46
|
+
SharedCameras._add(this, container);
|
|
47
|
+
|
|
44
48
|
this.videoContainer = container;
|
|
45
49
|
this._resizeOnWindowChange = resizeOnWindowChange;
|
|
46
50
|
|
|
@@ -52,17 +56,15 @@ class Camera extends EventEmitter {
|
|
|
52
56
|
this.videoElement.setAttribute('muted', '');
|
|
53
57
|
this.videoElement.setAttribute('playsinline', '');
|
|
54
58
|
this.videoContainer.appendChild(this.videoElement);
|
|
55
|
-
|
|
56
|
-
this._cameraLogger = new CameraLogger();
|
|
57
59
|
}
|
|
58
60
|
|
|
59
61
|
async start() {
|
|
60
62
|
|
|
61
|
-
if (this.
|
|
63
|
+
if (this._isStarted) {
|
|
62
64
|
throw new Error('Camera is already started');
|
|
63
65
|
}
|
|
64
66
|
|
|
65
|
-
this.
|
|
67
|
+
this._isStarted = true;
|
|
66
68
|
|
|
67
69
|
await Camera.checkAvailability();
|
|
68
70
|
|
|
@@ -82,16 +84,19 @@ class Camera extends EventEmitter {
|
|
|
82
84
|
window.addEventListener('resize', this.notifyContainerSizeChanged);
|
|
83
85
|
}
|
|
84
86
|
|
|
85
|
-
this.
|
|
87
|
+
this.emit('start', {
|
|
88
|
+
videoElement: this.videoElement,
|
|
89
|
+
stream
|
|
90
|
+
});
|
|
86
91
|
}
|
|
87
92
|
|
|
88
93
|
async stop() {
|
|
89
94
|
|
|
90
|
-
if (!this.
|
|
95
|
+
if (!this._isStarted) {
|
|
91
96
|
throw new Error('Camera is not started yet');
|
|
92
97
|
}
|
|
93
98
|
|
|
94
|
-
this.
|
|
99
|
+
this.emit('stop');
|
|
95
100
|
|
|
96
101
|
if (this.videoStream && this.videoStream.stop) {
|
|
97
102
|
// compatibility with old JS API
|
|
@@ -106,7 +111,11 @@ class Camera extends EventEmitter {
|
|
|
106
111
|
if (this._resizeOnWindowChange) {
|
|
107
112
|
window.removeEventListener('resize', this.notifyContainerSizeChanged);
|
|
108
113
|
}
|
|
109
|
-
this.
|
|
114
|
+
this._isStarted = false;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
release() {
|
|
118
|
+
SharedCameras._remove(this);
|
|
110
119
|
}
|
|
111
120
|
|
|
112
121
|
static async checkAvailability(testUserMedia = false) {
|
|
@@ -138,6 +147,10 @@ class Camera extends EventEmitter {
|
|
|
138
147
|
}
|
|
139
148
|
}
|
|
140
149
|
|
|
150
|
+
get isStarted() {
|
|
151
|
+
return this._isStarted;
|
|
152
|
+
}
|
|
153
|
+
|
|
141
154
|
set hardwareVerticalFov(hardwareVerticalFov) {
|
|
142
155
|
this._hardwareVerticalFov = hardwareVerticalFov;
|
|
143
156
|
this._computeFov();
|
|
@@ -209,7 +222,6 @@ class Camera extends EventEmitter {
|
|
|
209
222
|
horizontal: fovH
|
|
210
223
|
};
|
|
211
224
|
|
|
212
|
-
this._cameraLogger.fov = this.fov;
|
|
213
225
|
this.emit('fov.changed', this.fov);
|
|
214
226
|
}
|
|
215
227
|
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
/* eslint-disable max-statements */
|
|
2
|
+
import EventEmitter from 'events';
|
|
3
|
+
import {
|
|
4
|
+
MultiFormatReader,
|
|
5
|
+
BarcodeFormat,
|
|
6
|
+
DecodeHintType,
|
|
7
|
+
RGBLuminanceSource,
|
|
8
|
+
BinaryBitmap,
|
|
9
|
+
HybridBinarizer
|
|
10
|
+
} from '@zxing/library';
|
|
11
|
+
|
|
12
|
+
import Camera from './Camera.js';
|
|
13
|
+
|
|
14
|
+
class QrCodeScanner extends EventEmitter {
|
|
15
|
+
|
|
16
|
+
static DEFAULT_FORMATS = [
|
|
17
|
+
BarcodeFormat.QR_CODE,
|
|
18
|
+
BarcodeFormat.DATA_MATRIX,
|
|
19
|
+
BarcodeFormat.CODABAR
|
|
20
|
+
];
|
|
21
|
+
|
|
22
|
+
/**
|
|
23
|
+
* @type {Camera}
|
|
24
|
+
*/
|
|
25
|
+
_camera;
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* @type {HTMLVideoElement}
|
|
29
|
+
*/
|
|
30
|
+
_videoElement;
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* @type {HTMLCanvasElement}
|
|
34
|
+
*/
|
|
35
|
+
_canvas;
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* @type {CanvasRenderingContext2D}
|
|
39
|
+
*/
|
|
40
|
+
_ctx;
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* @type {MultiFormatReader}
|
|
44
|
+
*/
|
|
45
|
+
_codeReader;
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* @type {number}
|
|
49
|
+
*/
|
|
50
|
+
_intervalTime;
|
|
51
|
+
|
|
52
|
+
/**
|
|
53
|
+
* @type {number}
|
|
54
|
+
*/
|
|
55
|
+
_intervalTick;
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* @type {boolean}
|
|
59
|
+
*/
|
|
60
|
+
_isStarted = false;
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* @param {Camera} camera
|
|
65
|
+
*/
|
|
66
|
+
constructor(camera) {
|
|
67
|
+
super();
|
|
68
|
+
|
|
69
|
+
this._camera = camera;
|
|
70
|
+
this._videoElement = camera.videoElement;
|
|
71
|
+
|
|
72
|
+
this._codeReader = new MultiFormatReader();
|
|
73
|
+
|
|
74
|
+
this._canvas = document.createElement('canvas');
|
|
75
|
+
this._ctx = this._canvas.getContext('2d');
|
|
76
|
+
|
|
77
|
+
this._camera.on('start', () => this._tryStart());
|
|
78
|
+
this._camera.on('stop', () => this._stop());
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
start(intervalTime = 500, formats = QrCodeScanner.DEFAULT_FORMATS) {
|
|
82
|
+
this._intervalTime = intervalTime;
|
|
83
|
+
|
|
84
|
+
if (this._isStarted) {
|
|
85
|
+
return;
|
|
86
|
+
}
|
|
87
|
+
this._isStarted = true;
|
|
88
|
+
|
|
89
|
+
const hints = new Map();
|
|
90
|
+
hints.set(DecodeHintType.POSSIBLE_FORMATS, formats);
|
|
91
|
+
this._codeReader.setHints(hints);
|
|
92
|
+
|
|
93
|
+
this._tryStart();
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
stop() {
|
|
97
|
+
this._isStarted = false;
|
|
98
|
+
this._stop();
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
_tryStart() {
|
|
102
|
+
|
|
103
|
+
if (!this._isStarted || !this._camera.isStarted) {
|
|
104
|
+
return;
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
this._width = this._videoElement.videoWidth;
|
|
108
|
+
this._height = this._videoElement.videoHeight;
|
|
109
|
+
this._canvas.width = this._width;
|
|
110
|
+
this._canvas.height = this._height;
|
|
111
|
+
this._luminances = new Uint8Array(this._width * this._height);
|
|
112
|
+
|
|
113
|
+
this._intervalTick = setInterval(() => this._onFrame(), this._intervalTime);
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
_stop() {
|
|
117
|
+
clearInterval(this._intervalTick);
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
_onFrame() {
|
|
121
|
+
|
|
122
|
+
if (!this._width || !this._height) {
|
|
123
|
+
return;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
this._ctx.drawImage(this._videoElement, 0, 0, this._width, this._height);
|
|
127
|
+
const img = this._ctx.getImageData(0, 0, this._width, this._height);
|
|
128
|
+
|
|
129
|
+
for (let i = 0; i < this._luminances.length; i++) {
|
|
130
|
+
// eslint-disable-next-line no-bitwise
|
|
131
|
+
this._luminances[i] = ((img.data[i * 4] + img.data[i * 4 + 1] * 2 + img.data[i * 4 + 2]) / 4) & 0xFF;
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
const binaryBitmap = new BinaryBitmap(
|
|
135
|
+
new HybridBinarizer(
|
|
136
|
+
new RGBLuminanceSource(this._luminances, this._width, this._height)
|
|
137
|
+
)
|
|
138
|
+
);
|
|
139
|
+
|
|
140
|
+
try {
|
|
141
|
+
const result = this._codeReader.decodeWithState(binaryBitmap);
|
|
142
|
+
this.emit('scan', result.getText());
|
|
143
|
+
} catch (e) {
|
|
144
|
+
// do nothing
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
export default QrCodeScanner;
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { EventEmitter } from 'events';
|
|
2
|
+
|
|
3
|
+
import Camera from './Camera.js';
|
|
4
|
+
|
|
5
|
+
class SharedCameras extends EventEmitter {
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Singleton pattern.
|
|
9
|
+
* @returns {SharedCameras}
|
|
10
|
+
*/
|
|
11
|
+
static get instance() {
|
|
12
|
+
if (!this._instance) {
|
|
13
|
+
this._instance = new SharedCameras();
|
|
14
|
+
}
|
|
15
|
+
return this._instance;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
_list = [];
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* @param {Camera} camera
|
|
22
|
+
* @param {Node}
|
|
23
|
+
*/
|
|
24
|
+
_add(camera, container) {
|
|
25
|
+
const obj = {
|
|
26
|
+
camera,
|
|
27
|
+
container
|
|
28
|
+
};
|
|
29
|
+
this._list.push(obj);
|
|
30
|
+
this.emit('added', obj);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* @param {Camera} camera
|
|
35
|
+
*/
|
|
36
|
+
_remove(camera) {
|
|
37
|
+
this._list = this._list.filter(({ camera: _camera }) => _camera !== camera);
|
|
38
|
+
this.emit('removed', camera);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
get list() {
|
|
42
|
+
return this._list;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
getCameraByContainer(container) {
|
|
46
|
+
for (const {
|
|
47
|
+
camera, container: _container
|
|
48
|
+
} of this._list) {
|
|
49
|
+
if (container === _container) {
|
|
50
|
+
return camera;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
return null;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
export default SharedCameras.instance;
|
package/src/CameraLogger.js
DELETED
|
@@ -1,120 +0,0 @@
|
|
|
1
|
-
import { NavigationLogger } from '@wemap/navigation-logger';
|
|
2
|
-
import { TimeUtils } from '@wemap/utils';
|
|
3
|
-
|
|
4
|
-
class CameraLogger {
|
|
5
|
-
|
|
6
|
-
static _videoPart = 0;
|
|
7
|
-
|
|
8
|
-
_videoStream = null;
|
|
9
|
-
|
|
10
|
-
constructor() {
|
|
11
|
-
|
|
12
|
-
NavigationLogger.on('started', () => {
|
|
13
|
-
CameraLogger._videoPart = 0;
|
|
14
|
-
if (this._videoStream !== null) {
|
|
15
|
-
this._start();
|
|
16
|
-
}
|
|
17
|
-
});
|
|
18
|
-
|
|
19
|
-
NavigationLogger.on('stopped', () => {
|
|
20
|
-
this._stop();
|
|
21
|
-
});
|
|
22
|
-
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
attachStream(videoStream) {
|
|
26
|
-
this._videoStream = videoStream;
|
|
27
|
-
if (NavigationLogger.isRecording) {
|
|
28
|
-
this._start();
|
|
29
|
-
}
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
detachStream() {
|
|
33
|
-
this._videoStream = null;
|
|
34
|
-
this._stop();
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
set fov(fov) {
|
|
38
|
-
this._fov = fov;
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
_start() {
|
|
42
|
-
CameraLogger._videoPart++;
|
|
43
|
-
|
|
44
|
-
if (!('MediaRecorder' in window)) {
|
|
45
|
-
return;
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
if (this.mediaRecorder) {
|
|
49
|
-
throw new Error('CameraLogger is already recording');
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
const options = {
|
|
53
|
-
mimeType: 'video/webm;codecs=vp8',
|
|
54
|
-
bitsPerSecond: NavigationLogger.params.videoBitrate
|
|
55
|
-
};
|
|
56
|
-
|
|
57
|
-
let isFirstChunck = true;
|
|
58
|
-
|
|
59
|
-
const startTime = TimeUtils.preciseTime;
|
|
60
|
-
|
|
61
|
-
// https://stackoverflow.com/questions/56826079/how-to-concat-chunks-of-incoming-binary-into-video-webm-file-node-js
|
|
62
|
-
this.mediaRecorder = new MediaRecorder(this._videoStream, options);
|
|
63
|
-
this.mediaRecorder.ondataavailable = event => {
|
|
64
|
-
if (event.data && event.data.size > 0) {
|
|
65
|
-
if (isFirstChunck) {
|
|
66
|
-
this._sendEvent('video-start', {
|
|
67
|
-
// startTime: TimeUtils.preciseTime - NavigationLogger.params.flushInterval,
|
|
68
|
-
startTime,
|
|
69
|
-
part: CameraLogger._videoPart,
|
|
70
|
-
fov: this._fov
|
|
71
|
-
});
|
|
72
|
-
isFirstChunck = false;
|
|
73
|
-
}
|
|
74
|
-
this._sendChunck(CameraLogger._videoPart, event.data);
|
|
75
|
-
}
|
|
76
|
-
};
|
|
77
|
-
|
|
78
|
-
this.mediaRecorder.start(NavigationLogger.params.flushInterval);
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
_stop() {
|
|
83
|
-
|
|
84
|
-
if (!this.mediaRecorder) {
|
|
85
|
-
return;
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
this._sendEvent('video-end', {
|
|
89
|
-
time: TimeUtils.preciseTime,
|
|
90
|
-
part: CameraLogger._videoPart
|
|
91
|
-
});
|
|
92
|
-
|
|
93
|
-
this.mediaRecorder.stop();
|
|
94
|
-
this.mediaRecorder = null;
|
|
95
|
-
}
|
|
96
|
-
|
|
97
|
-
_sendChunck(videoPart, chunck) {
|
|
98
|
-
fetch(NavigationLogger.getVideoChunckUrl(videoPart), {
|
|
99
|
-
method: 'POST',
|
|
100
|
-
headers: { 'Content-Type': 'application/octet-stream' },
|
|
101
|
-
body: chunck
|
|
102
|
-
});
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
_sendEvent(eventName, data) {
|
|
106
|
-
fetch(NavigationLogger.getVideoConfigUrl(), {
|
|
107
|
-
method: 'POST',
|
|
108
|
-
headers: {
|
|
109
|
-
'Accept': 'application/json',
|
|
110
|
-
'Content-Type': 'application/json'
|
|
111
|
-
},
|
|
112
|
-
body: JSON.stringify({
|
|
113
|
-
eventName,
|
|
114
|
-
data
|
|
115
|
-
})
|
|
116
|
-
});
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
export default CameraLogger;
|