@jaak.ai/stamps 2.0.0-dev.28 → 2.0.0-dev.30
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/cjs/jaak-stamps.cjs.entry.js +189 -72
- package/dist/cjs/jaak-stamps.cjs.entry.js.map +1 -1
- package/dist/cjs/jaak-stamps.entry.cjs.js.map +1 -1
- package/dist/collection/components/my-component/my-component.js +189 -72
- package/dist/collection/components/my-component/my-component.js.map +1 -1
- package/dist/components/jaak-stamps.js +189 -72
- package/dist/components/jaak-stamps.js.map +1 -1
- package/dist/esm/jaak-stamps.entry.js +189 -72
- package/dist/esm/jaak-stamps.entry.js.map +1 -1
- package/dist/jaak-stamps-webcomponent/jaak-stamps-webcomponent.esm.js +1 -1
- package/dist/jaak-stamps-webcomponent/jaak-stamps.entry.esm.js.map +1 -1
- package/dist/jaak-stamps-webcomponent/p-b62b53f8.entry.js +2 -0
- package/dist/jaak-stamps-webcomponent/p-b62b53f8.entry.js.map +1 -0
- package/dist/types/components/my-component/my-component.d.ts +2 -1
- package/package.json +1 -1
- package/dist/jaak-stamps-webcomponent/p-67b8e4cf.entry.js +0 -2
- package/dist/jaak-stamps-webcomponent/p-67b8e4cf.entry.js.map +0 -1
|
@@ -61,41 +61,72 @@ export class JaakStamps {
|
|
|
61
61
|
preprocessCtx;
|
|
62
62
|
captureCanvas;
|
|
63
63
|
captureCtx;
|
|
64
|
-
MODEL_PATH = "https://storage.googleapis.com/jaak-static/web/component/stamps/ddmyp-
|
|
64
|
+
MODEL_PATH = "https://storage.googleapis.com/jaak-static/web/component/stamps/ddmyp-v2.onnx";
|
|
65
65
|
MOBILENET_MODEL_PATH = "https://storage.googleapis.com/jaak-static/web/component/stamps/cdmmp-v1.onnx";
|
|
66
66
|
MOBILENET_CLASSES_PATH = "https://storage.googleapis.com/jaak-static/web/component/stamps/cdmmp-v1.json";
|
|
67
67
|
INPUT_SIZE = 320;
|
|
68
68
|
CONFIDENCE_THRESHOLD = 0.6;
|
|
69
69
|
// ISO/IEC 7810 ID-1 standard dimensions (85.60mm x 53.98mm)
|
|
70
70
|
ID1_ASPECT_RATIO = 85.60 / 53.98; // 1.5863320574...
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
71
|
+
logger = {
|
|
72
|
+
info: (...args) => {
|
|
73
|
+
if (this.debug) {
|
|
74
|
+
console.log(`[JAAK-STAMPS] [INFO] [${new Date().toLocaleTimeString()}]`, ...args);
|
|
75
|
+
}
|
|
76
|
+
},
|
|
77
|
+
warn: (...args) => {
|
|
78
|
+
if (this.debug) {
|
|
79
|
+
console.warn(`[JAAK-STAMPS] [WARN] [${new Date().toLocaleTimeString()}]`, ...args);
|
|
80
|
+
}
|
|
81
|
+
},
|
|
82
|
+
error: (...args) => {
|
|
83
|
+
if (this.debug) {
|
|
84
|
+
console.error(`[JAAK-STAMPS] [ERROR] [${new Date().toLocaleTimeString()}]`, ...args);
|
|
85
|
+
}
|
|
86
|
+
},
|
|
87
|
+
debug: (...args) => {
|
|
88
|
+
if (this.debug) {
|
|
89
|
+
console.debug(`[JAAK-STAMPS] [DEBUG] [${new Date().toLocaleTimeString()}]`, ...args);
|
|
90
|
+
}
|
|
91
|
+
},
|
|
92
|
+
state: (state, data) => {
|
|
93
|
+
if (this.debug) {
|
|
94
|
+
console.log(`[JAAK-STAMPS] [STATE] [${new Date().toLocaleTimeString()}] ${state}`, data || '');
|
|
95
|
+
}
|
|
96
|
+
},
|
|
97
|
+
performance: (operation, duration) => {
|
|
98
|
+
if (this.debug) {
|
|
99
|
+
console.log(`[JAAK-STAMPS] [PERF] [${new Date().toLocaleTimeString()}] ${operation}: ${duration}ms`);
|
|
100
|
+
}
|
|
74
101
|
}
|
|
75
|
-
}
|
|
102
|
+
};
|
|
76
103
|
validateMaskSize() {
|
|
77
104
|
if (this.maskSize < 50 || this.maskSize > 100) {
|
|
78
|
-
|
|
105
|
+
this.logger.warn(`Propiedad maskSize inválida. Valor: ${this.maskSize}, esperado: 50-100. Usando valor por defecto: 90`);
|
|
79
106
|
this.maskSize = 90;
|
|
80
107
|
}
|
|
81
108
|
}
|
|
82
109
|
validateCropMargin() {
|
|
83
110
|
if (this.cropMargin < 0 || this.cropMargin > 100) {
|
|
84
|
-
|
|
111
|
+
this.logger.warn(`Propiedad cropMargin inválida. Valor: ${this.cropMargin}, esperado: 0-100. Usando valor por defecto: 0`);
|
|
85
112
|
this.cropMargin = 0;
|
|
86
113
|
}
|
|
87
114
|
}
|
|
88
115
|
validatePreferredCamera() {
|
|
89
116
|
const validOptions = ['auto', 'front', 'back'];
|
|
90
117
|
if (!validOptions.includes(this.preferredCamera)) {
|
|
91
|
-
|
|
118
|
+
this.logger.warn(`Propiedad preferredCamera inválida. Valor: ${this.preferredCamera}, esperado: ${validOptions.join(', ')}. Usando valor por defecto: 'auto'`);
|
|
92
119
|
this.preferredCamera = 'auto';
|
|
93
120
|
}
|
|
94
121
|
}
|
|
95
122
|
emitReadyEvent() {
|
|
96
123
|
const isDocumentReady = !!window.ort && this.isModelPreloaded;
|
|
97
124
|
this.isReady.emit(isDocumentReady);
|
|
98
|
-
this.
|
|
125
|
+
this.logger.state('COMPONENTE_LISTO', {
|
|
126
|
+
ortLibraryLoaded: !!window.ort,
|
|
127
|
+
modelPreloaded: this.isModelPreloaded,
|
|
128
|
+
isReady: isDocumentReady
|
|
129
|
+
});
|
|
99
130
|
}
|
|
100
131
|
isRearCamera(stream) {
|
|
101
132
|
const videoTrack = stream.getVideoTracks()[0];
|
|
@@ -118,7 +149,11 @@ export class JaakStamps {
|
|
|
118
149
|
else {
|
|
119
150
|
this.deviceType = 'desktop';
|
|
120
151
|
}
|
|
121
|
-
this.
|
|
152
|
+
this.logger.state('DISPOSITIVO_DETECTADO', {
|
|
153
|
+
deviceType: this.deviceType,
|
|
154
|
+
userAgent: navigator.userAgent,
|
|
155
|
+
screenDimensions: { width: window.innerWidth, height: window.innerHeight }
|
|
156
|
+
});
|
|
122
157
|
// Enumerate available cameras
|
|
123
158
|
await this.enumerateAndDetectCameras();
|
|
124
159
|
// Load user preference
|
|
@@ -129,7 +164,7 @@ export class JaakStamps {
|
|
|
129
164
|
// First, check if we have permission to enumerate devices
|
|
130
165
|
const permissionStatus = await this.checkCameraPermission();
|
|
131
166
|
if (permissionStatus === 'denied') {
|
|
132
|
-
this.
|
|
167
|
+
this.logger.error('Permiso de cámara denegado por el usuario');
|
|
133
168
|
this.statusMessage = "Permiso de cámara denegado";
|
|
134
169
|
this.statusColor = "#ff6b6b";
|
|
135
170
|
return;
|
|
@@ -143,7 +178,7 @@ export class JaakStamps {
|
|
|
143
178
|
const devices = await navigator.mediaDevices.enumerateDevices();
|
|
144
179
|
this.availableCameras = devices.filter(device => device.kind === 'videoinput');
|
|
145
180
|
this.isMultipleCamerasAvailable = this.availableCameras.length > 1;
|
|
146
|
-
this.
|
|
181
|
+
this.logger.state('CAMARAS_DETECTADAS', {
|
|
147
182
|
count: this.availableCameras.length,
|
|
148
183
|
isMultipleCamerasAvailable: this.isMultipleCamerasAvailable,
|
|
149
184
|
cameras: this.availableCameras.map(cam => ({
|
|
@@ -155,7 +190,7 @@ export class JaakStamps {
|
|
|
155
190
|
this.setInitialCameraPreference();
|
|
156
191
|
}
|
|
157
192
|
catch (error) {
|
|
158
|
-
this.
|
|
193
|
+
this.logger.error('Error al enumerar cámaras disponibles:', error);
|
|
159
194
|
this.handleCameraPermissionError(error);
|
|
160
195
|
}
|
|
161
196
|
}
|
|
@@ -168,7 +203,7 @@ export class JaakStamps {
|
|
|
168
203
|
return permission.state;
|
|
169
204
|
}
|
|
170
205
|
catch (error) {
|
|
171
|
-
this.
|
|
206
|
+
this.logger.warn('No se pudo verificar permisos de cámara:', error);
|
|
172
207
|
return 'prompt';
|
|
173
208
|
}
|
|
174
209
|
}
|
|
@@ -211,11 +246,11 @@ export class JaakStamps {
|
|
|
211
246
|
!camera.label.toLowerCase().includes('back') && !camera.label.toLowerCase().includes('rear'));
|
|
212
247
|
if (frontCamera) {
|
|
213
248
|
this.selectedCameraId = frontCamera.deviceId;
|
|
214
|
-
this.
|
|
249
|
+
this.logger.state('CAMARA_FRONTAL_SELECCIONADA', { label: frontCamera.label, deviceId: frontCamera.deviceId });
|
|
215
250
|
}
|
|
216
251
|
else {
|
|
217
252
|
this.selectedCameraId = this.availableCameras[0].deviceId;
|
|
218
|
-
this.
|
|
253
|
+
this.logger.warn('Cámara frontal no encontrada, usando primera disponible:', this.availableCameras[0].label);
|
|
219
254
|
}
|
|
220
255
|
}
|
|
221
256
|
else if (this.preferredCamera === 'back') {
|
|
@@ -226,11 +261,11 @@ export class JaakStamps {
|
|
|
226
261
|
camera.label.toLowerCase().includes('environment'));
|
|
227
262
|
if (backCamera) {
|
|
228
263
|
this.selectedCameraId = backCamera.deviceId;
|
|
229
|
-
this.
|
|
264
|
+
this.logger.state('CAMARA_TRASERA_SELECCIONADA', { label: backCamera.label, deviceId: backCamera.deviceId });
|
|
230
265
|
}
|
|
231
266
|
else {
|
|
232
267
|
this.selectedCameraId = this.availableCameras[0].deviceId;
|
|
233
|
-
this.
|
|
268
|
+
this.logger.warn('Cámara trasera no encontrada, usando primera disponible:', this.availableCameras[0].label);
|
|
234
269
|
}
|
|
235
270
|
}
|
|
236
271
|
else {
|
|
@@ -243,17 +278,17 @@ export class JaakStamps {
|
|
|
243
278
|
camera.label.toLowerCase().includes('environment'));
|
|
244
279
|
if (rearCamera) {
|
|
245
280
|
this.selectedCameraId = rearCamera.deviceId;
|
|
246
|
-
this.
|
|
281
|
+
this.logger.state('CAMARA_AUTO_SELECCIONADA_MOBILE', { type: 'rear', label: rearCamera.label, deviceId: rearCamera.deviceId });
|
|
247
282
|
}
|
|
248
283
|
else {
|
|
249
284
|
this.selectedCameraId = this.availableCameras[0].deviceId;
|
|
250
|
-
this.
|
|
285
|
+
this.logger.warn('Cámara trasera no encontrada en mobile, usando primera disponible:', this.availableCameras[0].label);
|
|
251
286
|
}
|
|
252
287
|
}
|
|
253
288
|
else {
|
|
254
289
|
// For desktop, use first available camera (usually the only one)
|
|
255
290
|
this.selectedCameraId = this.availableCameras[0].deviceId;
|
|
256
|
-
this.
|
|
291
|
+
this.logger.state('CAMARA_AUTO_SELECCIONADA_DESKTOP', { label: this.availableCameras[0].label, deviceId: this.availableCameras[0].deviceId });
|
|
257
292
|
}
|
|
258
293
|
}
|
|
259
294
|
}
|
|
@@ -267,12 +302,12 @@ export class JaakStamps {
|
|
|
267
302
|
if (isStillAvailable) {
|
|
268
303
|
this.selectedCameraId = preference.cameraId;
|
|
269
304
|
this.preferredCameraFacing = preference.facing;
|
|
270
|
-
this.
|
|
305
|
+
this.logger.state('PREFERENCIA_CAMARA_CARGADA', preference);
|
|
271
306
|
}
|
|
272
307
|
}
|
|
273
308
|
}
|
|
274
309
|
catch (error) {
|
|
275
|
-
this.
|
|
310
|
+
this.logger.warn('Error al cargar preferencia de cámara:', error);
|
|
276
311
|
}
|
|
277
312
|
}
|
|
278
313
|
saveCameraPreference() {
|
|
@@ -283,10 +318,10 @@ export class JaakStamps {
|
|
|
283
318
|
timestamp: Date.now()
|
|
284
319
|
};
|
|
285
320
|
localStorage.setItem('jaak-stamps-camera-preference', JSON.stringify(preference));
|
|
286
|
-
this.
|
|
321
|
+
this.logger.state('PREFERENCIA_CAMARA_GUARDADA', preference);
|
|
287
322
|
}
|
|
288
323
|
catch (error) {
|
|
289
|
-
this.
|
|
324
|
+
this.logger.warn('Error al guardar preferencia de cámara:', error);
|
|
290
325
|
}
|
|
291
326
|
}
|
|
292
327
|
async switchCamera(cameraId) {
|
|
@@ -296,7 +331,7 @@ export class JaakStamps {
|
|
|
296
331
|
// Check if the selected camera is still available
|
|
297
332
|
const selectedCamera = this.availableCameras.find(cam => cam.deviceId === cameraId);
|
|
298
333
|
if (!selectedCamera) {
|
|
299
|
-
this.
|
|
334
|
+
this.logger.warn('Cámara seleccionada no encontrada, re-enumerando dispositivos...');
|
|
300
335
|
await this.enumerateAndDetectCameras();
|
|
301
336
|
return;
|
|
302
337
|
}
|
|
@@ -320,10 +355,10 @@ export class JaakStamps {
|
|
|
320
355
|
this.saveCameraPreference();
|
|
321
356
|
// Setup new camera with error handling
|
|
322
357
|
await this.setupCameraWithRetry();
|
|
323
|
-
this.
|
|
358
|
+
this.logger.state('CAMARA_CAMBIADA', { label: selectedCamera.label, deviceId: selectedCamera.deviceId });
|
|
324
359
|
}
|
|
325
360
|
catch (error) {
|
|
326
|
-
this.
|
|
361
|
+
this.logger.error('Error al cambiar de cámara:', error);
|
|
327
362
|
this.handleCameraPermissionError(error);
|
|
328
363
|
}
|
|
329
364
|
}
|
|
@@ -338,7 +373,7 @@ export class JaakStamps {
|
|
|
338
373
|
return; // Success
|
|
339
374
|
}
|
|
340
375
|
catch (error) {
|
|
341
|
-
this.
|
|
376
|
+
this.logger.error(`Intento ${attempt} de configuración de cámara fallido:`, error);
|
|
342
377
|
if (attempt === maxRetries) {
|
|
343
378
|
// Last attempt failed, handle the error
|
|
344
379
|
this.statusMessage = "Error al configurar la cámara";
|
|
@@ -358,7 +393,7 @@ export class JaakStamps {
|
|
|
358
393
|
}
|
|
359
394
|
toggleCameraSelector() {
|
|
360
395
|
this.showCameraSelector = !this.showCameraSelector;
|
|
361
|
-
this.
|
|
396
|
+
this.logger.state('SELECTOR_CAMARA_TOGGLE', {
|
|
362
397
|
showCameraSelector: this.showCameraSelector,
|
|
363
398
|
isMultipleCamerasAvailable: this.isMultipleCamerasAvailable,
|
|
364
399
|
availableCameras: this.availableCameras.length,
|
|
@@ -374,6 +409,13 @@ export class JaakStamps {
|
|
|
374
409
|
await this.switchCamera(nextCamera.deviceId);
|
|
375
410
|
}
|
|
376
411
|
async componentDidLoad() {
|
|
412
|
+
this.logger.state('COMPONENTE_INICIALIZANDO', {
|
|
413
|
+
debug: this.debug,
|
|
414
|
+
maskSize: this.maskSize,
|
|
415
|
+
cropMargin: this.cropMargin,
|
|
416
|
+
useDocumentClassification: this.useDocumentClassification,
|
|
417
|
+
preferredCamera: this.preferredCamera
|
|
418
|
+
});
|
|
377
419
|
if (this.debug) {
|
|
378
420
|
// Show detailed initialization loading state only in debug mode
|
|
379
421
|
this.isLoading = true;
|
|
@@ -438,7 +480,7 @@ export class JaakStamps {
|
|
|
438
480
|
this.canvasRef.height = rect.height;
|
|
439
481
|
// Update mask positioning based on container and video dimensions
|
|
440
482
|
this.updateMaskDimensions(rect);
|
|
441
|
-
this.
|
|
483
|
+
this.logger.debug('Canvas redimensionado:', { width: rect.width, height: rect.height });
|
|
442
484
|
}
|
|
443
485
|
}
|
|
444
486
|
updateMaskDimensions(containerRect) {
|
|
@@ -498,7 +540,7 @@ export class JaakStamps {
|
|
|
498
540
|
this.el.style.setProperty('--mask-center-y', `${videoCenterYPercent}%`);
|
|
499
541
|
// Mark mask as ready now that dimensions are calculated
|
|
500
542
|
this.isMaskReady = true;
|
|
501
|
-
this.
|
|
543
|
+
this.logger.state('DIMENSIONES_MASCARA_ACTUALIZADAS', {
|
|
502
544
|
video: { width: videoWidth, height: videoHeight },
|
|
503
545
|
displayed: { width: displayedVideoWidth, height: displayedVideoHeight },
|
|
504
546
|
mask: { widthPercent: maskWidthPercent, heightPercent: maskHeightPercent },
|
|
@@ -520,7 +562,7 @@ export class JaakStamps {
|
|
|
520
562
|
this.captureCtx = this.captureCanvas.getContext('2d', {
|
|
521
563
|
alpha: false
|
|
522
564
|
});
|
|
523
|
-
this.
|
|
565
|
+
this.logger.state('CANVAS_POOL_INICIALIZADO', { preprocessCanvasSize: this.INPUT_SIZE });
|
|
524
566
|
}
|
|
525
567
|
disconnectedCallback() {
|
|
526
568
|
this.cleanup();
|
|
@@ -568,7 +610,7 @@ export class JaakStamps {
|
|
|
568
610
|
}
|
|
569
611
|
async preloadModel() {
|
|
570
612
|
if (this.isModelPreloaded || this.session) {
|
|
571
|
-
this.
|
|
613
|
+
this.logger.state('MODELO_YA_PRECARGADO', { sessionExists: !!this.session, modelPreloaded: this.isModelPreloaded });
|
|
572
614
|
return { success: true, message: 'Model already loaded' };
|
|
573
615
|
}
|
|
574
616
|
try {
|
|
@@ -576,7 +618,7 @@ export class JaakStamps {
|
|
|
576
618
|
this.statusMessage = "Precargando modelos...";
|
|
577
619
|
this.statusColor = "#007bff";
|
|
578
620
|
const modelPath = this.MODEL_PATH;
|
|
579
|
-
this.
|
|
621
|
+
this.logger.state('PRECARGANDO_MODELO_DETECCION', { modelPath });
|
|
580
622
|
// Configure ONNX Runtime with device-specific optimizations
|
|
581
623
|
const sessionOptions = this.getSessionOptions();
|
|
582
624
|
const deviceInfo = this.getDeviceMemoryInfo();
|
|
@@ -585,7 +627,7 @@ export class JaakStamps {
|
|
|
585
627
|
}
|
|
586
628
|
catch (error) {
|
|
587
629
|
if (error.message.includes('failed to allocate a buffer')) {
|
|
588
|
-
this.
|
|
630
|
+
this.logger.warn('Fallo en asignación de buffer durante precarga, intentando con configuración mínima');
|
|
589
631
|
const fallbackOptions = {
|
|
590
632
|
executionProviders: ['wasm'],
|
|
591
633
|
graphOptimizationLevel: 'disabled',
|
|
@@ -606,7 +648,7 @@ export class JaakStamps {
|
|
|
606
648
|
// For low memory devices, load sequentially to avoid memory pressure
|
|
607
649
|
if (this.useDocumentClassification) {
|
|
608
650
|
if (deviceInfo.isLowMemory) {
|
|
609
|
-
this.
|
|
651
|
+
this.logger.state('CARGA_SECUENCIAL_MODELOS', { reason: 'low memory device' });
|
|
610
652
|
await new Promise(resolve => setTimeout(resolve, 1000));
|
|
611
653
|
}
|
|
612
654
|
await this.loadMobileNetModel();
|
|
@@ -616,11 +658,15 @@ export class JaakStamps {
|
|
|
616
658
|
this.statusMessage = "Modelos precargados. Listo para comenzar detección";
|
|
617
659
|
this.statusColor = "#28a745";
|
|
618
660
|
this.emitReadyEvent();
|
|
619
|
-
this.
|
|
661
|
+
this.logger.state('MODELOS_PRECARGADOS_EXITOSAMENTE', {
|
|
662
|
+
detectionModel: !!this.session,
|
|
663
|
+
classificationModel: !!this.mobileNetSession,
|
|
664
|
+
useClassification: this.useDocumentClassification
|
|
665
|
+
});
|
|
620
666
|
return { success: true, message: 'Models preloaded successfully' };
|
|
621
667
|
}
|
|
622
668
|
catch (error) {
|
|
623
|
-
this.
|
|
669
|
+
this.logger.error('Error al precargar modelos:', error);
|
|
624
670
|
this.isLoading = false;
|
|
625
671
|
this.statusMessage = "Error al precargar los modelos";
|
|
626
672
|
this.statusColor = "#ff6b6b";
|
|
@@ -648,7 +694,7 @@ export class JaakStamps {
|
|
|
648
694
|
}
|
|
649
695
|
async setPreferredCamera(camera) {
|
|
650
696
|
this.preferredCamera = camera;
|
|
651
|
-
this.
|
|
697
|
+
this.logger.state('PREFERENCIA_CAMARA_CAMBIADA', { newPreference: camera });
|
|
652
698
|
// Re-detect and apply new camera preference
|
|
653
699
|
await this.enumerateAndDetectCameras();
|
|
654
700
|
// If video is active, switch to the new preferred camera
|
|
@@ -663,14 +709,14 @@ export class JaakStamps {
|
|
|
663
709
|
}
|
|
664
710
|
async loadMobileNetModel() {
|
|
665
711
|
try {
|
|
666
|
-
this.
|
|
712
|
+
this.logger.state('CARGANDO_MODELO_MOBILENET', { path: this.MOBILENET_MODEL_PATH });
|
|
667
713
|
// Load class map
|
|
668
714
|
const classResponse = await fetch(this.MOBILENET_CLASSES_PATH);
|
|
669
715
|
if (!classResponse.ok) {
|
|
670
716
|
throw new Error(`Failed to load class map: ${this.MOBILENET_CLASSES_PATH}`);
|
|
671
717
|
}
|
|
672
718
|
this.mobileNetClassMap = await classResponse.json();
|
|
673
|
-
this.
|
|
719
|
+
this.logger.state('CLASES_MOBILENET_CARGADAS', { classCount: Object.keys(this.mobileNetClassMap).length });
|
|
674
720
|
// Load model
|
|
675
721
|
const sessionOptions = this.getSessionOptions();
|
|
676
722
|
try {
|
|
@@ -678,7 +724,7 @@ export class JaakStamps {
|
|
|
678
724
|
}
|
|
679
725
|
catch (error) {
|
|
680
726
|
if (error.message.includes('failed to allocate a buffer')) {
|
|
681
|
-
this.
|
|
727
|
+
this.logger.warn('Fallo en asignación de buffer de MobileNet, intentando con configuración mínima');
|
|
682
728
|
const fallbackOptions = {
|
|
683
729
|
executionProviders: ['wasm'],
|
|
684
730
|
graphOptimizationLevel: 'disabled',
|
|
@@ -695,10 +741,10 @@ export class JaakStamps {
|
|
|
695
741
|
throw error;
|
|
696
742
|
}
|
|
697
743
|
}
|
|
698
|
-
this.
|
|
744
|
+
this.logger.state('MODELO_MOBILENET_CARGADO_EXITOSAMENTE', { sessionCreated: !!this.mobileNetSession });
|
|
699
745
|
}
|
|
700
746
|
catch (error) {
|
|
701
|
-
this.
|
|
747
|
+
this.logger.error('Error al cargar modelo MobileNet:', error);
|
|
702
748
|
throw error;
|
|
703
749
|
}
|
|
704
750
|
}
|
|
@@ -725,11 +771,11 @@ export class JaakStamps {
|
|
|
725
771
|
}
|
|
726
772
|
async classifyDocument(canvas) {
|
|
727
773
|
if (!this.mobileNetSession || !this.mobileNetClassMap) {
|
|
728
|
-
this.
|
|
774
|
+
this.logger.warn('Modelo MobileNet no está cargado, saltando clasificación');
|
|
729
775
|
return null;
|
|
730
776
|
}
|
|
731
777
|
try {
|
|
732
|
-
this.
|
|
778
|
+
this.logger.state('CLASIFICANDO_DOCUMENTO', { timestamp: Date.now() });
|
|
733
779
|
// Preprocess image for MobileNet
|
|
734
780
|
const inputTensor = this.preprocessMobileNet(canvas);
|
|
735
781
|
// Run inference
|
|
@@ -740,10 +786,11 @@ export class JaakStamps {
|
|
|
740
786
|
const maxIdx = output.reduce((bestIdx, val, idx, arr) => val > arr[bestIdx] ? idx : bestIdx, 0);
|
|
741
787
|
const confidence = output[maxIdx];
|
|
742
788
|
const className = this.mobileNetClassMap[maxIdx.toString()] || "unknown";
|
|
743
|
-
this.
|
|
789
|
+
this.logger.state('DOCUMENTO_CLASIFICADO', {
|
|
744
790
|
class: className,
|
|
745
791
|
confidence: confidence.toFixed(3),
|
|
746
|
-
classIndex: maxIdx
|
|
792
|
+
classIndex: maxIdx,
|
|
793
|
+
timestamp: Date.now()
|
|
747
794
|
});
|
|
748
795
|
return {
|
|
749
796
|
class: className,
|
|
@@ -752,7 +799,7 @@ export class JaakStamps {
|
|
|
752
799
|
};
|
|
753
800
|
}
|
|
754
801
|
catch (error) {
|
|
755
|
-
this.
|
|
802
|
+
this.logger.error('Error al clasificar documento:', error);
|
|
756
803
|
return null;
|
|
757
804
|
}
|
|
758
805
|
}
|
|
@@ -794,7 +841,7 @@ export class JaakStamps {
|
|
|
794
841
|
}
|
|
795
842
|
this.mobileNetClassMap = undefined;
|
|
796
843
|
this.isModelPreloaded = false;
|
|
797
|
-
this.
|
|
844
|
+
this.logger.state('CANVAS_POOL_LIMPIADO', { timestamp: Date.now() });
|
|
798
845
|
}
|
|
799
846
|
async getMaxResolution() {
|
|
800
847
|
try {
|
|
@@ -844,18 +891,19 @@ export class JaakStamps {
|
|
|
844
891
|
constraints.width = { ideal: maxWidth };
|
|
845
892
|
constraints.height = { ideal: maxHeight };
|
|
846
893
|
}
|
|
847
|
-
this.
|
|
894
|
+
this.logger.state('CAPACIDADES_RESOLUCION_DETECTADAS', {
|
|
848
895
|
maxWidth: capabilities.width.max,
|
|
849
896
|
maxHeight: capabilities.height.max,
|
|
850
897
|
selectedWidth: constraints.width.ideal,
|
|
851
898
|
selectedHeight: constraints.height.ideal,
|
|
852
|
-
isTablet
|
|
899
|
+
isTablet,
|
|
900
|
+
deviceType: this.deviceType
|
|
853
901
|
});
|
|
854
902
|
}
|
|
855
903
|
return constraints;
|
|
856
904
|
}
|
|
857
905
|
catch (err) {
|
|
858
|
-
this.
|
|
906
|
+
this.logger.warn('No se pudieron obtener capacidades de cámara, usando configuración de respaldo');
|
|
859
907
|
// Optimized fallback for tablets
|
|
860
908
|
const isTablet = /iPad|Android/i.test(navigator.userAgent) && window.innerWidth >= 768;
|
|
861
909
|
const fallbackConstraints = {
|
|
@@ -888,8 +936,11 @@ export class JaakStamps {
|
|
|
888
936
|
// Determine if video should be mirrored
|
|
889
937
|
const isRear = this.isRearCamera(stream);
|
|
890
938
|
this.shouldMirrorVideo = !isRear;
|
|
891
|
-
this.
|
|
892
|
-
|
|
939
|
+
this.logger.state('CAMARA_CONFIGURADA', {
|
|
940
|
+
isRearCamera: isRear,
|
|
941
|
+
shouldMirrorVideo: this.shouldMirrorVideo,
|
|
942
|
+
videoActive: this.isVideoActive
|
|
943
|
+
});
|
|
893
944
|
return new Promise((resolve) => {
|
|
894
945
|
this.videoRef.onloadedmetadata = async () => {
|
|
895
946
|
await this.videoRef.play();
|
|
@@ -906,7 +957,7 @@ export class JaakStamps {
|
|
|
906
957
|
}
|
|
907
958
|
}
|
|
908
959
|
catch (err) {
|
|
909
|
-
this.
|
|
960
|
+
this.logger.error('No se pudo acceder a la cámara:', err);
|
|
910
961
|
this.handleCameraPermissionError(err);
|
|
911
962
|
}
|
|
912
963
|
}
|
|
@@ -928,7 +979,37 @@ export class JaakStamps {
|
|
|
928
979
|
B.push(data[i + 2] / 255);
|
|
929
980
|
}
|
|
930
981
|
const transposedData = new Float32Array(R.concat(G, B));
|
|
931
|
-
|
|
982
|
+
// Convert to float16 for the lighter model
|
|
983
|
+
const float16Data = new Uint16Array(transposedData.length);
|
|
984
|
+
for (let i = 0; i < transposedData.length; i++) {
|
|
985
|
+
float16Data[i] = this.float32ToFloat16(transposedData[i]);
|
|
986
|
+
}
|
|
987
|
+
return new window.ort.Tensor("float16", float16Data, [1, 3, this.INPUT_SIZE, this.INPUT_SIZE]);
|
|
988
|
+
}
|
|
989
|
+
float32ToFloat16(value) {
|
|
990
|
+
// Convert float32 to float16 using IEEE 754 half precision format
|
|
991
|
+
const buffer = new ArrayBuffer(4);
|
|
992
|
+
const view = new DataView(buffer);
|
|
993
|
+
view.setFloat32(0, value, true);
|
|
994
|
+
const f = view.getUint32(0, true);
|
|
995
|
+
const sign = (f >> 31) & 0x1;
|
|
996
|
+
const exp = (f >> 23) & 0xFF;
|
|
997
|
+
const frac = f & 0x7FFFFF;
|
|
998
|
+
let newExp = exp - 127 + 15;
|
|
999
|
+
if (exp === 0) {
|
|
1000
|
+
newExp = 0;
|
|
1001
|
+
}
|
|
1002
|
+
else if (exp === 0xFF) {
|
|
1003
|
+
newExp = 0x1F;
|
|
1004
|
+
}
|
|
1005
|
+
else if (newExp >= 0x1F) {
|
|
1006
|
+
newExp = 0x1F;
|
|
1007
|
+
return (sign << 15) | (newExp << 10);
|
|
1008
|
+
}
|
|
1009
|
+
else if (newExp <= 0) {
|
|
1010
|
+
return (sign << 15);
|
|
1011
|
+
}
|
|
1012
|
+
return (sign << 15) | (newExp << 10) | (frac >> 13);
|
|
932
1013
|
}
|
|
933
1014
|
getDeviceMemoryInfo() {
|
|
934
1015
|
const nav = navigator;
|
|
@@ -972,6 +1053,12 @@ export class JaakStamps {
|
|
|
972
1053
|
};
|
|
973
1054
|
}
|
|
974
1055
|
async startDetection() {
|
|
1056
|
+
this.logger.state('INICIANDO_DETECCION', {
|
|
1057
|
+
sessionExists: !!this.session,
|
|
1058
|
+
modelPreloaded: this.isModelPreloaded,
|
|
1059
|
+
videoActive: this.isVideoActive,
|
|
1060
|
+
captureStep: this.captureStep
|
|
1061
|
+
});
|
|
975
1062
|
try {
|
|
976
1063
|
// Check if model is already preloaded
|
|
977
1064
|
if (!this.session) {
|
|
@@ -985,14 +1072,14 @@ export class JaakStamps {
|
|
|
985
1072
|
this.statusColor = "#007bff";
|
|
986
1073
|
}
|
|
987
1074
|
const modelPath = this.MODEL_PATH;
|
|
988
|
-
this.
|
|
1075
|
+
this.logger.state('CARGANDO_MODELO_DETECCION', { modelPath });
|
|
989
1076
|
const sessionOptions = this.getSessionOptions();
|
|
990
1077
|
try {
|
|
991
1078
|
this.session = await window.ort.InferenceSession.create(modelPath, sessionOptions);
|
|
992
1079
|
}
|
|
993
1080
|
catch (error) {
|
|
994
1081
|
if (error.message.includes('failed to allocate a buffer')) {
|
|
995
|
-
this.
|
|
1082
|
+
this.logger.warn('Fallo en asignación de buffer, intentando con configuración mínima');
|
|
996
1083
|
const fallbackOptions = {
|
|
997
1084
|
executionProviders: ['wasm'],
|
|
998
1085
|
graphOptimizationLevel: 'disabled',
|
|
@@ -1023,7 +1110,7 @@ export class JaakStamps {
|
|
|
1023
1110
|
this.emitReadyEvent();
|
|
1024
1111
|
}
|
|
1025
1112
|
else {
|
|
1026
|
-
this.
|
|
1113
|
+
this.logger.state('USANDO_MODELOS_PRECARGADOS', { sessionExists: !!this.session, modelPreloaded: this.isModelPreloaded });
|
|
1027
1114
|
if (this.debug) {
|
|
1028
1115
|
this.statusMessage = "Usando modelos precargados...";
|
|
1029
1116
|
this.statusColor = "#007bff";
|
|
@@ -1042,7 +1129,7 @@ export class JaakStamps {
|
|
|
1042
1129
|
this.detectFrame();
|
|
1043
1130
|
}
|
|
1044
1131
|
catch (err) {
|
|
1045
|
-
this.
|
|
1132
|
+
this.logger.error('Error al inicializar detección:', err);
|
|
1046
1133
|
this.statusMessage = "Error al inicializar el detector";
|
|
1047
1134
|
this.statusColor = "#ff6b6b";
|
|
1048
1135
|
this.isLoading = false;
|
|
@@ -1124,7 +1211,7 @@ export class JaakStamps {
|
|
|
1124
1211
|
}
|
|
1125
1212
|
}
|
|
1126
1213
|
catch (e) {
|
|
1127
|
-
this.
|
|
1214
|
+
this.logger.error('Error en inferencia de modelo:', e);
|
|
1128
1215
|
// Solo continuar si no hemos completado el proceso
|
|
1129
1216
|
if (this.captureStep !== 'completed') {
|
|
1130
1217
|
// On error, wait longer before retrying
|
|
@@ -1252,7 +1339,7 @@ export class JaakStamps {
|
|
|
1252
1339
|
if (!this.hasScreenshotTaken) {
|
|
1253
1340
|
this.lastDetectedBox = bestBox;
|
|
1254
1341
|
this.takeScreenshot().catch(error => {
|
|
1255
|
-
this.
|
|
1342
|
+
this.logger.error('Error al tomar captura de pantalla:', error);
|
|
1256
1343
|
});
|
|
1257
1344
|
this.hasScreenshotTaken = true;
|
|
1258
1345
|
// Reset para permitir segunda captura
|
|
@@ -1270,6 +1357,7 @@ export class JaakStamps {
|
|
|
1270
1357
|
if (boxes.length === 0) {
|
|
1271
1358
|
this.statusMessage = "Posicione la identificación dentro del marco";
|
|
1272
1359
|
this.statusColor = "#ff6b6b";
|
|
1360
|
+
this.logger.debug('Sin detección de documento en el frame');
|
|
1273
1361
|
}
|
|
1274
1362
|
else {
|
|
1275
1363
|
const bestBox = boxes.reduce((best, current) => current.score > best.score ? current : best);
|
|
@@ -1279,6 +1367,11 @@ export class JaakStamps {
|
|
|
1279
1367
|
if (allSidesAligned) {
|
|
1280
1368
|
this.statusMessage = "Identificación perfectamente alineada. Mantenga inmóvil";
|
|
1281
1369
|
this.statusColor = "#00ff00";
|
|
1370
|
+
this.logger.state('DOCUMENTO_PERFECTAMENTE_ALINEADO', {
|
|
1371
|
+
score: bestBox.score,
|
|
1372
|
+
boxDimensions: { width: bestBox.w, height: bestBox.h },
|
|
1373
|
+
alignedSides: 4
|
|
1374
|
+
});
|
|
1282
1375
|
}
|
|
1283
1376
|
else if (alignedSides > 0) {
|
|
1284
1377
|
this.statusMessage = `Alinee los lados restantes (${alignedSides}/4 lados correctos)`;
|
|
@@ -1339,6 +1432,14 @@ export class JaakStamps {
|
|
|
1339
1432
|
async takeScreenshot() {
|
|
1340
1433
|
if (!this.videoRef || !this.lastDetectedBox)
|
|
1341
1434
|
return;
|
|
1435
|
+
this.logger.state('INICIANDO_CAPTURA', {
|
|
1436
|
+
captureStep: this.captureStep,
|
|
1437
|
+
detectedBox: this.lastDetectedBox,
|
|
1438
|
+
videoResolution: {
|
|
1439
|
+
width: this.videoRef.videoWidth,
|
|
1440
|
+
height: this.videoRef.videoHeight
|
|
1441
|
+
}
|
|
1442
|
+
});
|
|
1342
1443
|
// Activar animación
|
|
1343
1444
|
this.triggerCaptureAnimation();
|
|
1344
1445
|
// OPTIMIZATION: Reuse capture canvas for full frame
|
|
@@ -1378,7 +1479,7 @@ export class JaakStamps {
|
|
|
1378
1479
|
await this.loadMobileNetModel();
|
|
1379
1480
|
}
|
|
1380
1481
|
catch (error) {
|
|
1381
|
-
this.
|
|
1482
|
+
this.logger.warn('Fallo al cargar modelo de clasificación, continuando sin clasificación:', error);
|
|
1382
1483
|
}
|
|
1383
1484
|
}
|
|
1384
1485
|
// Classify the cropped document if model is available
|
|
@@ -1386,7 +1487,7 @@ export class JaakStamps {
|
|
|
1386
1487
|
const classification = await this.classifyDocument(croppedCanvas);
|
|
1387
1488
|
if (classification && classification.class === 'passport') {
|
|
1388
1489
|
// If it's a passport, skip back capture since passports don't have a back side
|
|
1389
|
-
this.
|
|
1490
|
+
this.logger.state('PASAPORTE_DETECTADO_SALTANDO_REVERSO', { classification: classification?.class });
|
|
1390
1491
|
this.completeProcess(true);
|
|
1391
1492
|
return;
|
|
1392
1493
|
}
|
|
@@ -1407,14 +1508,23 @@ export class JaakStamps {
|
|
|
1407
1508
|
this.isDetectionPaused = false;
|
|
1408
1509
|
}, 3000);
|
|
1409
1510
|
}, 800);
|
|
1410
|
-
this.
|
|
1511
|
+
this.logger.state('CAPTURA_FRENTE_COMPLETADA', {
|
|
1512
|
+
captureStep: this.captureStep,
|
|
1513
|
+
hasFullFrame: !!this.capturedFullFrame,
|
|
1514
|
+
hasCroppedId: !!this.capturedCroppedId
|
|
1515
|
+
});
|
|
1411
1516
|
}
|
|
1412
1517
|
else if (this.captureStep === 'back') {
|
|
1413
1518
|
// Captura de la trasera usando canvas reutilizado
|
|
1414
1519
|
this.capturedBackFullFrame = this.captureCanvas.toDataURL('image/png');
|
|
1415
1520
|
this.capturedBackCroppedId = croppedCanvas.toDataURL('image/png');
|
|
1416
1521
|
this.completeProcess(false);
|
|
1417
|
-
this.
|
|
1522
|
+
this.logger.state('CAPTURA_TRASERA_COMPLETADA', {
|
|
1523
|
+
captureStep: this.captureStep,
|
|
1524
|
+
hasBackFullFrame: !!this.capturedBackFullFrame,
|
|
1525
|
+
hasBackCroppedId: !!this.capturedBackCroppedId,
|
|
1526
|
+
processCompleted: true
|
|
1527
|
+
});
|
|
1418
1528
|
}
|
|
1419
1529
|
}
|
|
1420
1530
|
triggerCaptureAnimation() {
|
|
@@ -1438,7 +1548,7 @@ export class JaakStamps {
|
|
|
1438
1548
|
const ctx = this.canvasRef.getContext("2d");
|
|
1439
1549
|
ctx.clearRect(0, 0, this.canvasRef.width, this.canvasRef.height);
|
|
1440
1550
|
}
|
|
1441
|
-
this.
|
|
1551
|
+
this.logger.state('DETECTOR_DETENIDO', { timestamp: Date.now() });
|
|
1442
1552
|
}
|
|
1443
1553
|
resetDetection() {
|
|
1444
1554
|
this.bestScore = 0;
|
|
@@ -1477,6 +1587,13 @@ export class JaakStamps {
|
|
|
1477
1587
|
"Proceso completado (solo frente capturado)" :
|
|
1478
1588
|
"Proceso de captura completado exitosamente";
|
|
1479
1589
|
this.statusColor = "#28a745";
|
|
1590
|
+
this.logger.state('PROCESO_COMPLETADO', {
|
|
1591
|
+
skippedBack,
|
|
1592
|
+
hasFrontImages: !!(this.capturedFullFrame && this.capturedCroppedId),
|
|
1593
|
+
hasBackImages: !!(this.capturedBackFullFrame && this.capturedBackCroppedId),
|
|
1594
|
+
totalImages: skippedBack ? 2 : 4,
|
|
1595
|
+
timestamp: new Date().toISOString()
|
|
1596
|
+
});
|
|
1480
1597
|
// Detener el detector
|
|
1481
1598
|
this.stopDetection();
|
|
1482
1599
|
// Emitir evento con las imágenes capturadas
|
|
@@ -1528,7 +1645,7 @@ export class JaakStamps {
|
|
|
1528
1645
|
this.cleanup();
|
|
1529
1646
|
}
|
|
1530
1647
|
render() {
|
|
1531
|
-
return (h("div", { key: '
|
|
1648
|
+
return (h("div", { key: 'a09694bc3b5f78bc792ea101d470ada1a438a57b', class: "detector-container" }, h("div", { key: 'c673c10d3311a44479d4462f3efbb4b6257ec6a9', class: "video-container" }, h("video", { key: 'c9faf3f111c50f945bce9d566fea2bd6b249fa78', ref: el => this.videoRef = el, autoplay: true, muted: true, playsinline: true, class: this.shouldMirrorVideo ? 'mirror' : '', style: { display: this.isVideoActive ? 'block' : 'none' } }), h("canvas", { key: 'bdc04a389f6b956f7ca138d9fe74db38a6c8812c', ref: el => this.canvasRef = el, class: this.shouldMirrorVideo ? 'mirror' : '' }), this.isMaskReady && (h("div", { key: '317156579b40924a7bb96c89dd247713f87f1aa9', class: "overlay-mask" }, h("div", { key: '71cfc3c3bbfdae49f05fd563e14f56181440fafa', class: "card-outline" }, h("div", { key: '3f940eeb59d783f47e2e2651ccf1a7be19f1d8b9', class: "side side-top" }), h("div", { key: 'f07e54e9542811897191e9a9a08f91b9e4785cc6', class: "side side-right" }), h("div", { key: '5b6a323213ddff52071b3469068cba0b31930ea0', class: "side side-bottom" }), h("div", { key: '44cf6567819855ab915fcee51cec7d08cb8654a8', class: "side side-left" }), h("div", { key: '8f866542b2d1a399418d1c8cb58ea856d5f3b9e7', class: "corner corner-tl" }), h("div", { key: 'a6567d410c755553d4be5b77dfc965e63b4ef07f', class: "corner corner-tr" }), h("div", { key: '255636461627f2deb61c9feacda3c9379abaaf29', class: "corner corner-bl" }), h("div", { key: 'dd029757b1ccc49c44bedee12c19b9485ef16545', class: "corner corner-br" }), !this.showFlipAnimation && !this.showSuccessAnimation && (h("div", { key: '37aef58019835eac5883042554c648b89cd305ac', class: "guide-text" }, this.statusMessage))), this.captureStep === 'back' && !this.showFlipAnimation && !this.showSuccessAnimation && (h("button", { key: '541f6d35d0655093f767423fc6851b521a5b43cd', class: "skip-button", onClick: () => this.skipBackCapture(), type: "button" }, "Saltar reverso")), this.isVideoActive && (h("div", { key: '73f2232b7c79f8b935cc78f2e5de1f064e4a3472', class: "camera-controls" }, this.isMultipleCamerasAvailable && (h("button", { key: '3c176f9848dc4bf3b7144e2d68225562ae3780c0', class: "flip-camera-button", onClick: () => this.flipCamera(), type: "button", title: "Cambiar c\u00E1mara" }, "Girar c\u00E1mara")), h("button", { key: '9460ad4c42872324141ab19b516e7fa026afdd37', class: "camera-selector-button", onClick: () => this.toggleCameraSelector(), type: "button", title: "Seleccionar c\u00E1mara" }, "C\u00E1maras"), this.debug && (h("div", { key: '961d825eaba6077189f32193d527fe98a6d4e1e1', style: {
|
|
1532
1649
|
position: 'absolute',
|
|
1533
1650
|
top: '50px',
|
|
1534
1651
|
right: '0',
|
|
@@ -1538,10 +1655,10 @@ export class JaakStamps {
|
|
|
1538
1655
|
fontSize: '10px',
|
|
1539
1656
|
borderRadius: '4px',
|
|
1540
1657
|
whiteSpace: 'nowrap'
|
|
1541
|
-
} }, "C\u00E1maras: ", this.availableCameras.length, h("br", { key: '
|
|
1658
|
+
} }, "C\u00E1maras: ", this.availableCameras.length, h("br", { key: 'f7e12d21177478d03f6df0490dfc91df12bd1225' }), "M\u00FAltiples: ", this.isMultipleCamerasAvailable ? 'Sí' : 'No', h("br", { key: '1f1cc8cf92e10b9b902fd981875621fa8dbe70f2' }), "Selector: ", this.showCameraSelector ? 'Visible' : 'Oculto', h("br", { key: 'c119c6567b28fc33e99b59f76e53e9359491ab77' }), "Video: ", this.isVideoActive ? 'Activo' : 'Inactivo')))), this.showCameraSelector && this.availableCameras.length > 0 && (h("div", { key: 'c230990e87f3b6133263c42fc1b568c0caf076e2', class: "camera-selector-dropdown" }, h("div", { key: '44c224e93c5832eea498e756a446e12ce8255e61', class: "camera-selector-header" }, h("span", { key: '64d951db4843164378424f2d8d2ed2802eb35170' }, "Seleccionar C\u00E1mara"), h("button", { key: '0575a7d0a9a99d665d42c6a7f7d8ceff53da9bd2', class: "close-selector", onClick: () => this.toggleCameraSelector(), type: "button" }, "\u00D7")), h("div", { key: '4aceed8bcf821710af343611f1b31efdfe61438e', class: "camera-list" }, this.availableCameras.map((camera) => (h("button", { key: camera.deviceId, class: `camera-option ${this.selectedCameraId === camera.deviceId ? 'selected' : ''}`, onClick: () => {
|
|
1542
1659
|
this.switchCamera(camera.deviceId);
|
|
1543
1660
|
this.toggleCameraSelector();
|
|
1544
|
-
}, type: "button" }, h("span", { class: "camera-label" }, camera.label || `Cámara ${this.availableCameras.indexOf(camera) + 1}`), this.selectedCameraId === camera.deviceId && (h("span", { class: "selected-indicator" }, "\u2713")))))), h("div", { key: '
|
|
1661
|
+
}, type: "button" }, h("span", { class: "camera-label" }, camera.label || `Cámara ${this.availableCameras.indexOf(camera) + 1}`), this.selectedCameraId === camera.deviceId && (h("span", { class: "selected-indicator" }, "\u2713")))))), h("div", { key: 'd6d691cc499a35f40e348cf61d8f81a380e6fe98', class: "device-info" }, h("small", { key: 'ed38304b9dcac5b99d7b32f5733c59b335433f61' }, "Dispositivo: ", this.deviceType)))))), this.isCapturing && (h("div", { key: 'ad19c6c3a2cb761a67b80e52761b2b9cb14d251d', class: "capture-animation" })), this.showFlipAnimation && (h("div", { key: '480615ac9b8ceb5cfc2d821d5777b213c2e86d83', class: "flip-animation" }, h("div", { key: '45e74e5ef254bce75f51d2d12a5961722fb0af03', class: "id-card-icon" }), h("div", { key: '38b9274a67fa8cf1f83bd4b06a3d4ef3d03cdb14', class: "flip-text" }, "\u00A1Voltea tu identificaci\u00F3n!"))), this.showSuccessAnimation && (h("div", { key: 'a6344502e3bbbe298dfb509b41354a54038826aa', class: "success-animation" }, h("div", { key: '579f89d7c8d0ff76e42af611286d96a35d3dbfb9', class: "check-icon" }), h("div", { key: '5bb5c155c70f4bf7a04a62d10142e413763fa1fa', class: "success-text" }, "\u00A1Proceso completado!"))), this.isLoading && (h("div", { key: '664113d7266be3c4171291faede143e736efadf0', class: "loading-overlay" }, h("div", { key: 'b699ad30f1784e1a92657391c080b91e017f7420', class: "loading-spinner" }), h("div", { key: '287f8e13229e4d14de31b0c5ad7d89a202eca5f9', class: "loading-text" }, this.statusMessage))), this.debug && (h("div", { key: 'ba649b0414153cb28b2c6e3c5451b324a990ec63', class: "status-bar" }, h("div", { key: '55b11462af7ef04d293757e2e45344f9206352ac', class: "status-message", style: { 'color': this.statusColor } }, this.statusMessage))), h("div", { key: '3b24a505519d8b483fad2b2f66ef8159d458e1b4', class: "watermark" }, h("img", { key: 'd61f9366631661835e1dd9500500c2b7a7334581', src: "https://storage.googleapis.com/jaak-static/commons/powered-by-jaak.png", alt: "Powered by Jaak" })))));
|
|
1545
1662
|
}
|
|
1546
1663
|
static get is() { return "jaak-stamps"; }
|
|
1547
1664
|
static get encapsulation() { return "shadow"; }
|