@nddeps/barcode-scanner 0.3.1 → 0.4.0

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nddeps/barcode-scanner",
3
- "version": "0.3.1",
3
+ "version": "0.4.0",
4
4
  "private": false,
5
5
  "keywords": [
6
6
  "barcode",
@@ -34,9 +34,6 @@
34
34
  "dev": "vite",
35
35
  "preview": "vite preview"
36
36
  },
37
- "overrides": {
38
- "vite": "npm:rolldown-vite@7.3.1"
39
- },
40
37
  "dependencies": {
41
38
  "barcode-detector": "^3.0.8",
42
39
  "zxing-wasm": "^2.2.4"
@@ -63,6 +60,6 @@
63
60
  "stylelint-order": "^7.0.1",
64
61
  "typescript": "~5.9.3",
65
62
  "typescript-eslint": "^8.54.0",
66
- "vite": "npm:rolldown-vite@7.3.1"
63
+ "vite": "^7.3.1"
67
64
  }
68
65
  }
package/dist/index.js DELETED
@@ -1,289 +0,0 @@
1
- function createWatchable(e) {
2
- let r = new EventTarget(), i = new Proxy(e, {
3
- get(e, r, i) {
4
- return Reflect.get(e, r, i);
5
- },
6
- set(e, i, a, o) {
7
- let s = Reflect.set(e, i, a, o);
8
- return r.dispatchEvent(new CustomEvent("change")), s;
9
- }
10
- });
11
- function a(e, i) {
12
- let a = e();
13
- function o() {
14
- let r = e();
15
- JSON.stringify(r) !== JSON.stringify(a) && (a = r, i(r));
16
- }
17
- return r.addEventListener("change", o), () => r.removeEventListener("change", o);
18
- }
19
- return {
20
- state: i,
21
- watch: a
22
- };
23
- }
24
- async function hasCameraAccess() {
25
- try {
26
- return (await navigator.permissions.query({ name: "camera" })).state === "granted";
27
- } catch {
28
- return (await navigator.mediaDevices.enumerateDevices()).filter((e) => e.deviceId && e.kind === "videoinput").length > 0;
29
- }
30
- }
31
- async function getCameraAccess() {
32
- if (await hasCameraAccess()) return !0;
33
- try {
34
- let e = (await navigator.mediaDevices.getUserMedia({ video: !0 })).getTracks();
35
- for (let r of e) r.stop();
36
- return !0;
37
- } catch {
38
- return !1;
39
- }
40
- }
41
- function getScanArea(e) {
42
- let r = Math.round(2 / 3 * Math.min(e.videoWidth, e.videoHeight));
43
- return {
44
- height: r,
45
- width: r,
46
- x: Math.round((e.videoWidth - r) / 2),
47
- y: Math.round((e.videoHeight - r) / 2)
48
- };
49
- }
50
- function getVideoRenderOffset(e, r) {
51
- let [i, a] = window.getComputedStyle(e).objectPosition.split(" ").map((i, a) => i.endsWith("%") ? (a === 0 ? e.offsetWidth - r.width : e.offsetHeight - r.height) * parseFloat(i) / 100 : parseFloat(i));
52
- return {
53
- x: i,
54
- y: a
55
- };
56
- }
57
- function getVideoRenderSize(e) {
58
- let r = window.getComputedStyle(e), i = {
59
- height: e.offsetHeight,
60
- width: e.offsetWidth
61
- }, a = i.width / i.height, o = {
62
- height: e.videoHeight,
63
- width: e.videoWidth
64
- }, s = o.width / o.height;
65
- switch (r.objectFit) {
66
- case "contain": return {
67
- height: s < a ? e.offsetHeight : e.offsetWidth / s,
68
- width: s < a ? e.offsetHeight * s : e.offsetWidth
69
- };
70
- case "cover": return {
71
- height: s > a ? e.offsetHeight : e.offsetWidth / s,
72
- width: s > a ? e.offsetHeight * s : e.offsetWidth
73
- };
74
- case "fill": return i;
75
- case "none": return o;
76
- case "scale-down": return {
77
- height: Math.min(s < a ? e.offsetHeight : e.offsetWidth / s, e.videoHeight),
78
- width: Math.min(s < a ? e.offsetHeight * s : e.offsetWidth, e.videoWidth)
79
- };
80
- default: return o;
81
- }
82
- }
83
- function isBarcodeDetectorAvailable(e) {
84
- return "BarcodeDetector" in e;
85
- }
86
- function translateAreaToVideoRender(e, r) {
87
- let i = /scaleX\(-1\)/.test(e.style.transform), a = getVideoRenderSize(e), c = getVideoRenderOffset(e, a), l = i ? e.videoWidth - r.x - r.width : r.x, u = r.y;
88
- return {
89
- height: r.height / e.videoHeight * a.height,
90
- width: r.width / e.videoWidth * a.width,
91
- x: l / e.videoWidth * a.width + c.x,
92
- y: u / e.videoHeight * a.height + c.y
93
- };
94
- }
95
- function translateAreaToVideoSource(e, r) {
96
- let i = /scaleX\(-1\)/.test(e.style.transform), a = getVideoRenderSize(e), c = getVideoRenderOffset(e, a), l = i ? a.width - (r.x - c.x) - r.width : r.x - c.x, u = r.y - c.y, d = e.videoHeight / a.height, f = e.videoWidth / a.width;
97
- return {
98
- height: r.height * d,
99
- width: r.width * f,
100
- x: l * f,
101
- y: u * d
102
- };
103
- }
104
- function wait(e) {
105
- return new Promise((r) => setTimeout(r, e));
106
- }
107
- var Dt = [
108
- ["Aztec", "M"],
109
- ["Codabar", "L"],
110
- ["Code39", "L"],
111
- ["Code93", "L"],
112
- ["Code128", "L"],
113
- ["DataBar", "L"],
114
- ["DataBarExpanded", "L"],
115
- ["DataMatrix", "M"],
116
- ["EAN-8", "L"],
117
- ["EAN-13", "L"],
118
- ["ITF", "L"],
119
- ["MaxiCode", "M"],
120
- ["PDF417", "M"],
121
- ["QRCode", "M"],
122
- ["UPC-A", "L"],
123
- ["UPC-E", "L"],
124
- ["MicroQRCode", "M"],
125
- ["rMQRCode", "M"],
126
- ["DXFilmEdge", "L"],
127
- ["DataBarLimited", "L"]
128
- ], Mt = Dt.map(([e]) => e);
129
- Mt.filter((e, r) => Dt[r][1] === "L"), Mt.filter((e, r) => Dt[r][1] === "M");
130
- var It = {
131
- formats: [],
132
- tryHarder: !0,
133
- tryRotate: !0,
134
- tryInvert: !0,
135
- tryDownscale: !0,
136
- tryDenoise: !1,
137
- binarizer: "LocalAverage",
138
- isPure: !1,
139
- downscaleFactor: 3,
140
- downscaleThreshold: 500,
141
- minLineCount: 2,
142
- maxNumberOfSymbols: 255,
143
- tryCode39ExtendedMode: !0,
144
- returnErrors: !1,
145
- eanAddOnSymbol: "Ignore",
146
- textMode: "HRI",
147
- characterSet: "Unknown"
148
- };
149
- ({ ...It }), [...It.formats], [...[
150
- ["aztec", "Aztec"],
151
- ["code_128", "Code128"],
152
- ["code_39", "Code39"],
153
- ["code_93", "Code93"],
154
- ["codabar", "Codabar"],
155
- ["databar", "DataBar"],
156
- ["databar_expanded", "DataBarExpanded"],
157
- ["databar_limited", "DataBarLimited"],
158
- ["data_matrix", "DataMatrix"],
159
- ["dx_film_edge", "DXFilmEdge"],
160
- ["ean_13", "EAN-13"],
161
- ["ean_8", "EAN-8"],
162
- ["itf", "ITF"],
163
- ["maxi_code", "MaxiCode"],
164
- ["micro_qr_code", "MicroQRCode"],
165
- ["pdf417", "PDF417"],
166
- ["qr_code", "QRCode"],
167
- ["rm_qr_code", "rMQRCode"],
168
- ["upc_a", "UPC-A"],
169
- ["upc_e", "UPC-E"],
170
- ["linear_codes", "Linear-Codes"],
171
- ["matrix_codes", "Matrix-Codes"],
172
- ["any", "Any"]
173
- ], ["unknown"]].map((e) => e[0]);
174
- var instance = { value: null };
175
- async function decode(e) {
176
- let r = instance.value;
177
- if (!r) throw Error("Worker not installed");
178
- let i = `${performance.now()}-${Math.random().toString(36).slice(2)}`;
179
- return new Promise((a, o) => {
180
- let s = 0, c = ({ data: { payload: e, type: o } }) => {
181
- o !== "decode" || e.uuid !== i || (clearTimeout(s), r.removeEventListener("message", c), a(e.data));
182
- };
183
- s = setTimeout(() => {
184
- r.removeEventListener("message", c), o(null);
185
- }, 1e3), r.addEventListener("message", c), r.postMessage({
186
- payload: {
187
- data: e,
188
- uuid: i
189
- },
190
- type: "decode"
191
- });
192
- });
193
- }
194
- function install() {
195
- if (instance.value) return Promise.resolve(instance.value);
196
- let e = new Worker(new URL(
197
- /* @vite-ignore */
198
- "" + new URL("worker.js", import.meta.url).href,
199
- "" + import.meta.url
200
- ), { type: "module" });
201
- return new Promise((r, i) => {
202
- e.addEventListener("message", ({ data: { type: a } }) => {
203
- a === "init" ? r(e) : i(/* @__PURE__ */ Error("Worker load failed"));
204
- }, { once: !0 }), instance.value = e;
205
- });
206
- }
207
- function createBarcodeScanner(r, { calcScanArea: o, debug: s = !1 } = {}) {
208
- if (!(r instanceof HTMLVideoElement)) throw Error("video is not a HTMLVideoElement");
209
- let c = document.createElement("canvas"), l = c.getContext("2d", { willReadFrequently: !0 });
210
- if (!l) throw Error("Failed to get canvas context");
211
- let { state: u, watch: d } = createWatchable({
212
- calcScanArea: o ?? getScanArea,
213
- canvas: c,
214
- canvasContext: l,
215
- debug: s,
216
- decodeFrameRequestTimestamp: performance.now(),
217
- facingMode: "environment",
218
- isDecodeFrameProcessed: !1,
219
- isDestroyed: !1,
220
- isReady: !1,
221
- isVideoActive: !1,
222
- isVideoPaused: !1,
223
- onDecodeFailure: () => {},
224
- onDecodeSuccess: () => {},
225
- requestFrame: r.requestVideoFrameCallback ? r.requestVideoFrameCallback.bind(r) : requestAnimationFrame,
226
- resumeOnVisibilityChange: !1,
227
- scanArea: {
228
- height: 0,
229
- width: 0,
230
- x: 0,
231
- y: 0
232
- },
233
- scanRate: 24,
234
- video: r,
235
- worker: null
236
- });
237
- install().then((e) => u.worker = e).then(() => Promise.resolve()).then(() => u.isReady = !0), u.video.autoplay = !0, u.video.disablePictureInPicture = !0, u.video.hidden = !1, u.video.muted = !0, u.video.playsInline = !0, document.addEventListener("visibilitychange", f);
238
- function f() {
239
- s && console.log("barcode-scanner:handleVisibilityChange", document.visibilityState, u), document.visibilityState === "hidden" ? u.isVideoActive && u.isVideoPaused === !1 && (u.resumeOnVisibilityChange = !0, h()) : u.resumeOnVisibilityChange && (u.resumeOnVisibilityChange = !1, g({ facingMode: u.facingMode }, u.onDecodeSuccess, u.onDecodeFailure));
240
- }
241
- function p(e, r) {
242
- s && console.log("barcode-scanner:handleDecode", u, performance.now()), !(u.isDestroyed || u.isVideoActive === !1 || u.isVideoPaused) && u.requestFrame(() => {
243
- if (u.isReady === !1 || performance.now() - u.decodeFrameRequestTimestamp < 1e3 / u.scanRate || u.isDecodeFrameProcessed || u.video.readyState <= 1) {
244
- u.decodeFrameRequestTimestamp = performance.now(), p(e, r);
245
- return;
246
- }
247
- u.isDecodeFrameProcessed = !0, u.scanArea = u.calcScanArea(u.video), u.canvas.height = u.scanArea.height, u.canvas.width = u.scanArea.width, u.canvasContext.clearRect(0, 0, u.canvas.width, u.canvas.height), u.canvasContext.drawImage(u.video, u.scanArea.x, u.scanArea.y, u.scanArea.width, u.scanArea.height, 0, 0, u.canvas.width, u.canvas.height);
248
- let i = u.canvasContext.getImageData(0, 0, u.canvas.width, u.canvas.height);
249
- u.debug && window.dispatchEvent(new CustomEvent("barcode-scanner:decode-frame", { detail: { imageData: i } })), decode(i).then((i) => {
250
- if (i) {
251
- let r = i.cornerPoints.map((e) => e.x), a = i.cornerPoints.map((e) => e.y);
252
- e(i.rawValue, {
253
- height: Math.max(...a) - Math.min(...a),
254
- width: Math.max(...r) - Math.min(...r),
255
- x: Math.min(...r) + u.scanArea.x,
256
- y: Math.min(...a) + u.scanArea.y
257
- });
258
- } else r();
259
- }).catch(() => {
260
- console.error("Failed to decode barcode");
261
- }).finally(() => {
262
- u.isDecodeFrameProcessed = !1, u.decodeFrameRequestTimestamp = performance.now(), p(e, r);
263
- });
264
- });
265
- }
266
- async function m() {
267
- u.isDestroyed || (_(), document.removeEventListener("visibilitychange", f), u.worker?.terminate(), u.worker = null, u.isDestroyed = !0, u.isReady = !1);
268
- }
269
- function h() {
270
- s && console.log("barcode-scanner:pause", u), u.canvas.height = u.video.videoHeight, u.canvas.width = u.video.videoWidth, u.canvasContext.clearRect(0, 0, u.canvas.width, u.canvas.height), u.canvasContext.drawImage(u.video, 0, 0, u.canvas.width, u.canvas.height, 0, 0, u.canvas.width, u.canvas.height), u.video.poster = u.canvas.toDataURL(), u.video.srcObject instanceof MediaStream && u.video.srcObject.getTracks().forEach((e) => e.stop()), u.video.srcObject = null, u.isVideoPaused = !0;
271
- }
272
- async function g({ facingMode: e = "environment" } = {}, r, a = () => {}) {
273
- if (s && console.log("barcode-scanner:start:before", u), !await getCameraAccess()) throw Error("No camera access");
274
- u.video.srcObject instanceof MediaStream && u.isVideoActive && u.isVideoPaused === !1 || (u.video.srcObject instanceof MediaStream || (u.video.srcObject = await navigator.mediaDevices.getUserMedia({ video: { facingMode: e } })), await u.video.play(), u.facingMode = e, u.isVideoActive = !0, u.isVideoPaused = !1, u.onDecodeFailure = a, u.onDecodeSuccess = r, u.scanArea = u.calcScanArea(u.video), u.video.style.transform = e === "user" ? "scaleX(-1)" : "none", s && console.log("barcode-scanner:start:after", u), p(r, a));
275
- }
276
- function _() {
277
- u.video.srcObject instanceof MediaStream && u.video.srcObject.getTracks().forEach((e) => e.stop()), u.video.poster = "", u.video.srcObject = null, u.isVideoActive = !1, u.isVideoPaused = !1;
278
- }
279
- return {
280
- destroy: m,
281
- pause: h,
282
- start: g,
283
- state: u,
284
- stop: _,
285
- watch: d
286
- };
287
- }
288
- var lib_default = createBarcodeScanner;
289
- export { createBarcodeScanner, lib_default as default, getCameraAccess, getScanArea, getVideoRenderOffset, getVideoRenderSize, hasCameraAccess, isBarcodeDetectorAvailable, translateAreaToVideoRender, translateAreaToVideoSource, wait };
@@ -1,3 +0,0 @@
1
- export * from './worker.decode';
2
- export * from './worker.install';
3
- export * from './worker.instance';
@@ -1,3 +0,0 @@
1
- import { type DetectedBarcode } from 'barcode-detector/ponyfill';
2
- declare function decode(imageData: ImageData): Promise<DetectedBarcode | null>;
3
- export { decode };
@@ -1,2 +0,0 @@
1
- declare function install(): Promise<Worker>;
2
- export { install };
@@ -1,4 +0,0 @@
1
- declare const instance: {
2
- value: null | Worker;
3
- };
4
- export { instance };