@jaak.ai/stamps 2.1.0-dev.3 → 2.1.0-dev.5
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-webcomponent.cjs.js +1 -1
- package/dist/cjs/jaak-stamps.cjs.entry.js +180 -45
- package/dist/cjs/jaak-stamps.cjs.entry.js.map +1 -1
- package/dist/cjs/jaak-stamps.entry.cjs.js.map +1 -1
- package/dist/cjs/loader.cjs.js +1 -1
- package/dist/collection/components/my-component/my-component.css +19 -0
- package/dist/collection/components/my-component/my-component.js +181 -51
- package/dist/collection/components/my-component/my-component.js.map +1 -1
- package/dist/components/jaak-stamps.js +182 -46
- package/dist/components/jaak-stamps.js.map +1 -1
- package/dist/esm/jaak-stamps-webcomponent.js +1 -1
- package/dist/esm/jaak-stamps.entry.js +180 -45
- package/dist/esm/jaak-stamps.entry.js.map +1 -1
- package/dist/esm/loader.js +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-c08802a9.entry.js +2 -0
- package/dist/jaak-stamps-webcomponent/p-c08802a9.entry.js.map +1 -0
- package/dist/types/components/my-component/my-component.d.ts +11 -2
- package/package.json +1 -1
- package/dist/jaak-stamps-webcomponent/p-4b2f9fb3.entry.js +0 -2
- package/dist/jaak-stamps-webcomponent/p-4b2f9fb3.entry.js.map +0 -1
package/dist/cjs/loader.cjs.js
CHANGED
|
@@ -5,7 +5,7 @@ var index = require('./index-BfhtOB0D.js');
|
|
|
5
5
|
const defineCustomElements = async (win, options) => {
|
|
6
6
|
if (typeof window === 'undefined') return undefined;
|
|
7
7
|
await index.globalScripts();
|
|
8
|
-
return index.bootstrapLazy([["jaak-stamps.cjs",[[1,"jaak-stamps",{"debug":[4],"alignmentTolerance":[2,"alignment-tolerance"],"maskSize":[2,"mask-size"],"cropMargin":[2,"crop-margin"],"useDocumentClassification":[4,"use-document-classification"],"useDocumentDetector":[4,"use-document-detector"],"preferredCamera":[1,"preferred-camera"],"captureDelay":[2,"capture-delay"],"enableBackDocumentTimer":[4,"enable-back-document-timer"],"backDocumentTimerDuration":[2,"back-document-timer-duration"],"detectionBoxes":[32],"sideAlignment":[32],"isMaskReady":[32],"shouldMirrorVideo":[32],"showCameraSelector":[32],"isSwitchingCamera":[32],"hasDocumentDetected":[32],"cameraInfoWithAutofocus":[32],"currentStatus":[32],"performanceData":[32],"backDocumentTimerRemaining":[32],"showManualCaptureButton":[32],"
|
|
8
|
+
return index.bootstrapLazy([["jaak-stamps.cjs",[[1,"jaak-stamps",{"debug":[4],"alignmentTolerance":[2,"alignment-tolerance"],"maskSize":[2,"mask-size"],"cropMargin":[2,"crop-margin"],"useDocumentClassification":[4,"use-document-classification"],"useDocumentDetector":[4,"use-document-detector"],"preferredCamera":[1,"preferred-camera"],"captureDelay":[2,"capture-delay"],"enableBackDocumentTimer":[4,"enable-back-document-timer"],"backDocumentTimerDuration":[2,"back-document-timer-duration"],"detectionBoxes":[32],"sideAlignment":[32],"isMaskReady":[32],"shouldMirrorVideo":[32],"showCameraSelector":[32],"isSwitchingCamera":[32],"hasDocumentDetected":[32],"cameraInfoWithAutofocus":[32],"currentStatus":[32],"performanceData":[32],"backDocumentTimerRemaining":[32],"showManualCaptureButton":[32],"performanceDegradedMode":[32],"showPerformanceMessage":[32],"getCapturedImages":[64],"isProcessCompleted":[64],"startCapture":[64],"stopCapture":[64],"resetCapture":[64],"skipBackCapture":[64],"getStatus":[64],"preloadModel":[64],"getCameraInfo":[64],"setPreferredCamera":[64],"setCaptureDelay":[64],"getCaptureDelay":[64]}]]]], options);
|
|
9
9
|
};
|
|
10
10
|
|
|
11
11
|
exports.setNonce = index.setNonce;
|
|
@@ -621,6 +621,25 @@ video {
|
|
|
621
621
|
to { opacity: 1; transform: translateY(0); }
|
|
622
622
|
}
|
|
623
623
|
|
|
624
|
+
/* Performance warning animation for guide-text */
|
|
625
|
+
.guide-text.performance-warning-text {
|
|
626
|
+
animation: gentlePulse 2s ease-in-out infinite;
|
|
627
|
+
background: rgba(255, 107, 107, 0.3);
|
|
628
|
+
border: 1px solid rgba(255, 107, 107, 0.5);
|
|
629
|
+
}
|
|
630
|
+
|
|
631
|
+
@keyframes gentlePulse {
|
|
632
|
+
0%, 100% {
|
|
633
|
+
transform: translate(-50%, -50%) scale(1);
|
|
634
|
+
background: rgba(255, 107, 107, 0.3);
|
|
635
|
+
}
|
|
636
|
+
50% {
|
|
637
|
+
transform: translate(-50%, -50%) scale(1.02);
|
|
638
|
+
background: rgba(255, 107, 107, 0.4);
|
|
639
|
+
}
|
|
640
|
+
}
|
|
641
|
+
|
|
642
|
+
|
|
624
643
|
/* Botón para saltar reverso */
|
|
625
644
|
.skip-button {
|
|
626
645
|
pointer-events: auto;
|
|
@@ -49,7 +49,8 @@ export class JaakStamps {
|
|
|
49
49
|
};
|
|
50
50
|
backDocumentTimerRemaining = 0;
|
|
51
51
|
showManualCaptureButton = false;
|
|
52
|
-
|
|
52
|
+
performanceDegradedMode = false; // Auto-switched to manual mode due to performance
|
|
53
|
+
showPerformanceMessage = false; // Show performance message temporarily
|
|
53
54
|
// Services
|
|
54
55
|
serviceContainer;
|
|
55
56
|
eventBus;
|
|
@@ -73,7 +74,6 @@ export class JaakStamps {
|
|
|
73
74
|
fps: 0,
|
|
74
75
|
inferenceTime: 0,
|
|
75
76
|
memoryUsage: 0,
|
|
76
|
-
cpuUsage: 0,
|
|
77
77
|
onnxLoadTime: 0,
|
|
78
78
|
frameProcessingTime: 0,
|
|
79
79
|
totalDetections: 0,
|
|
@@ -92,6 +92,12 @@ export class JaakStamps {
|
|
|
92
92
|
MIN_INFERENCE_INTERVAL = 50;
|
|
93
93
|
performanceHistory = [];
|
|
94
94
|
PERFORMANCE_HISTORY_SIZE = 10;
|
|
95
|
+
// Sistema simplificado de monitoreo de rendimiento
|
|
96
|
+
PERFORMANCE_THRESHOLD_MS = 2000; // Umbral único para todos los frames
|
|
97
|
+
SLOW_FRAMES_TO_TRIGGER = 2; // Cuántos frames lentos consecutivos antes de cambiar
|
|
98
|
+
slowFrameCount = 0; // Contador de frames consecutivos lentos
|
|
99
|
+
processedFramesCount = 0; // Contador total de frames procesados
|
|
100
|
+
hasAutoSwitchedToManual = false;
|
|
95
101
|
// Canvas pool for optimized screenshot capture
|
|
96
102
|
canvasPool = [];
|
|
97
103
|
MAX_CANVAS_POOL_SIZE = 3;
|
|
@@ -124,14 +130,8 @@ export class JaakStamps {
|
|
|
124
130
|
this.detectionService = this.serviceContainer.getDetectionService();
|
|
125
131
|
}
|
|
126
132
|
async setupEventListeners() {
|
|
127
|
-
this.eventBus.on('state-changed', (
|
|
128
|
-
this.handleStateChange(
|
|
129
|
-
});
|
|
130
|
-
this.eventBus.on('camera-changed', () => {
|
|
131
|
-
// Camera changed event
|
|
132
|
-
});
|
|
133
|
-
this.eventBus.on('error', () => {
|
|
134
|
-
// Handle service errors
|
|
133
|
+
this.eventBus.on('state-changed', () => {
|
|
134
|
+
this.handleStateChange();
|
|
135
135
|
});
|
|
136
136
|
}
|
|
137
137
|
async initializeComponent() {
|
|
@@ -238,13 +238,8 @@ export class JaakStamps {
|
|
|
238
238
|
return false;
|
|
239
239
|
}
|
|
240
240
|
}
|
|
241
|
-
handleStateChange(
|
|
242
|
-
//
|
|
243
|
-
// This is where the component updates its internal state based on service state changes
|
|
244
|
-
if (data.changes.isLoading !== undefined) {
|
|
245
|
-
// Force re-render when loading state changes
|
|
246
|
-
// Note: Stencil automatically re-renders when @State changes
|
|
247
|
-
}
|
|
241
|
+
handleStateChange() {
|
|
242
|
+
// Handle state changes from StateManager if needed
|
|
248
243
|
}
|
|
249
244
|
initializeResizeObserver() {
|
|
250
245
|
if ('ResizeObserver' in window && this.detectionContainer) {
|
|
@@ -261,13 +256,14 @@ export class JaakStamps {
|
|
|
261
256
|
this.updateMaskDimensions(rect);
|
|
262
257
|
}
|
|
263
258
|
}
|
|
264
|
-
triggerRerender() {
|
|
265
|
-
this.captureStateVersion = this.captureStateVersion + 1;
|
|
266
|
-
}
|
|
267
259
|
getGuideText(step) {
|
|
268
260
|
if (step === 'completed') {
|
|
269
261
|
return 'Proceso completado';
|
|
270
262
|
}
|
|
263
|
+
// Check if we should show performance message
|
|
264
|
+
if (this.showPerformanceMessage && step === 'front') {
|
|
265
|
+
return 'Modo manual activado por rendimiento. Use el botón para capturar.';
|
|
266
|
+
}
|
|
271
267
|
if (step === 'front') {
|
|
272
268
|
// Para el frente, si el detector manual está activo, mostrar instrucciones de captura manual
|
|
273
269
|
if (this.showManualCaptureButton) {
|
|
@@ -497,9 +493,21 @@ export class JaakStamps {
|
|
|
497
493
|
if (this.stateManager) {
|
|
498
494
|
this.stateManager.updateCaptureState({ isLoading: true });
|
|
499
495
|
}
|
|
500
|
-
|
|
496
|
+
try {
|
|
497
|
+
await this.detectionService.loadModel();
|
|
498
|
+
}
|
|
499
|
+
catch (modelError) {
|
|
500
|
+
this.switchToManualModeWithError('Error al cargar modelo de detección');
|
|
501
|
+
throw modelError;
|
|
502
|
+
}
|
|
501
503
|
this.updateStatus('Optimizando detección...', 'Configurando reconocimiento de documentos', 'loading');
|
|
502
|
-
|
|
504
|
+
try {
|
|
505
|
+
await this.detectionService.loadClassificationModel();
|
|
506
|
+
}
|
|
507
|
+
catch (classificationError) {
|
|
508
|
+
this.switchToManualModeWithError('Error al cargar modelo de clasificación');
|
|
509
|
+
throw classificationError;
|
|
510
|
+
}
|
|
503
511
|
const loadEndTime = performance.now();
|
|
504
512
|
const loadTime = loadEndTime - loadStartTime;
|
|
505
513
|
// Record ONNX load time
|
|
@@ -616,9 +624,21 @@ export class JaakStamps {
|
|
|
616
624
|
const loadStartTime = performance.now();
|
|
617
625
|
this.updateStatus('Preparando reconocimiento...', 'Configurando detección de documentos', 'loading');
|
|
618
626
|
this.stateManager.updateCaptureState({ isLoading: true });
|
|
619
|
-
|
|
627
|
+
try {
|
|
628
|
+
await this.detectionService.loadModel();
|
|
629
|
+
}
|
|
630
|
+
catch (modelError) {
|
|
631
|
+
this.switchToManualModeWithError('Error al cargar modelo de detección');
|
|
632
|
+
throw modelError;
|
|
633
|
+
}
|
|
620
634
|
this.updateStatus('Optimizando detección...', 'Configurando reconocimiento de documentos', 'loading');
|
|
621
|
-
|
|
635
|
+
try {
|
|
636
|
+
await this.detectionService.loadClassificationModel();
|
|
637
|
+
}
|
|
638
|
+
catch (classificationError) {
|
|
639
|
+
this.switchToManualModeWithError('Error al cargar modelo de clasificación');
|
|
640
|
+
throw classificationError;
|
|
641
|
+
}
|
|
622
642
|
const loadEndTime = performance.now();
|
|
623
643
|
const loadTime = loadEndTime - loadStartTime;
|
|
624
644
|
// Record ONNX load time
|
|
@@ -633,9 +653,9 @@ export class JaakStamps {
|
|
|
633
653
|
// Paso 3: Configurar cámara seleccionada
|
|
634
654
|
this.updateStatus('Ajustando cámara...', 'Configurando calidad de imagen', 'loading');
|
|
635
655
|
const stream = await this.cameraService.setupCamera();
|
|
636
|
-
// Paso 4: Inicializar video y
|
|
656
|
+
// Paso 4: Inicializar video y mostrar estado de análisis inicial
|
|
637
657
|
if (this.useDocumentDetector) {
|
|
638
|
-
this.updateStatus('
|
|
658
|
+
this.updateStatus('Analizando estabilidad...', 'Evaluando rendimiento del sistema', 'loading');
|
|
639
659
|
}
|
|
640
660
|
else {
|
|
641
661
|
this.updateStatus('Captura activa', 'Posicione su documento y use el botón para capturar', 'active');
|
|
@@ -685,8 +705,8 @@ export class JaakStamps {
|
|
|
685
705
|
const captureState = this.stateManager.getCaptureState();
|
|
686
706
|
if (!this.videoRef || !this.detectionContainer || !this.detectionService.isModelLoaded())
|
|
687
707
|
return;
|
|
688
|
-
// Show manual capture button when document detector is disabled
|
|
689
|
-
if (!this.useDocumentDetector) {
|
|
708
|
+
// Show manual capture button when document detector is disabled or performance is degraded
|
|
709
|
+
if (!this.useDocumentDetector || this.performanceDegradedMode) {
|
|
690
710
|
this.showManualCaptureButton = true;
|
|
691
711
|
// Continue the loop for UI updates but skip detection logic
|
|
692
712
|
if (captureState.step !== 'completed') {
|
|
@@ -694,7 +714,7 @@ export class JaakStamps {
|
|
|
694
714
|
}
|
|
695
715
|
return;
|
|
696
716
|
}
|
|
697
|
-
else {
|
|
717
|
+
else if (!this.performanceDegradedMode) {
|
|
698
718
|
this.showManualCaptureButton = false;
|
|
699
719
|
}
|
|
700
720
|
if (captureState.isDetectionPaused) {
|
|
@@ -724,10 +744,27 @@ export class JaakStamps {
|
|
|
724
744
|
this.lastInferenceTime = currentTime;
|
|
725
745
|
// Measure preprocessing and inference time
|
|
726
746
|
const inferenceStartTime = performance.now();
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
747
|
+
let inputTensor;
|
|
748
|
+
let detections;
|
|
749
|
+
let inferenceTime;
|
|
750
|
+
try {
|
|
751
|
+
inputTensor = this.detectionService.preprocess(this.videoRef);
|
|
752
|
+
}
|
|
753
|
+
catch (preprocessError) {
|
|
754
|
+
this.switchToManualModeWithError('Error al procesar imagen');
|
|
755
|
+
return;
|
|
756
|
+
}
|
|
757
|
+
try {
|
|
758
|
+
// Standard detection without timeout (timeout is handled by frame counting)
|
|
759
|
+
detections = await this.detectionService.runInference(inputTensor);
|
|
760
|
+
inferenceTime = performance.now() - inferenceStartTime;
|
|
761
|
+
}
|
|
762
|
+
catch (inferenceError) {
|
|
763
|
+
this.switchToManualModeWithError('Error en detección automática');
|
|
764
|
+
return;
|
|
765
|
+
}
|
|
766
|
+
// Increment frame count
|
|
767
|
+
this.processedFramesCount++;
|
|
731
768
|
// Record ONNX performance metrics
|
|
732
769
|
if (this.debug) {
|
|
733
770
|
this.recordOnnxPerformance(0, inferenceTime);
|
|
@@ -766,9 +803,30 @@ export class JaakStamps {
|
|
|
766
803
|
}
|
|
767
804
|
this.updateMaskColor(detections);
|
|
768
805
|
// Record frame processing metrics
|
|
806
|
+
const frameEndTime = performance.now();
|
|
807
|
+
const totalFrameTime = frameEndTime - frameStartTime;
|
|
808
|
+
// Sistema simplificado: Verificar rendimiento de cada frame (solo si no se ha cambiado a manual)
|
|
809
|
+
if (this.useDocumentDetector && !this.hasAutoSwitchedToManual) {
|
|
810
|
+
// Verificar si el frame es lento
|
|
811
|
+
if (totalFrameTime >= this.PERFORMANCE_THRESHOLD_MS) {
|
|
812
|
+
this.slowFrameCount++;
|
|
813
|
+
// Si tenemos suficientes frames lentos consecutivos, cambiar a manual
|
|
814
|
+
if (this.slowFrameCount >= this.SLOW_FRAMES_TO_TRIGGER) {
|
|
815
|
+
this.switchToManualMode();
|
|
816
|
+
}
|
|
817
|
+
}
|
|
818
|
+
else {
|
|
819
|
+
// Frame rápido, reiniciar contador
|
|
820
|
+
if (this.slowFrameCount > 0) {
|
|
821
|
+
this.slowFrameCount = 0;
|
|
822
|
+
}
|
|
823
|
+
}
|
|
824
|
+
// Cambiar mensaje de estado después de analizar los primeros 2 frames
|
|
825
|
+
if (this.processedFramesCount === 2) {
|
|
826
|
+
this.updateStatus('Captura activa', 'Buscando documento en el marco de captura', 'active');
|
|
827
|
+
}
|
|
828
|
+
}
|
|
769
829
|
if (this.debug) {
|
|
770
|
-
const frameEndTime = performance.now();
|
|
771
|
-
const totalFrameTime = frameEndTime - frameStartTime;
|
|
772
830
|
this.recordFrameProcessing(totalFrameTime, detections.length);
|
|
773
831
|
}
|
|
774
832
|
// Continue detection loop
|
|
@@ -804,6 +862,8 @@ export class JaakStamps {
|
|
|
804
862
|
clearTimeout(this.alignmentTimer);
|
|
805
863
|
this.alignmentTimer = undefined;
|
|
806
864
|
}
|
|
865
|
+
// Liberar recursos de ONNX al limpiar el componente
|
|
866
|
+
this.releaseOnnxResources();
|
|
807
867
|
if (this.performanceUpdateInterval) {
|
|
808
868
|
clearInterval(this.performanceUpdateInterval);
|
|
809
869
|
this.performanceUpdateInterval = undefined;
|
|
@@ -825,7 +885,7 @@ export class JaakStamps {
|
|
|
825
885
|
isCapturing: false
|
|
826
886
|
};
|
|
827
887
|
const cameraInfo = this.cameraInfoWithAutofocus;
|
|
828
|
-
return (h("div", { key: '
|
|
888
|
+
return (h("div", { key: '687a01ebb87f3c9e4424f4bcd355cd68c21366f0', class: "detector-container" }, h("div", { key: 'd4c9f1fbf653ea7764dcc7265f5f7180c99fe5e7', class: "video-container" }, h("video", { key: '37a159daaaa4682d8e14a1dcdef32225706e1f20', ref: el => this.videoRef = el, autoplay: true, muted: true, playsinline: true, class: this.shouldMirrorVideo ? 'mirror' : '', style: { display: captureState.isVideoActive ? 'block' : 'none' } }), h("div", { key: '74fe5c8612be7a8d904510c226d68a6860a0f67d', ref: el => this.detectionContainer = el, class: `detection-overlay ${this.shouldMirrorVideo ? 'mirror' : ''}` }, this.debug && this.detectionBoxes.map((box, index) => (h("div", { key: index, class: "detection-box", style: {
|
|
829
889
|
position: 'absolute',
|
|
830
890
|
left: `${box.x}px`,
|
|
831
891
|
top: `${box.y}px`,
|
|
@@ -834,9 +894,9 @@ export class JaakStamps {
|
|
|
834
894
|
border: '2px solid #32406C',
|
|
835
895
|
pointerEvents: 'none',
|
|
836
896
|
boxSizing: 'border-box'
|
|
837
|
-
} })))), this.isMaskReady && (h("div", { key: '
|
|
897
|
+
} })))), this.isMaskReady && (h("div", { key: '4f2e282a8eb99947b1e67690ef236019e87ad87e', class: "overlay-mask" }, h("div", { key: '1d102684d59e5f7f5d6243f95e39ee0e1812032e', class: "card-outline" }, h("div", { key: '4ba0df1528de02cc037022948e425ffb13c49822', class: "side side-top" }), h("div", { key: '36bc3f2d39f61d39af2522ffe13b6df16c8bf00b', class: "side side-right" }), h("div", { key: '88d2402044de0309055c31fd98e596b88b1d51ce', class: "side side-bottom" }), h("div", { key: '72262621ee2c2b4824f3b313f27a5793fa4c123f', class: "side side-left" })), !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: 'df9320c0f5518c04b1504d355223730e6d686779', class: `guide-text ${this.showPerformanceMessage ? 'performance-warning-text' : ''}` }, this.getGuideText(captureState.step))), captureState.step === 'back' && !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: 'e86f6eec1ea7712fb8c94d1455dd9c0c7c01db21', class: "back-capture-section" }, h("div", { key: 'ad965847b25eeae92eb22c3d89b09e953fabb2d2', class: "back-capture-buttons" }, (!this.useDocumentDetector || this.performanceDegradedMode) && (h("button", { key: '3e57f0bf7600bc650e44f40e3c1fd13747885781', class: "capture-button primary-button", onClick: () => this.takeManualScreenshot(), type: "button", disabled: captureState.isCapturing }, captureState.isCapturing ? 'Capturando...' : 'Capturar Reverso')), h("button", { key: 'd598cd7778869b46b5c7ceafcb43c469b4b5c7e7', class: "skip-button", onClick: () => this.skipBackCapture(), type: "button" }, this.enableBackDocumentTimer && this.backDocumentTimerRemaining > 0
|
|
838
898
|
? `Saltar reverso (${this.backDocumentTimerRemaining}s)`
|
|
839
|
-
: 'Saltar reverso')))), captureState.isVideoActive && (h("div", { key: '
|
|
899
|
+
: 'Saltar reverso')))), captureState.isVideoActive && (h("div", { key: 'b1508382d2b75584a19dade3f8e685a34ff2c3a3', class: "camera-controls" }, h("button", { key: '9c1f945b051f8e000f87fb3674ecfd386bdc2208', class: `camera-selector-button ${this.isSwitchingCamera ? 'loading' : ''}`, onClick: () => this.toggleCameraSelector(), type: "button", title: "Seleccionar c\u00E1mara", disabled: this.isSwitchingCamera }, this.isSwitchingCamera ? (h("div", { class: "button-spinner" })) : ('Cámaras')))), this.showCameraSelector && cameraInfo.availableCameras.length > 0 && (h("div", { key: '4adab3b896be86322be168db377cbacbcb3a7422', class: "camera-selector-dropdown" }, h("div", { key: 'a60e3f46cfe5997cf9b82d685a1574b7002c0071', class: "camera-selector-header" }, h("span", { key: '71e012a8a4953f584aeffc985040e434fadfb00b' }, "Seleccionar C\u00E1mara"), h("button", { key: '046ee4f6d81b34349ecad4e9de98f4d8653dad6b', class: "close-selector", onClick: () => this.toggleCameraSelector(), type: "button" }, "\u00D7")), h("div", { key: '539ad135914d9ceb3a6b9a2de2d9ae4ea7a996b3', class: "camera-list" }, cameraInfo.availableCameras.map((camera) => (h("button", { key: camera.id, class: `camera-option ${cameraInfo.selectedCameraId === camera.id ? 'selected' : ''}`, onClick: () => this.handleCameraSwitch(camera.id), type: "button" }, h("span", { class: "camera-label" }, camera.label || `Cámara ${cameraInfo.availableCameras.indexOf(camera) + 1}`, camera.hasAutofocus && (h("span", { class: "autofocus-icon", title: "Autofoco disponible" }, "\u29BF"))), cameraInfo.selectedCameraId === camera.id && (h("span", { class: "selected-indicator" }, "\u2713")))))), h("div", { key: '082d1cc259af3c1fc95b53da1e754382e874b837', class: "device-info" }, h("small", { key: 'dad398582ac7bfd31ee43704d47fd3036fc59d06' }, "Dispositivo: ", cameraInfo.deviceType)))), this.showManualCaptureButton && captureState.step === 'front' && !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: '231ff3eb4672b4ac310419cccc8cd6d1caab9e14', class: "manual-capture-section" }, h("button", { key: 'fa2fcc4bfe63bf2ccdba2c2ad3c8c4b4a5aabbb5', class: "manual-capture-button", onClick: () => this.takeManualScreenshot(), type: "button", disabled: captureState.isCapturing }, captureState.isCapturing ? 'Capturando...' : 'Capturar Frente'))))), captureState.isCapturing && (h("div", { key: '39426754973f1a9e07b56399f344add21bf9b848', class: "capture-animation" })), captureState.showFlipAnimation && (h("div", { key: '307a7eb06b41a8baebe37ad26b1f5e4cf0a43ec1', class: "flip-animation" }, h("div", { key: '7070ad263e3894dc1488bb8a17f5bf23b7b757f0', class: "id-card-icon" }), h("div", { key: '81a0d8b6377b397bbeebe2e31800fe88f88593a0', class: "flip-text" }, "\u00A1Voltea tu identificaci\u00F3n!"))), captureState.showSuccessAnimation && (h("div", { key: '741e5043bd57a3e13e39fd897a64cd20a75dad2e', class: "success-animation" }, h("div", { key: '6269a51c0651e5f76490906e50eb111f6a88f267', class: "check-icon" }), h("div", { key: '1c90a9cf6c90bb10af90660c714b7ff1ed6acfa0', class: "success-text" }, "\u00A1Proceso completado!"))), h("div", { key: 'f6746c1fb15cc238846f047743a9d45b1d4a41f8', class: `component-status status-${this.currentStatus.type}` }, (this.currentStatus.type === 'loading' || this.currentStatus.type === 'initializing') && (h("div", { key: '00d198abdc90683e5f05a9fd9b54d44e55c16630', class: "status-spinner" })), h("div", { key: 'b0254dea36bae65692bfbd200dfb75eb5a3a50dc', class: "status-content" }, h("div", { key: 'e3e48ea04f40ddd7c66aa8eda3d341f24a9c3dc4', class: "status-message" }, this.currentStatus.message), this.currentStatus.description && (h("div", { key: 'd3f40ca5b72a661f9631145880fc6d1bba878961', class: "status-description" }, this.currentStatus.description)))), this.debug && (h("div", { key: 'eabe40809e744eb62b2ac76733952060988b675c', class: "performance-monitor" }, h("div", { key: '44e51257d4ba2c2153749cf14f3aebbf22ca02ec', class: "performance-expanded" }, h("div", { key: '493fc680db2d1e82068eadda3786fad57e8594cc', class: "metrics-row" }, h("div", { key: 'aaa734d066246c9364d51c04d41a0a84d0b7e216', class: "metric-compact" }, h("span", { key: 'f0b59f76e8aa1723a429289b7898d35f22ff86d4', class: "metric-label" }, "FPS"), h("span", { key: 'a562359df92cabe40f54b355ffa264f246e7ec8e', class: `metric-value ${this.performanceData.fps < 15 ? 'warning' : this.performanceData.fps < 10 ? 'danger' : 'good'}` }, this.performanceData.fps)), h("div", { key: '9adca77e934ee3cd07fb54a056132e305637848c', class: "metric-compact" }, h("span", { key: '65ec83dca0e74b42065962d2a2e4bae7515b9fc1', class: "metric-label" }, "MEM"), h("span", { key: '427fc6b5b538742d0987b0240f526616b910ae69', class: `metric-value ${this.performanceData.memoryUsage > 100 ? 'warning' : this.performanceData.memoryUsage > 200 ? 'danger' : 'good'}` }, this.performanceData.memoryUsage, "MB"))), h("div", { key: 'fc551d8ef39308980437b72b3fb4c0bdb2bfbf67', class: "metrics-row" }, h("div", { key: 'b88785c108e5586fecc8702f3e4da883ace00f15', class: "metric-compact" }, h("span", { key: '31db440861e6fd9c2ee36ccd242f1b7bb3d47f45', class: "metric-label" }, "INF"), h("span", { key: 'af45bbb41110a04ed3d22a9e112b8644dd7ec355', class: `metric-value ${this.performanceData.inferenceTime > 100 ? 'warning' : this.performanceData.inferenceTime > 200 ? 'danger' : 'good'}` }, this.performanceData.inferenceTime, "ms")), h("div", { key: 'deabe5ce0661557fabe4ccdde1af48beed564ad9', class: "metric-compact" }, h("span", { key: '072f9159e95b3f3226f07b879b377a3d34940825', class: "metric-label" }, "FRAME"), h("span", { key: '841de1ae8df76919c2b644c6ff813dd927b52013', class: `metric-value ${this.performanceData.frameProcessingTime > 50 ? 'warning' : this.performanceData.frameProcessingTime > 100 ? 'danger' : 'good'}` }, this.performanceData.frameProcessingTime, "ms"))), h("div", { key: '68c6c777db1430987f20536849a3ed9169ec794a', class: "metrics-row" }, h("div", { key: '736e361beaa88d268041ec55fd73db0ee405e1ae', class: "metric-compact" }, h("span", { key: 'bfa6c3aa54a96e5eab32dc4fa0227ca836142561', class: "metric-label" }, "DET"), h("span", { key: 'f9a2479c470779403bf1cbfd4f433f80e5fa34d8', class: "metric-value good" }, this.performanceData.successfulDetections, "/", this.performanceData.totalDetections)), h("div", { key: 'bfc1d7f8cbc7449a96e751b005a02bb112e63a86', class: "metric-compact" }, h("span", { key: '45a7171a72ac6ae9c29a4de3c7a260ae78681dc1', class: "metric-label" }, "RATE"), h("span", { key: '7419ace73d0302d662b3a6308f313be271049b5a', class: `metric-value ${this.performanceData.detectionRate < 30 ? 'danger' : this.performanceData.detectionRate < 60 ? 'warning' : 'good'}` }, this.performanceData.detectionRate, "%")))))), h("div", { key: '786544dff913bb4b1003e62d9ab35b3f29f4b497', class: "watermark" }, h("img", { key: 'e08c893afa8bad94d04b01ea4732044b1c9a2d6c', src: "https://storage.googleapis.com/jaak-static/commons/powered-by-jaak.png", alt: "Powered by Jaak" })))));
|
|
840
900
|
}
|
|
841
901
|
// Utility methods
|
|
842
902
|
updateDetectionBoxes(boxes) {
|
|
@@ -1024,12 +1084,17 @@ export class JaakStamps {
|
|
|
1024
1084
|
});
|
|
1025
1085
|
// Check if document classification is enabled (independent of detector)
|
|
1026
1086
|
if (this.useDocumentClassification) {
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1087
|
+
try {
|
|
1088
|
+
const classification = await this.detectionService.classifyDocument(croppedCanvas);
|
|
1089
|
+
if (classification && classification.class === 'passport') {
|
|
1090
|
+
this.completeProcess(true);
|
|
1091
|
+
this.returnCanvasToPool(captureCanvas);
|
|
1092
|
+
this.returnCanvasToPool(croppedCanvas);
|
|
1093
|
+
return;
|
|
1094
|
+
}
|
|
1095
|
+
}
|
|
1096
|
+
catch (classifyError) {
|
|
1097
|
+
// No cambiar a manual aquí, solo registrar el error y continuar
|
|
1033
1098
|
}
|
|
1034
1099
|
}
|
|
1035
1100
|
this.stateManager.updateCaptureState({
|
|
@@ -1037,13 +1102,11 @@ export class JaakStamps {
|
|
|
1037
1102
|
isDetectionPaused: true,
|
|
1038
1103
|
showFlipAnimation: true
|
|
1039
1104
|
});
|
|
1040
|
-
this.triggerRerender();
|
|
1041
1105
|
setTimeout(() => {
|
|
1042
1106
|
this.stateManager.updateCaptureState({
|
|
1043
1107
|
showFlipAnimation: false,
|
|
1044
1108
|
isDetectionPaused: false
|
|
1045
1109
|
});
|
|
1046
|
-
this.triggerRerender();
|
|
1047
1110
|
this.startBackDocumentTimer();
|
|
1048
1111
|
}, 3000);
|
|
1049
1112
|
}
|
|
@@ -1093,10 +1156,15 @@ export class JaakStamps {
|
|
|
1093
1156
|
});
|
|
1094
1157
|
// Check if document classification is enabled
|
|
1095
1158
|
if (this.useDocumentClassification) {
|
|
1096
|
-
|
|
1097
|
-
|
|
1098
|
-
|
|
1099
|
-
|
|
1159
|
+
try {
|
|
1160
|
+
const classification = await this.detectionService.classifyDocument(croppedCanvas);
|
|
1161
|
+
if (classification && classification.class === 'passport') {
|
|
1162
|
+
this.completeProcess(true);
|
|
1163
|
+
return;
|
|
1164
|
+
}
|
|
1165
|
+
}
|
|
1166
|
+
catch (classifyError) {
|
|
1167
|
+
// No cambiar a manual aquí, solo registrar el error y continuar
|
|
1100
1168
|
}
|
|
1101
1169
|
}
|
|
1102
1170
|
this.stateManager.updateCaptureState({
|
|
@@ -1133,6 +1201,60 @@ export class JaakStamps {
|
|
|
1133
1201
|
cardOutline?.classList.remove('capturing');
|
|
1134
1202
|
}, 600);
|
|
1135
1203
|
}
|
|
1204
|
+
// Método simplificado para cambio a modo manual
|
|
1205
|
+
switchToManualMode() {
|
|
1206
|
+
// Only switch if detector is enabled and not already switched
|
|
1207
|
+
if (!this.useDocumentDetector || this.hasAutoSwitchedToManual) {
|
|
1208
|
+
return;
|
|
1209
|
+
}
|
|
1210
|
+
// Detener todo el monitoreo de performance
|
|
1211
|
+
this.stopPerformanceMonitoring();
|
|
1212
|
+
// Liberar recursos de ONNX
|
|
1213
|
+
this.releaseOnnxResources();
|
|
1214
|
+
this.hasAutoSwitchedToManual = true;
|
|
1215
|
+
this.performanceDegradedMode = true;
|
|
1216
|
+
this.showManualCaptureButton = true;
|
|
1217
|
+
this.showPerformanceMessage = true;
|
|
1218
|
+
// Hide performance message after 5 seconds
|
|
1219
|
+
setTimeout(() => {
|
|
1220
|
+
this.showPerformanceMessage = false;
|
|
1221
|
+
}, 5000);
|
|
1222
|
+
}
|
|
1223
|
+
// Método para cambiar a modo manual por errores de ONNX
|
|
1224
|
+
switchToManualModeWithError(errorMessage) {
|
|
1225
|
+
// Solo cambiar si el detector está habilitado y no se ha cambiado ya
|
|
1226
|
+
if (!this.useDocumentDetector || this.hasAutoSwitchedToManual) {
|
|
1227
|
+
return;
|
|
1228
|
+
}
|
|
1229
|
+
// Liberar recursos de ONNX inmediatamente
|
|
1230
|
+
this.releaseOnnxResources();
|
|
1231
|
+
// Cambiar a modo manual
|
|
1232
|
+
this.hasAutoSwitchedToManual = true;
|
|
1233
|
+
this.performanceDegradedMode = true;
|
|
1234
|
+
this.showManualCaptureButton = true;
|
|
1235
|
+
this.useDocumentDetector = false; // Desactivar detector automático
|
|
1236
|
+
// Actualizar el estado con mensaje de error
|
|
1237
|
+
this.updateStatus('Modo manual activado', errorMessage, 'error');
|
|
1238
|
+
// Ocultar mensaje después de 5 segundos
|
|
1239
|
+
setTimeout(() => {
|
|
1240
|
+
this.updateStatus('Captura manual', 'Use el botón para capturar', 'ready');
|
|
1241
|
+
}, 5000);
|
|
1242
|
+
}
|
|
1243
|
+
stopPerformanceMonitoring() {
|
|
1244
|
+
// Nota: No necesitamos limpiar más variables porque ya no se usarán
|
|
1245
|
+
// El sistema automáticamente saltará la lógica de performance una vez que hasAutoSwitchedToManual = true
|
|
1246
|
+
}
|
|
1247
|
+
// Método para liberar recursos de ONNX cuando se cambia a modo manual
|
|
1248
|
+
releaseOnnxResources() {
|
|
1249
|
+
try {
|
|
1250
|
+
// Liberar recursos del servicio de detección
|
|
1251
|
+
if (this.detectionService) {
|
|
1252
|
+
this.detectionService.cleanup();
|
|
1253
|
+
}
|
|
1254
|
+
}
|
|
1255
|
+
catch (error) {
|
|
1256
|
+
}
|
|
1257
|
+
}
|
|
1136
1258
|
completeProcess(skippedBack = false) {
|
|
1137
1259
|
this.stateManager.updateCaptureState({
|
|
1138
1260
|
step: 'completed',
|
|
@@ -1246,6 +1368,13 @@ export class JaakStamps {
|
|
|
1246
1368
|
this.detectionBoxes = [];
|
|
1247
1369
|
this.alignmentStartTime = undefined;
|
|
1248
1370
|
this.hasDocumentDetected = false;
|
|
1371
|
+
// Reset sistema simplificado
|
|
1372
|
+
this.processedFramesCount = 0;
|
|
1373
|
+
this.slowFrameCount = 0;
|
|
1374
|
+
// Reset performance degradation state
|
|
1375
|
+
this.hasAutoSwitchedToManual = false;
|
|
1376
|
+
this.performanceDegradedMode = false;
|
|
1377
|
+
this.showPerformanceMessage = false;
|
|
1249
1378
|
if (this.alignmentTimer) {
|
|
1250
1379
|
clearTimeout(this.alignmentTimer);
|
|
1251
1380
|
this.alignmentTimer = undefined;
|
|
@@ -1609,7 +1738,8 @@ export class JaakStamps {
|
|
|
1609
1738
|
"performanceData": {},
|
|
1610
1739
|
"backDocumentTimerRemaining": {},
|
|
1611
1740
|
"showManualCaptureButton": {},
|
|
1612
|
-
"
|
|
1741
|
+
"performanceDegradedMode": {},
|
|
1742
|
+
"showPerformanceMessage": {}
|
|
1613
1743
|
};
|
|
1614
1744
|
}
|
|
1615
1745
|
static get events() {
|