@jaak.ai/stamps 2.5.3 → 2.5.4-dev.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cjs/jaak-stamps.cjs.entry.js +293 -12
- 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 +293 -12
- package/dist/collection/components/my-component/my-component.js.map +1 -1
- package/dist/components/jaak-stamps.js +293 -12
- package/dist/components/jaak-stamps.js.map +1 -1
- package/dist/esm/jaak-stamps.entry.js +293 -12
- 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-adece4d2.entry.js → p-0f4d77b3.entry.js} +3 -3
- package/dist/jaak-stamps-webcomponent/p-0f4d77b3.entry.js.map +1 -0
- package/dist/types/components/my-component/my-component.d.ts +10 -0
- package/package.json +1 -1
- package/dist/jaak-stamps-webcomponent/p-adece4d2.entry.js.map +0 -1
|
@@ -18779,6 +18779,18 @@ const JaakStamps = class {
|
|
|
18779
18779
|
processedFramesCount = 0; // Contador total de frames procesados
|
|
18780
18780
|
hasAutoSwitchedToManual = false;
|
|
18781
18781
|
_manualModeLoggedOnce = false;
|
|
18782
|
+
VIDEO_DIAGNOSTIC_EVENTS = [
|
|
18783
|
+
'loadstart',
|
|
18784
|
+
'loadedmetadata',
|
|
18785
|
+
'loadeddata',
|
|
18786
|
+
'canplay',
|
|
18787
|
+
'playing',
|
|
18788
|
+
'pause',
|
|
18789
|
+
'stalled',
|
|
18790
|
+
'suspend',
|
|
18791
|
+
'abort',
|
|
18792
|
+
'emptied',
|
|
18793
|
+
];
|
|
18782
18794
|
// Canvas pool for optimized screenshot capture
|
|
18783
18795
|
canvasPool = [];
|
|
18784
18796
|
MAX_CANVAS_POOL_SIZE = 3;
|
|
@@ -19507,6 +19519,130 @@ const JaakStamps = class {
|
|
|
19507
19519
|
memoryMB: deviceMemory ? deviceMemory * 1024 : null
|
|
19508
19520
|
};
|
|
19509
19521
|
}
|
|
19522
|
+
debugLog(message, details) {
|
|
19523
|
+
if (!this.debug) {
|
|
19524
|
+
return;
|
|
19525
|
+
}
|
|
19526
|
+
if (typeof details === 'undefined') {
|
|
19527
|
+
console.log(`[jaak-stamps][diag] ${message}`);
|
|
19528
|
+
return;
|
|
19529
|
+
}
|
|
19530
|
+
console.log(`[jaak-stamps][diag] ${message}`, details);
|
|
19531
|
+
}
|
|
19532
|
+
debugWarn(message, details) {
|
|
19533
|
+
if (!this.debug) {
|
|
19534
|
+
return;
|
|
19535
|
+
}
|
|
19536
|
+
if (typeof details === 'undefined') {
|
|
19537
|
+
console.warn(`[jaak-stamps][diag] ${message}`);
|
|
19538
|
+
return;
|
|
19539
|
+
}
|
|
19540
|
+
console.warn(`[jaak-stamps][diag] ${message}`, details);
|
|
19541
|
+
}
|
|
19542
|
+
summarizeId(id) {
|
|
19543
|
+
if (!id) {
|
|
19544
|
+
return null;
|
|
19545
|
+
}
|
|
19546
|
+
return id.length <= 8 ? id : `${id.slice(0, 8)}...`;
|
|
19547
|
+
}
|
|
19548
|
+
getCameraDevicesSnapshot() {
|
|
19549
|
+
return this.cameraService.getAvailableCameras().map(camera => ({
|
|
19550
|
+
label: camera.label || '(sin label)',
|
|
19551
|
+
deviceId: this.summarizeId(camera.deviceId),
|
|
19552
|
+
groupId: this.summarizeId(camera.groupId),
|
|
19553
|
+
kind: camera.kind,
|
|
19554
|
+
}));
|
|
19555
|
+
}
|
|
19556
|
+
sanitizeTrackSettings(settings) {
|
|
19557
|
+
if (!settings) {
|
|
19558
|
+
return null;
|
|
19559
|
+
}
|
|
19560
|
+
return {
|
|
19561
|
+
...settings,
|
|
19562
|
+
deviceId: this.summarizeId(settings.deviceId),
|
|
19563
|
+
groupId: this.summarizeId(settings.groupId),
|
|
19564
|
+
};
|
|
19565
|
+
}
|
|
19566
|
+
sanitizeTrackConstraints(track) {
|
|
19567
|
+
if (!track) {
|
|
19568
|
+
return null;
|
|
19569
|
+
}
|
|
19570
|
+
const constraints = track.getConstraints ? track.getConstraints() : {};
|
|
19571
|
+
const sanitizedConstraints = { ...constraints };
|
|
19572
|
+
if (typeof sanitizedConstraints.deviceId === 'string') {
|
|
19573
|
+
sanitizedConstraints.deviceId = this.summarizeId(sanitizedConstraints.deviceId);
|
|
19574
|
+
}
|
|
19575
|
+
return sanitizedConstraints;
|
|
19576
|
+
}
|
|
19577
|
+
getStreamSnapshot(stream) {
|
|
19578
|
+
if (!stream) {
|
|
19579
|
+
return { hasStream: false };
|
|
19580
|
+
}
|
|
19581
|
+
const videoTrack = stream.getVideoTracks()[0];
|
|
19582
|
+
if (!videoTrack) {
|
|
19583
|
+
return {
|
|
19584
|
+
hasStream: true,
|
|
19585
|
+
streamActive: stream.active,
|
|
19586
|
+
trackCount: stream.getTracks().length,
|
|
19587
|
+
hasVideoTrack: false,
|
|
19588
|
+
};
|
|
19589
|
+
}
|
|
19590
|
+
return {
|
|
19591
|
+
hasStream: true,
|
|
19592
|
+
streamActive: stream.active,
|
|
19593
|
+
trackCount: stream.getTracks().length,
|
|
19594
|
+
trackLabel: videoTrack.label || '(sin label)',
|
|
19595
|
+
trackEnabled: videoTrack.enabled,
|
|
19596
|
+
trackMuted: videoTrack.muted,
|
|
19597
|
+
trackReadyState: videoTrack.readyState,
|
|
19598
|
+
settings: this.sanitizeTrackSettings(videoTrack.getSettings ? videoTrack.getSettings() : undefined),
|
|
19599
|
+
constraints: this.sanitizeTrackConstraints(videoTrack),
|
|
19600
|
+
};
|
|
19601
|
+
}
|
|
19602
|
+
getVideoElementSnapshot() {
|
|
19603
|
+
if (!this.videoRef) {
|
|
19604
|
+
return { hasVideoRef: false };
|
|
19605
|
+
}
|
|
19606
|
+
const computedStyle = this.el.ownerDocument?.defaultView?.getComputedStyle(this.videoRef);
|
|
19607
|
+
return {
|
|
19608
|
+
hasVideoRef: true,
|
|
19609
|
+
isConnected: this.videoRef.isConnected,
|
|
19610
|
+
readyState: this.videoRef.readyState,
|
|
19611
|
+
networkState: this.videoRef.networkState,
|
|
19612
|
+
paused: this.videoRef.paused,
|
|
19613
|
+
muted: this.videoRef.muted,
|
|
19614
|
+
autoplay: this.videoRef.autoplay,
|
|
19615
|
+
playsInline: this.videoRef.playsInline,
|
|
19616
|
+
currentTime: Number.isFinite(this.videoRef.currentTime)
|
|
19617
|
+
? Number(this.videoRef.currentTime.toFixed(3))
|
|
19618
|
+
: this.videoRef.currentTime,
|
|
19619
|
+
videoWidth: this.videoRef.videoWidth,
|
|
19620
|
+
videoHeight: this.videoRef.videoHeight,
|
|
19621
|
+
clientWidth: this.videoRef.clientWidth,
|
|
19622
|
+
clientHeight: this.videoRef.clientHeight,
|
|
19623
|
+
hasSrcObject: !!this.videoRef.srcObject,
|
|
19624
|
+
display: computedStyle?.display ?? 'unknown',
|
|
19625
|
+
visibility: computedStyle?.visibility ?? 'unknown',
|
|
19626
|
+
};
|
|
19627
|
+
}
|
|
19628
|
+
attachVideoDiagnosticListeners() {
|
|
19629
|
+
if (!this.debug || !this.videoRef) {
|
|
19630
|
+
return () => undefined;
|
|
19631
|
+
}
|
|
19632
|
+
const video = this.videoRef;
|
|
19633
|
+
const listeners = this.VIDEO_DIAGNOSTIC_EVENTS.map(eventName => {
|
|
19634
|
+
const handler = () => {
|
|
19635
|
+
this.debugLog(`video event "${eventName}"`, this.getVideoElementSnapshot());
|
|
19636
|
+
};
|
|
19637
|
+
video.addEventListener(eventName, handler);
|
|
19638
|
+
return { eventName, handler };
|
|
19639
|
+
});
|
|
19640
|
+
return () => {
|
|
19641
|
+
listeners.forEach(({ eventName, handler }) => {
|
|
19642
|
+
video.removeEventListener(eventName, handler);
|
|
19643
|
+
});
|
|
19644
|
+
};
|
|
19645
|
+
}
|
|
19510
19646
|
// DETECTION METHODS
|
|
19511
19647
|
async startDetection() {
|
|
19512
19648
|
try {
|
|
@@ -19593,12 +19729,19 @@ const JaakStamps = class {
|
|
|
19593
19729
|
this.updateStatus('Configurando cámara...', 'Buscando dispositivos disponibles', 'loading');
|
|
19594
19730
|
try {
|
|
19595
19731
|
await this.cameraService.enumerateDevices();
|
|
19732
|
+
this.debugLog('step 2/5 enumerateDevices()', {
|
|
19733
|
+
cameras: this.getCameraDevicesSnapshot(),
|
|
19734
|
+
selectedCameraId: this.summarizeId(this.cameraService.getSelectedCameraId() || undefined),
|
|
19735
|
+
});
|
|
19596
19736
|
}
|
|
19597
19737
|
catch (enumerateError) {
|
|
19598
19738
|
throw new Error(`Error al enumerar dispositivos: ${enumerateError.message}`);
|
|
19599
19739
|
}
|
|
19600
19740
|
try {
|
|
19601
19741
|
await this.updateCameraInfoWithAutofocus();
|
|
19742
|
+
this.debugLog('step 2/5 updateCameraInfoWithAutofocus()', {
|
|
19743
|
+
cameraInfo: this.cameraInfoWithAutofocus,
|
|
19744
|
+
});
|
|
19602
19745
|
}
|
|
19603
19746
|
catch (cameraInfoError) {
|
|
19604
19747
|
throw new Error(`Error al actualizar información de cámara: ${cameraInfoError.message}`);
|
|
@@ -19608,6 +19751,10 @@ const JaakStamps = class {
|
|
|
19608
19751
|
let stream;
|
|
19609
19752
|
try {
|
|
19610
19753
|
stream = await this.cameraService.setupCamera();
|
|
19754
|
+
this.debugLog('step 3/5 setupCamera() resolved', {
|
|
19755
|
+
stream: this.getStreamSnapshot(stream),
|
|
19756
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19757
|
+
});
|
|
19611
19758
|
}
|
|
19612
19759
|
catch (setupError) {
|
|
19613
19760
|
throw new Error(`Error al configurar cámara: ${setupError.message}`);
|
|
@@ -19620,7 +19767,15 @@ const JaakStamps = class {
|
|
|
19620
19767
|
this.updateStatus('Captura activa', 'Posicione su documento y use el botón para capturar', 'active');
|
|
19621
19768
|
}
|
|
19622
19769
|
try {
|
|
19770
|
+
this.debugLog('step 4/5 initializeVideoStream() start', {
|
|
19771
|
+
stream: this.getStreamSnapshot(stream),
|
|
19772
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19773
|
+
});
|
|
19623
19774
|
await this.initializeVideoStream(stream);
|
|
19775
|
+
this.debugLog('step 4/5 initializeVideoStream() completed', {
|
|
19776
|
+
stream: this.getStreamSnapshot(stream),
|
|
19777
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19778
|
+
});
|
|
19624
19779
|
}
|
|
19625
19780
|
catch (videoError) {
|
|
19626
19781
|
throw new Error(`Error al inicializar video: ${videoError.message}`);
|
|
@@ -19638,9 +19793,19 @@ const JaakStamps = class {
|
|
|
19638
19793
|
if (!this.useDocumentDetector) {
|
|
19639
19794
|
this.showManualCaptureButton = true;
|
|
19640
19795
|
}
|
|
19796
|
+
this.debugLog('step 5/5 capture loop ready', {
|
|
19797
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19798
|
+
stream: this.getStreamSnapshot(this.videoStream),
|
|
19799
|
+
useDocumentDetector: this.useDocumentDetector,
|
|
19800
|
+
});
|
|
19641
19801
|
this.detectFrame();
|
|
19642
19802
|
}
|
|
19643
19803
|
catch (err) {
|
|
19804
|
+
this.debugWarn('startDetection() failed', {
|
|
19805
|
+
error: err instanceof Error ? err.message : String(err),
|
|
19806
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19807
|
+
stream: this.getStreamSnapshot(this.videoStream),
|
|
19808
|
+
});
|
|
19644
19809
|
console.error('[jaak-stamps] Error al preparar captura:', err);
|
|
19645
19810
|
this.updateStatus('Error al iniciar', 'No se pudo preparar la captura', 'error');
|
|
19646
19811
|
this.stateManager.updateCaptureState({ isLoading: false });
|
|
@@ -19650,11 +19815,93 @@ const JaakStamps = class {
|
|
|
19650
19815
|
if (!this.videoRef) {
|
|
19651
19816
|
throw new Error('Video element not available');
|
|
19652
19817
|
}
|
|
19818
|
+
const detachVideoDiagnosticListeners = this.attachVideoDiagnosticListeners();
|
|
19819
|
+
this.debugLog('initializeVideoStream() pre-assign', {
|
|
19820
|
+
stream: this.getStreamSnapshot(stream),
|
|
19821
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19822
|
+
});
|
|
19653
19823
|
this.videoRef.srcObject = stream;
|
|
19654
19824
|
this.videoStream = stream;
|
|
19825
|
+
this.debugLog('initializeVideoStream() post-srcObject assignment', {
|
|
19826
|
+
stream: this.getStreamSnapshot(stream),
|
|
19827
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19828
|
+
});
|
|
19655
19829
|
const isRear = this.cameraService.isRearCamera(stream);
|
|
19656
19830
|
this.shouldMirrorVideo = !isRear;
|
|
19657
19831
|
const LOAD_METADATA_TIMEOUT_MS = 10000;
|
|
19832
|
+
// Diagnostic instrumentation: when the timeout fires we need enough
|
|
19833
|
+
// context to distinguish between "OS muted the track", "permission
|
|
19834
|
+
// revoked mid-flight", "device never produced frames" and other modes
|
|
19835
|
+
// that all surface as the same generic timeout error.
|
|
19836
|
+
const track = stream.getVideoTracks()[0];
|
|
19837
|
+
const waitStart = performance.now();
|
|
19838
|
+
const trackEvents = [];
|
|
19839
|
+
const recordTrackEvent = (event) => {
|
|
19840
|
+
trackEvents.push({
|
|
19841
|
+
at: Math.round(performance.now() - waitStart),
|
|
19842
|
+
event,
|
|
19843
|
+
state: track?.readyState,
|
|
19844
|
+
});
|
|
19845
|
+
};
|
|
19846
|
+
const onTrackMute = () => recordTrackEvent('mute');
|
|
19847
|
+
const onTrackUnmute = () => recordTrackEvent('unmute');
|
|
19848
|
+
const onTrackEnded = () => recordTrackEvent('ended');
|
|
19849
|
+
if (track) {
|
|
19850
|
+
track.addEventListener('mute', onTrackMute);
|
|
19851
|
+
track.addEventListener('unmute', onTrackUnmute);
|
|
19852
|
+
track.addEventListener('ended', onTrackEnded);
|
|
19853
|
+
}
|
|
19854
|
+
const cleanupTrackListeners = () => {
|
|
19855
|
+
if (!track)
|
|
19856
|
+
return;
|
|
19857
|
+
track.removeEventListener('mute', onTrackMute);
|
|
19858
|
+
track.removeEventListener('unmute', onTrackUnmute);
|
|
19859
|
+
track.removeEventListener('ended', onTrackEnded);
|
|
19860
|
+
};
|
|
19861
|
+
const captureDiagnostics = () => {
|
|
19862
|
+
const settings = track?.getSettings?.();
|
|
19863
|
+
const computed = this.videoRef ? getComputedStyle(this.videoRef) : null;
|
|
19864
|
+
return {
|
|
19865
|
+
reason: 'VIDEO_METADATA_TIMEOUT',
|
|
19866
|
+
waitedMs: Math.round(performance.now() - waitStart),
|
|
19867
|
+
stream: {
|
|
19868
|
+
videoTrackCount: stream.getVideoTracks().length,
|
|
19869
|
+
audioTrackCount: stream.getAudioTracks().length,
|
|
19870
|
+
},
|
|
19871
|
+
track: track ? {
|
|
19872
|
+
readyState: track.readyState,
|
|
19873
|
+
muted: track.muted,
|
|
19874
|
+
enabled: track.enabled,
|
|
19875
|
+
label: track.label,
|
|
19876
|
+
kind: track.kind,
|
|
19877
|
+
settings: settings ? {
|
|
19878
|
+
width: settings.width,
|
|
19879
|
+
height: settings.height,
|
|
19880
|
+
frameRate: settings.frameRate,
|
|
19881
|
+
deviceId: settings.deviceId,
|
|
19882
|
+
facingMode: settings.facingMode,
|
|
19883
|
+
} : null,
|
|
19884
|
+
} : null,
|
|
19885
|
+
video: this.videoRef ? {
|
|
19886
|
+
readyState: this.videoRef.readyState,
|
|
19887
|
+
networkState: this.videoRef.networkState,
|
|
19888
|
+
error: this.videoRef.error ? { code: this.videoRef.error.code, message: this.videoRef.error.message } : null,
|
|
19889
|
+
paused: this.videoRef.paused,
|
|
19890
|
+
offsetWidth: this.videoRef.offsetWidth,
|
|
19891
|
+
offsetHeight: this.videoRef.offsetHeight,
|
|
19892
|
+
videoWidth: this.videoRef.videoWidth,
|
|
19893
|
+
videoHeight: this.videoRef.videoHeight,
|
|
19894
|
+
display: computed?.display,
|
|
19895
|
+
visibility: computed?.visibility,
|
|
19896
|
+
} : null,
|
|
19897
|
+
document: {
|
|
19898
|
+
visibilityState: document.visibilityState,
|
|
19899
|
+
hasFocus: document.hasFocus(),
|
|
19900
|
+
},
|
|
19901
|
+
trackEvents,
|
|
19902
|
+
userAgent: navigator.userAgent,
|
|
19903
|
+
};
|
|
19904
|
+
};
|
|
19658
19905
|
const finalizeStreamInitialization = async () => {
|
|
19659
19906
|
try {
|
|
19660
19907
|
await this.videoRef.play();
|
|
@@ -19669,24 +19916,39 @@ const JaakStamps = class {
|
|
|
19669
19916
|
const rect = container.getBoundingClientRect();
|
|
19670
19917
|
this.updateMaskDimensions(rect);
|
|
19671
19918
|
}
|
|
19919
|
+
this.debugLog('initializeVideoStream() finalized after play()', {
|
|
19920
|
+
stream: this.getStreamSnapshot(stream),
|
|
19921
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19922
|
+
});
|
|
19672
19923
|
};
|
|
19673
19924
|
// If metadata is already available (readyState >= HAVE_METADATA = 1),
|
|
19674
19925
|
// the 'loadedmetadata' event will not fire again. Handle both cases.
|
|
19675
19926
|
if (this.videoRef.readyState >= 1) {
|
|
19676
|
-
|
|
19677
|
-
|
|
19678
|
-
}
|
|
19927
|
+
this.debugLog('video metadata already available, skipping event wait', this.getVideoElementSnapshot());
|
|
19928
|
+
cleanupTrackListeners();
|
|
19679
19929
|
await finalizeStreamInitialization();
|
|
19930
|
+
detachVideoDiagnosticListeners();
|
|
19680
19931
|
return;
|
|
19681
19932
|
}
|
|
19682
19933
|
return new Promise((resolve, reject) => {
|
|
19683
19934
|
let settled = false;
|
|
19935
|
+
const cleanup = () => {
|
|
19936
|
+
this.videoRef.onloadedmetadata = null;
|
|
19937
|
+
this.videoRef.onerror = null;
|
|
19938
|
+
detachVideoDiagnosticListeners();
|
|
19939
|
+
};
|
|
19684
19940
|
const timeoutId = setTimeout(() => {
|
|
19685
19941
|
if (settled)
|
|
19686
19942
|
return;
|
|
19687
19943
|
settled = true;
|
|
19688
|
-
|
|
19689
|
-
this.
|
|
19944
|
+
const diagnostics = captureDiagnostics();
|
|
19945
|
+
this.debugWarn(`initializeVideoStream() timeout after ${LOAD_METADATA_TIMEOUT_MS}ms`, {
|
|
19946
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19947
|
+
stream: this.getStreamSnapshot(stream),
|
|
19948
|
+
});
|
|
19949
|
+
console.error('[jaak-stamps] Video metadata timeout diagnostics (json):', JSON.stringify(diagnostics));
|
|
19950
|
+
cleanup();
|
|
19951
|
+
cleanupTrackListeners();
|
|
19690
19952
|
reject(new Error(`Video metadata load timeout after ${LOAD_METADATA_TIMEOUT_MS}ms`));
|
|
19691
19953
|
}, LOAD_METADATA_TIMEOUT_MS);
|
|
19692
19954
|
this.videoRef.onloadedmetadata = async () => {
|
|
@@ -19694,13 +19956,18 @@ const JaakStamps = class {
|
|
|
19694
19956
|
return;
|
|
19695
19957
|
settled = true;
|
|
19696
19958
|
clearTimeout(timeoutId);
|
|
19697
|
-
this.
|
|
19698
|
-
|
|
19959
|
+
this.debugLog('initializeVideoStream() onloadedmetadata fired', {
|
|
19960
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19961
|
+
stream: this.getStreamSnapshot(stream),
|
|
19962
|
+
});
|
|
19963
|
+
cleanupTrackListeners();
|
|
19699
19964
|
try {
|
|
19700
19965
|
await finalizeStreamInitialization();
|
|
19966
|
+
cleanup();
|
|
19701
19967
|
resolve();
|
|
19702
19968
|
}
|
|
19703
19969
|
catch (err) {
|
|
19970
|
+
cleanup();
|
|
19704
19971
|
reject(err);
|
|
19705
19972
|
}
|
|
19706
19973
|
};
|
|
@@ -19709,8 +19976,13 @@ const JaakStamps = class {
|
|
|
19709
19976
|
return;
|
|
19710
19977
|
settled = true;
|
|
19711
19978
|
clearTimeout(timeoutId);
|
|
19712
|
-
this.
|
|
19713
|
-
|
|
19979
|
+
this.debugWarn('initializeVideoStream() video element emitted error', {
|
|
19980
|
+
event,
|
|
19981
|
+
videoRef: this.getVideoElementSnapshot(),
|
|
19982
|
+
stream: this.getStreamSnapshot(stream),
|
|
19983
|
+
});
|
|
19984
|
+
cleanup();
|
|
19985
|
+
cleanupTrackListeners();
|
|
19714
19986
|
reject(new Error(`Video element error: ${event}`));
|
|
19715
19987
|
};
|
|
19716
19988
|
});
|
|
@@ -19935,7 +20207,16 @@ const JaakStamps = class {
|
|
|
19935
20207
|
isCapturing: false
|
|
19936
20208
|
};
|
|
19937
20209
|
const cameraInfo = this.cameraInfoWithAutofocus;
|
|
19938
|
-
return (h("div", { key: '
|
|
20210
|
+
return (h("div", { key: '958fb0a94dcab5e15b2da9b2f6e1219d85e1f03a', class: "detector-container" }, !this.licenseValid && this.licenseError && (h("div", { key: 'b455ba5f14b5415d2b49c8ace3ead469cd2a7acc', class: "license-error-container" }, h("div", { key: '4c1e7f980319cf125b5186e26158c37a7a97842c', class: "license-error-card" }, h("svg", { key: '4c411ef193d03c543fe9298bc3aa077dcaf6b7ea', class: "license-error-icon", width: "64", height: "64", viewBox: "0 0 24 24", fill: "none", xmlns: "http://www.w3.org/2000/svg" }, h("path", { key: '24f0eb292901ee9cef24afdc2161bc69f6a51cd0', d: "M12 22C12 22 20 18 20 12V5L12 2L4 5V12C4 18 12 22 12 22Z", stroke: "currentColor", "stroke-width": "2", "stroke-linecap": "round", "stroke-linejoin": "round" }), h("path", { key: 'e5e61abf14d9422633d1c3de9efb7d1a909c941c', d: "M12 8V12", stroke: "currentColor", "stroke-width": "2", "stroke-linecap": "round" }), h("circle", { key: 'f5612a5748a26d33fbfa9a60ea084614f53197f9', cx: "12", cy: "16", r: "0.5", fill: "currentColor", stroke: "currentColor", "stroke-width": "1" })), h("h2", { key: '5ba51ab22b3dc341a5a59661a5f4f87d6dcc4f96', class: "license-error-title" }, "Licencia Requerida"), h("p", { key: 'd162830f9b888ff9d179abd4d532287c3edd2b44', class: "license-error-message" }, this.licenseError), h("p", { key: '8ac80117990849f03c4cac091a9642160b49c109', class: "license-error-help" }, "Contacte a soporte: ", h("a", { key: 'df4b871006f2d4e5f95be43b4a2c3699288d3773', href: "mailto:support@jaak.ai" }, "support@jaak.ai")), h("div", { key: 'aa1aacb0dc56c76cce5d6bdac373f2e64d7b3f18', class: "license-error-footer" }, "JAAK Stamps")))), this.licenseValid && (h("div", { key: '0a5a3ad11c511d0d8f1b33a4a2fff32aede47277', class: "video-container" }, h("video", { key: 'db9c667c035c27aec76625385bb7b1ec0624736e', ref: el => this.videoRef = el, autoplay: true, muted: true, playsinline: true, class: this.shouldMirrorVideo ? 'mirror' : '', style: {
|
|
20211
|
+
// Keep the element rendered (display: block) so the browser
|
|
20212
|
+
// loads stream metadata and fires 'loadedmetadata'. Hiding it
|
|
20213
|
+
// with display:none prevents metadata loading in Chrome and
|
|
20214
|
+
// causes initializeVideoStream to hang waiting for the event.
|
|
20215
|
+
// Use opacity + visibility to hide visually while keeping the
|
|
20216
|
+
// render context alive.
|
|
20217
|
+
opacity: captureState.isVideoActive ? '1' : '0',
|
|
20218
|
+
visibility: captureState.isVideoActive ? 'visible' : 'hidden',
|
|
20219
|
+
} }), h("div", { key: '424765f58b596d8459ae903245ee8e0717eaf14a', 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: {
|
|
19939
20220
|
position: 'absolute',
|
|
19940
20221
|
left: `${box.x}px`,
|
|
19941
20222
|
top: `${box.y}px`,
|
|
@@ -19944,9 +20225,9 @@ const JaakStamps = class {
|
|
|
19944
20225
|
border: '2px solid #32406C',
|
|
19945
20226
|
pointerEvents: 'none',
|
|
19946
20227
|
boxSizing: 'border-box'
|
|
19947
|
-
} })))), this.isMaskReady && (h("div", { key: '
|
|
20228
|
+
} })))), this.isMaskReady && (h("div", { key: '26b11d2375ac441dbd8b5eaec4f5976df4d1f0aa', class: "overlay-mask" }, h("div", { key: '51d95dab401719ed84533a76e58ce00c12d4f72a', class: "card-outline" }, h("div", { key: 'd2b87cb68858e74340611a46ea7e3efc1691f46e', class: "side side-top" }), h("div", { key: '55ff7658fcc123535c9710133ef4d8973bca1d2e', class: "side side-right" }), h("div", { key: '0dfa4f296ff756afa2003eb4fb368d208128c47e', class: "side side-bottom" }), h("div", { key: '9aefe3fef283ee27cbe412d27a1a873cd871eb1a', class: "side side-left" })), !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: 'ae93e17580fe8d6efa460857011ebf36d4b162b6', class: `guide-text ${this.showPerformanceMessage ? 'performance-warning-text' : ''}` }, this.getGuideText(captureState.step))), captureState.step === 'back' && !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: 'a9835585d26c8819ffb12e5a278d19c89d17ec6a', class: "back-capture-section" }, h("div", { key: '7563c10750eb649c337379bcd1966ebbe4c0a7be', class: "back-capture-buttons" }, (!this.useDocumentDetector || this.performanceDegradedMode || this.showManualCaptureButton) && (h("button", { key: '0c44faf4123197765b0bad30f5674ce7b1cc4f00', class: "capture-button primary-button", onClick: () => this.takeManualScreenshot(), type: "button", disabled: this.processingButton !== null }, this.processingButton === 'capture-back' && (h("span", { key: 'efed4645446e3ac5189dcc909998bda49771e61d', class: "button-spinner" })), "Capturar Reverso")), h("button", { key: '7f21e533d151507cb8aefeb232e2e6924ec4a935', class: "skip-button", onClick: () => this.skipBackCapture(), type: "button", disabled: this.processingButton !== null }, this.processingButton === 'skip-back' && (h("span", { key: '2634e6953b71e30b658dc632d853124f5ce5bb91', class: "button-spinner" })), this.enableBackDocumentTimer && this.backDocumentTimerRemaining > 0
|
|
19948
20229
|
? `Saltar reverso (${this.backDocumentTimerRemaining}s)`
|
|
19949
|
-
: 'Saltar reverso')))), captureState.isVideoActive && (h("div", { key: '
|
|
20230
|
+
: 'Saltar reverso')))), captureState.isVideoActive && (h("div", { key: 'ed8cf74950d02b58d4c8628663ec692d964757f0', class: "camera-controls" }, h("button", { key: 'd309850ed774ac08e63e1eb1ea0019f7c80d3db6', 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: '4a70996d233bffbeac7badc52537d94453db30d3', class: "camera-selector-dropdown" }, h("div", { key: '7f893af0afeff55fe63e4971d0afc24516d2b6a6', class: "camera-selector-header" }, h("span", { key: 'd20382742b5ee5d90f678988d0d2c1c964f615d6' }, "Seleccionar C\u00E1mara"), h("button", { key: '1542d189db50740dd10e2ea843f7c5dccc5e24f2', class: "close-selector", onClick: () => this.toggleCameraSelector(), type: "button" }, "\u00D7")), h("div", { key: 'e7907a23b4c7571c455f906333ccbd8e4172d3c9', 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: '8615ca9b81f57bbf5d52d40fd827b79a637f5e4f', class: "device-info" }, h("small", { key: '6f07c1bfb1a2b3824ccdfae4ebca11b0fa0297fe' }, "Dispositivo: ", cameraInfo.deviceType)))), this.showManualCaptureButton && captureState.step === 'front' && !captureState.showFlipAnimation && !captureState.showSuccessAnimation && (h("div", { key: 'c1c18723517003f2bcb9f68c527a13c4e6f30095', class: "manual-capture-section" }, h("button", { key: '94d21c348697cd28ecb44a5144e1e105f10e377c', class: "manual-capture-button", onClick: () => this.takeManualScreenshot(), type: "button", disabled: this.processingButton !== null }, this.processingButton === 'capture-front' && (h("span", { key: '74333b317328ad70da763e5d127635f3b6dc13d1', class: "button-spinner" })), "Capturar Frente"))))), captureState.isCapturing && (h("div", { key: '6761b16e393c5d496c5fde729b6b36580cfede0c', class: "capture-animation" })), captureState.showFlipAnimation && (h("div", { key: '7556dddec2de2c134f9b09fbd38569366c35da48', class: "flip-animation" }, h("div", { key: 'baa3cd8993ef761ebfb94ccda6d66896959f32ee', class: "id-card-icon" }), h("div", { key: '3c5027ada509290b9abbf599849dbd19e50113af', class: "flip-text" }, "\u00A1Voltea tu identificaci\u00F3n!"))), captureState.showSuccessAnimation && (h("div", { key: '1826a908ea94637428d9e800668d9ee02f0f03de', class: "success-animation" }, h("div", { key: '60d8e894ceed0c5198edb67a1e3e0fa24b9aaa3b', class: "check-icon" }), h("div", { key: '106d6ccec79f64b94273baeb8984f23e71987076', class: "success-text" }, "\u00A1Proceso completado!"))), h("div", { key: '804e4fe62de056dca22964283282e32336f8eb00', class: `component-status status-${this.currentStatus.type}` }, (this.currentStatus.type === 'loading' || this.currentStatus.type === 'initializing') && (h("div", { key: '108d6cab9eb7826cbe396806652a6b096ce0736d', class: "status-spinner" })), h("div", { key: '4abe0717c6b66b2bf44eb2da513fb6c22af31725', class: "status-content" }, h("div", { key: '77fb79d89df1f9e25c3c4962235b0605c7b6237f', class: "status-message" }, this.currentStatus.message), this.currentStatus.description && (h("div", { key: '2b24b09eabbbbbedd1270ebbf72f32f19ee063cb', class: "status-description" }, this.currentStatus.description)))), this.debug && (h("div", { key: '7c6bf594cdb26334bfe62ee09d860b19399b4fd2', class: "performance-monitor" }, h("div", { key: '06f2b94e8a08e8afe94a2947d928a4c3c1ec260f', class: "performance-expanded" }, h("div", { key: 'c9302538e10e53e81a5685226c89a293ffd1608b', class: "metrics-row" }, h("div", { key: '7499bee1d362bf9910b401c2f85961847facc9f8', class: "metric-compact" }, h("span", { key: 'f005aab118350af46520ece3615544976b5d533f', class: "metric-label" }, "FPS"), h("span", { key: '69102a7df1fdc559883f807a8d26ae9268e56b01', class: `metric-value ${this.performanceData.fps < 15 ? 'warning' : this.performanceData.fps < 10 ? 'danger' : 'good'}` }, this.performanceData.fps)), h("div", { key: '0a63031beb60eeeb19cd50637f506661cdb1da16', class: "metric-compact" }, h("span", { key: '0231014ed6f077d780252c3b822a269148675d2f', class: "metric-label" }, "MEM"), h("span", { key: '859eda6914fdab077635f983fd4ca01daaf47ce7', class: `metric-value ${this.performanceData.memoryUsage > 100 ? 'warning' : this.performanceData.memoryUsage > 200 ? 'danger' : 'good'}` }, this.performanceData.memoryUsage, "MB"))), h("div", { key: '102218bc7cf2d29c3c8ef7f91febf924ecb418a3', class: "metrics-row" }, h("div", { key: '205e50b3dbc43c541b76c21ef8e19a3defe065ce', class: "metric-compact" }, h("span", { key: '42eace007731c4642040e33f3e20462d7e150494', class: "metric-label" }, "INF"), h("span", { key: 'ff2d169c660011b24fa3340479d91befc9c2d06c', class: `metric-value ${this.performanceData.inferenceTime > 100 ? 'warning' : this.performanceData.inferenceTime > 200 ? 'danger' : 'good'}` }, this.performanceData.inferenceTime, "ms")), h("div", { key: 'ec3ec57e442b3aefb38acf774873b0b181731523', class: "metric-compact" }, h("span", { key: '27d6d74dcdffbdafb4382c40b60f032b20dc5ade', class: "metric-label" }, "FRAME"), h("span", { key: 'e55795508f97a27c0b03736de2e5960560970378', class: `metric-value ${this.performanceData.frameProcessingTime > 50 ? 'warning' : this.performanceData.frameProcessingTime > 100 ? 'danger' : 'good'}` }, this.performanceData.frameProcessingTime, "ms"))), h("div", { key: '60e80821ed57f1a724409e26a232fa2792886011', class: "metrics-row" }, h("div", { key: '7deb1504fb3705affaab105782ed7107d6e1a501', class: "metric-compact" }, h("span", { key: '0658ce3204ce120557caa248505def48a8a205dd', class: "metric-label" }, "DET"), h("span", { key: '6b14fafc3903912380edda27e5024e1221917db7', class: "metric-value good" }, this.performanceData.successfulDetections, "/", this.performanceData.totalDetections)), h("div", { key: 'ec602c3b4d7d8ab0ffbf165d98e8b2e7d7d0b0ec', class: "metric-compact" }, h("span", { key: '9615ae1d383d383f116d2953f05ddb252336f7be', class: "metric-label" }, "RATE"), h("span", { key: 'eca7277e9185b9ff4232e556e707a3f1ce80365f', class: `metric-value ${this.performanceData.detectionRate < 30 ? 'danger' : this.performanceData.detectionRate < 60 ? 'warning' : 'good'}` }, this.performanceData.detectionRate, "%")))))), h("div", { key: '3b6b9368797965d5795c9752d2b4a08a9934b441', class: "watermark" }, h("img", { key: 'b40ffaeb6f88d1a744bffeb64ac11d4f19be6220', src: "https://static.jaak.ai/commons/powered-by-jaak.png", alt: "Powered by Jaak" }))))));
|
|
19950
20231
|
}
|
|
19951
20232
|
// Utility methods
|
|
19952
20233
|
updateDetectionBoxes(boxes) {
|