packing-bingo 0.2.0 → 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/dist/index.d.cts CHANGED
@@ -1,25 +1,27 @@
1
1
  import * as react from 'react';
2
2
  import { CSSProperties } from 'react';
3
3
  import { PackingBingoOptions, PackingBingoState } from './core.cjs';
4
- export { BingoEvent, BingoItem, DEFAULT_ITEMS, LINES, Messages, PackingBingoInstance, PerfectEvent, createPackingBingo, en, ja } from './core.cjs';
4
+ export { BingoEvent, BingoItem, DEFAULT_ITEMS, LINES, Messages, PackingBingoInstance, PerfectEvent, bingoLines, createPackingBingo, en, ja } from './core.cjs';
5
5
 
6
6
  interface PackingBingoProps extends Omit<PackingBingoOptions, "controlled" | "defaultChecked"> {
7
- /** Controlled state (16 booleans). Update it from `onChange`. */
7
+ /** Controlled state (one boolean per item). Update it from `onChange`. */
8
8
  checked?: readonly boolean[];
9
- /** Initial state for an uncontrolled card (16 booleans), used when nothing is saved under `storageKey`. */
9
+ /** Initial state for an uncontrolled card (one boolean per item), used when nothing is saved under `storageKey`. */
10
10
  defaultChecked?: readonly boolean[];
11
11
  className?: string;
12
12
  style?: CSSProperties;
13
13
  }
14
14
  interface PackingBingoHandle {
15
- /** Clear the card and score (calls onChange). */
15
+ /** Clear the card and score (calls onChange), and put the items back in their own squares. */
16
16
  reset(): void;
17
+ /** Move the items to random squares, as the 🔀 button does. Checks stay with their items. */
18
+ shuffle(): void;
17
19
  /** Set the card. A one-item change plays like a tap; bigger jumps apply quietly. */
18
20
  setChecked(checked: readonly boolean[]): void;
19
21
  getState(): PackingBingoState | null;
20
22
  }
21
23
  /**
22
- * A 4×4 packing-list bingo card. Client-only: it renders an empty <div> on the server and
24
+ * A packing-list bingo card (4×4 by default; any size from 2×2 to 10×10, optionally with a FREE center). Client-only: it renders an empty <div> on the server and
23
25
  * builds the card after mount, so it is safe in Next.js (it ships with "use client").
24
26
  */
25
27
  declare const PackingBingo: react.ForwardRefExoticComponent<PackingBingoProps & react.RefAttributes<PackingBingoHandle>>;
package/dist/index.d.ts CHANGED
@@ -1,25 +1,27 @@
1
1
  import * as react from 'react';
2
2
  import { CSSProperties } from 'react';
3
3
  import { PackingBingoOptions, PackingBingoState } from './core.js';
4
- export { BingoEvent, BingoItem, DEFAULT_ITEMS, LINES, Messages, PackingBingoInstance, PerfectEvent, createPackingBingo, en, ja } from './core.js';
4
+ export { BingoEvent, BingoItem, DEFAULT_ITEMS, LINES, Messages, PackingBingoInstance, PerfectEvent, bingoLines, createPackingBingo, en, ja } from './core.js';
5
5
 
6
6
  interface PackingBingoProps extends Omit<PackingBingoOptions, "controlled" | "defaultChecked"> {
7
- /** Controlled state (16 booleans). Update it from `onChange`. */
7
+ /** Controlled state (one boolean per item). Update it from `onChange`. */
8
8
  checked?: readonly boolean[];
9
- /** Initial state for an uncontrolled card (16 booleans), used when nothing is saved under `storageKey`. */
9
+ /** Initial state for an uncontrolled card (one boolean per item), used when nothing is saved under `storageKey`. */
10
10
  defaultChecked?: readonly boolean[];
11
11
  className?: string;
12
12
  style?: CSSProperties;
13
13
  }
14
14
  interface PackingBingoHandle {
15
- /** Clear the card and score (calls onChange). */
15
+ /** Clear the card and score (calls onChange), and put the items back in their own squares. */
16
16
  reset(): void;
17
+ /** Move the items to random squares, as the 🔀 button does. Checks stay with their items. */
18
+ shuffle(): void;
17
19
  /** Set the card. A one-item change plays like a tap; bigger jumps apply quietly. */
18
20
  setChecked(checked: readonly boolean[]): void;
19
21
  getState(): PackingBingoState | null;
20
22
  }
21
23
  /**
22
- * A 4×4 packing-list bingo card. Client-only: it renders an empty <div> on the server and
24
+ * A packing-list bingo card (4×4 by default; any size from 2×2 to 10×10, optionally with a FREE center). Client-only: it renders an empty <div> on the server and
23
25
  * builds the card after mount, so it is safe in Next.js (it ships with "use client").
24
26
  */
25
27
  declare const PackingBingo: react.ForwardRefExoticComponent<PackingBingoProps & react.RefAttributes<PackingBingoHandle>>;
package/dist/index.js CHANGED
@@ -2,17 +2,18 @@
2
2
  import {
3
3
  DEFAULT_ITEMS,
4
4
  LINES,
5
+ bingoLines,
5
6
  createPackingBingo,
6
7
  en,
7
8
  ja,
8
9
  resolveStorageKey
9
- } from "./chunk-WGZKPODU.js";
10
+ } from "./chunk-BAA2CFUA.js";
10
11
 
11
12
  // src/react.tsx
12
13
  import { forwardRef, useEffect, useImperativeHandle, useRef } from "react";
13
14
  import { jsx } from "react/jsx-runtime";
14
15
  var PackingBingo = forwardRef(function PackingBingo2(props, ref) {
15
- const { checked, defaultChecked, className, style, onChange, onBingo, onPerfect, messages, ...config } = props;
16
+ const { checked, defaultChecked, defaultOrder, className, style, onChange, onBingo, onPerfect, messages, fonts: _fonts, ...config } = props;
16
17
  const host = useRef(null);
17
18
  const inst = useRef(null);
18
19
  const callbacks = useRef({ onChange, onBingo, onPerfect });
@@ -24,6 +25,7 @@ var PackingBingo = forwardRef(function PackingBingo2(props, ref) {
24
25
  const storageKey = resolveStorageKey({ ...config, controlled });
25
26
  const latestKey = useRef(storageKey);
26
27
  if (controlled) latest.current = checked;
28
+ const latestOrder = useRef(defaultOrder);
27
29
  const messageShape = messages ? Object.fromEntries(Object.entries(messages).map(([k, v]) => [k, typeof v === "function" ? "\u0192" : v])) : null;
28
30
  const key = JSON.stringify({ ...config, messageShape, controlled });
29
31
  useEffect(() => {
@@ -39,6 +41,7 @@ var PackingBingo = forwardRef(function PackingBingo2(props, ref) {
39
41
  messages: liveMessages,
40
42
  controlled,
41
43
  defaultChecked: controlled || latestKey.current === storageKey ? latest.current : defaultChecked,
44
+ defaultOrder: latestKey.current === storageKey ? latestOrder.current : defaultOrder,
42
45
  onChange: (next) => {
43
46
  if (!controlled) latest.current = next;
44
47
  callbacks.current.onChange?.(next);
@@ -48,7 +51,9 @@ var PackingBingo = forwardRef(function PackingBingo2(props, ref) {
48
51
  });
49
52
  inst.current = instance;
50
53
  return () => {
51
- if (!controlled) latest.current = instance.getState().checked;
54
+ const state = instance.getState();
55
+ if (!controlled) latest.current = state.checked;
56
+ latestOrder.current = state.order;
52
57
  latestKey.current = storageKey;
53
58
  instance.destroy();
54
59
  if (inst.current === instance) inst.current = null;
@@ -64,6 +69,7 @@ var PackingBingo = forwardRef(function PackingBingo2(props, ref) {
64
69
  ref,
65
70
  () => ({
66
71
  reset: () => inst.current?.reset(),
72
+ shuffle: () => inst.current?.shuffle(),
67
73
  setChecked: (next) => inst.current?.setChecked(next, { animate: true }),
68
74
  getState: () => inst.current?.getState() ?? null
69
75
  }),
@@ -75,6 +81,7 @@ export {
75
81
  DEFAULT_ITEMS,
76
82
  LINES,
77
83
  PackingBingo,
84
+ bingoLines,
78
85
  createPackingBingo,
79
86
  en,
80
87
  ja
@@ -1,24 +1,25 @@
1
- "use strict";var PackingBingo=(()=>{var Se=Object.defineProperty;var bt=Object.getOwnPropertyDescriptor;var dt=Object.getOwnPropertyNames;var mt=Object.prototype.hasOwnProperty;var ft=(o,n)=>{for(var m in n)Se(o,m,{get:n[m],enumerable:!0})},kt=(o,n,m,l)=>{if(n&&typeof n=="object"||typeof n=="function")for(let f of dt(n))!mt.call(o,f)&&f!==m&&Se(o,f,{get:()=>n[f],enumerable:!(l=bt(n,f))||l.enumerable});return o};var ut=o=>kt(Se({},"__esModule",{value:!0}),o);var Et={};ft(Et,{DEFAULT_ITEMS:()=>re,LINES:()=>F,createPackingBingo:()=>wt,en:()=>Ge,ja:()=>Be});var re=[{emoji:"\u{1F4D6}",label:"\u65C5\u306E\u3057\u304A\u308A"},{emoji:"\u{1FAAA}",label:"\u751F\u5F92\u624B\u5E33"},{emoji:"\u{1F3E5}",label:"\u4FDD\u967A\u8A3C\u30B3\u30D4\u30FC"},{emoji:"\u{1F45B}",label:"\u304A\u3053\u3065\u304B\u3044"},{emoji:"\u{1F455}",label:"\u7740\u66FF\u3048"},{emoji:"\u{1F319}",label:"\u30D1\u30B8\u30E3\u30DE"},{emoji:"\u{1F9E5}",label:"\u4E0A\u7740"},{emoji:"\u{1FAA5}",label:"\u6D17\u9762\u7528\u5177"},{emoji:"\u{1F6C1}",label:"\u30BF\u30AA\u30EB"},{emoji:"\u{1F927}",label:"\u30CF\u30F3\u30AB\u30C1\u30FB\u30C6\u30A3\u30C3\u30B7\u30E5"},{emoji:"\u{1F637}",label:"\u30DE\u30B9\u30AF"},{emoji:"\u{1F48A}",label:"\u5E38\u5099\u85AC\u30FB\u9154\u3044\u6B62\u3081"},{emoji:"\u2602\uFE0F",label:"\u6298\u308A\u305F\u305F\u307F\u5098"},{emoji:"\u270F\uFE0F",label:"\u7B46\u8A18\u7528\u5177"},{emoji:"\u{1F6CD}\uFE0F",label:"\u30D3\u30CB\u30FC\u30EB\u888B"},{emoji:"\u{1F4F1}",label:"\u30B9\u30DE\u30DB\u30FB\u5145\u96FB\u5668"}];var Be={title:"\u6301\u3061\u3082\u306E\u30D3\u30F3\u30B4",tag:"\u4FEE\u5B66\u65C5\u884C",subtitle:"\u30BF\u30C3\u30D7\u3067\u30B9\u30BF\u30F3\u30D7\u3002\u30BF\u30C6\u30FB\u30E8\u30B3\u30FB\u30CA\u30CA\u30E1\u3067\u30D3\u30F3\u30B4\uFF01",packed:"\u305D\u308D\u3063\u305F",bingo:"BINGO",score:"SCORE",combo:o=>`${o} COMBO`,comboPop:o=>`${o} COMBO!`,reset:"\u30EA\u30BB\u30C3\u30C8",soundOn:"\u{1F50A} \u97F3\u3042\u308A",soundOff:"\u{1F507} \u97F3\u306A\u3057",stamp:"OK",reachBadge:"\u30EA\u30FC\u30C1",reachPop:"\u30EA\u30FC\u30C1!",bannerSingle:"BINGO!",bannerDouble:"\u30C0\u30D6\u30EB\u30D3\u30F3\u30B4!",bannerTriple:"\u30C8\u30EA\u30D7\u30EB\u30D3\u30F3\u30B4!",bannerNth:o=>`${o} \u30E9\u30A4\u30F3\u76EE\uFF01`,bannerMulti:o=>`\u4E00\u6C17\u306B ${o} \u30E9\u30A4\u30F3\uFF01`,statusStart:o=>`\u306E\u3053\u308A ${o} \u3053\u3002\u307E\u305A\u306F1\u30E9\u30A4\u30F3\u305D\u308D\u3048\u3088\u3046`,statusLines:(o,n)=>`\u30D3\u30F3\u30B4 ${o} \u30E9\u30A4\u30F3\uFF01 \u306E\u3053\u308A ${n} \u3053`,statusReach:o=>`\u30EA\u30FC\u30C1\uFF01 \u3042\u3068${o.slice(0,2).map(n=>`\u300C${n}\u300D`).join("\u304B")}${o.length>2?"\u306A\u3069":""}\u3067\u30D3\u30F3\u30B4`,statusDone:"\u{1F389} \u30D1\u30FC\u30D5\u30A7\u30AF\u30C8\uFF01\u5FD8\u308C\u7269\u30BC\u30ED\u3067\u51FA\u767A\u3067\u304D\u307E\u3059",perfectTag:"\u{1F3C6} PERFECT",perfectStamp:`\u6E96\u5099
2
- \u5B8C\u4E86`,perfectTitle:"\u30D1\u30FC\u30D5\u30A7\u30AF\u30C8\uFF01",perfectBody:`16\u3053 \u305C\u3093\u3076\u305D\u308D\u3063\u305F\uFF01
3
- \u5FD8\u308C\u7269\u30BC\u30ED\u3067\u3001\u3044\u3063\u3066\u3089\u3063\u3057\u3083\u3044\uFF01`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",statCombo:"MAX COMBO",statLines:"BINGO",close:"\u3068\u3058\u308B",demoLabel:"\u30C7\u30E2\uFF1A",demoBingo:"\u25B6 \u30D3\u30F3\u30B4\u3092\u898B\u308B",demoPerfect:"\u25B6 \u30B3\u30F3\u30DC \u2192 \u30D1\u30FC\u30D5\u30A7\u30AF\u30C8",demoRestore:"\u6700\u521D\u306B\u623B\u3059"},Ge={title:"Packing Bingo",tag:"School trip",subtitle:"Tap to stamp. Rows, columns and diagonals all count!",packed:"PACKED",bingo:"BINGO",score:"SCORE",combo:o=>`${o} COMBO`,comboPop:o=>`${o} COMBO!`,reset:"Reset",soundOn:"\u{1F50A} Sound on",soundOff:"\u{1F507} Muted",stamp:"OK",reachBadge:"REACH",reachPop:"Reach!",bannerSingle:"BINGO!",bannerDouble:"DOUBLE BINGO!",bannerTriple:"TRIPLE BINGO!",bannerNth:o=>`Line ${o}!`,bannerMulti:o=>`${o} lines at once!`,statusStart:o=>`${o} to go. Finish a line first!`,statusLines:(o,n)=>`${o} bingo line${o===1?"":"s"}! ${n} to go`,statusReach:o=>`Reach! Pack ${o.slice(0,2).join(" or ")}${o.length>2?" (or more)":""} for a bingo`,statusDone:"\u{1F389} Perfect! Nothing left behind.",perfectTag:"\u{1F3C6} PERFECT",perfectStamp:`ALL
4
- SET`,perfectTitle:"Perfect!",perfectBody:`All 16 packed!
5
- Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",statCombo:"MAX COMBO",statLines:"BINGO",close:"Close",demoLabel:"Demo:",demoBingo:"\u25B6 Show a bingo",demoPerfect:"\u25B6 Combo \u2192 perfect",demoRestore:"Restore"};var Ue=[0,2,4,7,9,12,14,16,19,21,24,26,28,31,33,36],U=o=>523.25*Math.pow(2,o/12);function Ke(o){let n=null,m=null;function l(){if(o()||typeof window>"u")return null;let b=navigator.userActivation;if(!n&&b&&!b.hasBeenActive)return null;if(!n){let d=window.AudioContext??window.webkitAudioContext;if(!d)return null;n=new d;let y=n.createDynamicsCompressor();m=n.createGain(),m.gain.value=.6,m.connect(y).connect(n.destination)}return n.state==="suspended"&&n.resume(),n}function f(b,d=0,y=.15,E="triangle",M=.2,A=0){let p=l();if(!p||!m)return;let x=p.currentTime+d,B=p.createOscillator(),C=p.createGain();B.type=E,B.frequency.setValueAtTime(b,x),A&&B.frequency.exponentialRampToValueAtTime(A,x+y),C.gain.setValueAtTime(1e-4,x),C.gain.exponentialRampToValueAtTime(M,x+.01),C.gain.exponentialRampToValueAtTime(1e-4,x+y),B.connect(C).connect(m),B.start(x),B.stop(x+y+.05)}function P(b=0,d=.3,y=.25,E=1200){let M=l();if(!M||!m)return;let A=M.currentTime+b,p=Math.ceil(M.sampleRate*d),x=M.createBuffer(1,p,M.sampleRate),B=x.getChannelData(0);for(let k=0;k<p;k++)B[k]=(Math.random()*2-1)*Math.pow(1-k/p,2.5);let C=M.createBufferSource(),_=M.createBiquadFilter(),j=M.createGain();C.buffer=x,_.type="bandpass",_.frequency.value=E,_.Q.value=.7,j.gain.value=y,C.connect(_).connect(j).connect(m),C.start(A)}let R=b=>U(Ue[Math.min(Math.max(b,0),Ue.length-1)]);return{pop(b){let d=R(b);f(d,0,.16,"triangle",.22),f(d*2,0,.08,"sine",.06),f(150,0,.09,"sine",.25,60)},off:()=>f(392,0,.1,"sine",.1,262),reach(){f(988,0,.08,"square",.05),f(1319,.09,.14,"square",.05)},bingo(b){[0,4,7,12,16,19].forEach((d,y)=>f(U(d),y*.06,.22,"square",.06)),[12,16,19].forEach(d=>f(U(d),.38,.6,"triangle",.12)),b>1&&[24,28,31].forEach(d=>f(U(d),.55,.6,"triangle",.08)),P(0,.25,.12,3e3)},perfect(){[0,4,7,12,16,19,24].forEach((b,d)=>f(U(b-12),d*.07,.25,"square",.06)),[0,4,7,12].forEach(b=>f(U(b),.55,1.2,"triangle",.12)),[12,16,19].forEach(b=>f(U(b),.55,1.2,"sawtooth",.03)),f(U(-12),.55,1.2,"sine",.2)},boom(){P(0,.5,.3,500),f(90,0,.3,"sine",.25,40)},tick:()=>f(1760,0,.03,"square",.03),note:(b,d=0)=>f(R(b),d,.12,"square",.05),close(){n&&n.close().catch(()=>{}),n=null,m=null}}}function _e(o){return o.controlled?null:o.storageKey!==void 0?o.storageKey||null:o.demo?null:gt(o.items??re)}function gt(o){let n=o.map(l=>`${l.emoji}\0${l.label}`).join(""),m=2166136261;for(let l=0;l<n.length;l++)m^=n.charCodeAt(l),m=Math.imul(m,16777619);return`packing-bingo:${(m>>>0).toString(36)}`}var We="https://fonts.googleapis.com/css2?family=Dela+Gothic+One&family=M+PLUS+Rounded+1c:wght@500;800&display=swap",Ve=`
6
- .pkb{--pk-sun:var(--pkb-sun,#FFD54F);--pk-ink:var(--pkb-ink,#2A1F14);--pk-paper:var(--pkb-paper,#FFFDF6);--pk-red:var(--pkb-red,#E8473B);--pk-mint:var(--pkb-mint,#BDEBD2);--pk-display:"Dela Gothic One",var(--pkb-font-fallback,sans-serif);--pk-body:"M PLUS Rounded 1c","Hiragino Maru Gothic ProN",var(--pkb-font-fallback,sans-serif);container-type:inline-size;isolation:isolate;width:100%}
1
+ "use strict";var PackingBingo=(()=>{var We=Object.defineProperty;var Vt=Object.getOwnPropertyDescriptor;var Xt=Object.getOwnPropertyNames;var Yt=Object.prototype.hasOwnProperty;var Jt=(n,a)=>{for(var s in a)We(n,s,{get:a[s],enumerable:!0})},Zt=(n,a,s,m)=>{if(a&&typeof a=="object"||typeof a=="function")for(let c of Xt(a))!Yt.call(n,c)&&c!==s&&We(n,c,{get:()=>a[c],enumerable:!(m=Vt(a,c))||m.enumerable});return n};var Qt=n=>Zt(We({},"__esModule",{value:!0}),n);var pn={};Jt(pn,{DEFAULT_ITEMS:()=>ce,LINES:()=>tn,bingoLines:()=>Ye,createPackingBingo:()=>sn,en:()=>wt,ja:()=>Je});var ce=[{emoji:"\u{1F45B}",label:"\u8CA1\u5E03"},{emoji:"\u{1F4F1}",label:"\u30B9\u30DE\u30DB"},{emoji:"\u{1F50B}",label:"\u30E2\u30D0\u30A4\u30EB\u200B\u5145\u96FB\u5668"},{emoji:"\u{1F4CB}",label:"\u5065\u5EB7\u8ABF\u67FB\u7968"},{emoji:"\u{1FAAA}",label:"\u30DE\u30A4\u30CA\u30AB\u30FC\u30C9\u200B\u307E\u305F\u306F\u4FDD\u967A\u8A3C"},{emoji:"\u{1F4D6}",label:"\u3057\u304A\u308A"},{emoji:"\u{1F637}",label:"\u30DE\u30B9\u30AF"},{emoji:"\u{1F927}",label:"\u30CF\u30F3\u30AB\u30C1"},{emoji:"\u{1F48A}",label:"\u5E38\u5099\u85AC"},{emoji:"\u{1F6CD}\uFE0F",label:"\u30D3\u30CB\u30FC\u30EB\u888B"},{emoji:"\u{1F9E4}",label:"\u8ECD\u624B\uFF08\u5B66\u6821\u652F\u7D66\uFF09"},{emoji:"\u{1F526}",label:"\u30D8\u30C3\u30C9\u30E9\u30A4\u30C8"},{emoji:"\u{1F455}",label:"\u30B8\u30E3\u30FC\u30B8"},{emoji:"\u2614",label:"\u96E8\u5177"},{emoji:"\u{1F6C1}",label:"\u30BF\u30AA\u30EB"},{emoji:"\u{1F9F4}",label:"\u65E5\u713C\u3051\u6B62\u3081"}];var ze=2,Ve=10,Te=n=>{throw new Error(`[packing-bingo] ${n}`)};function Xe(n){if(n.items)return n.items;let a=n.size;return a==null||!Number.isInteger(a)||a<ze?ce:ce.slice(0,a*a-(n.free?1:0))}function xt(n,a){(!Number.isInteger(n)||n<ze||n>Ve)&&Te(`"size" must be a whole number from ${ze} to ${Ve} (got ${n}).`),a&&n%2===0&&Te(`"free" needs an odd size such as 3 or 5, so that the card has a center (got ${n}).`)}function vt(n,a){let s=b=>Array.from({length:n},(l,k)=>b(k)),m=[...s(b=>s(l=>b*n+l)),...s(b=>s(l=>l*n+b)),s(b=>b*(n+1)),s(b=>(b+1)*(n-1))],c=a?(n*n-1)/2:-1,x=b=>a&&b>c?b-1:b;return{center:c,cellLines:m,lines:m.map(b=>b.filter(l=>l!==c).map(x))}}function yt(n){let a=Xe(n),s=!!n.free,m=n.size;if(m==null){let v=a.length,$=u=>{let M=Math.round(Math.sqrt(u));return M*M===u&&M>=ze&&M<=Ve?M:0};if(m=$(v+(s?1:0)),!m){let u=$(v+(s?0:1)),M=s?u?`; ${v} items fill a ${u}\xD7${u} card without "free"`:"":u%2?`, or set "free" for a ${u}\xD7${u} card with a FREE center`:"";Te(s?`With "free", "items" must have one less than an odd square number of entries (8, 24, 48, 80)${M} (got ${v}).`:`"items" must have a square number of entries (4, 9, 16, 25, \u2026, 100)${M} (got ${v}).`)}}xt(m,s);let c=m*m-(s?1:0);if(a.length!==c){let v=`a ${m}\xD7${m} card${s?" with a FREE center":""}`;Te(n.items?`"items" must have exactly ${c} entries for ${v} (got ${a.length}).`:`A ${v.slice(2)} needs ${c} items, but DEFAULT_ITEMS has only ${ce.length}. Pass "items".`)}let{center:x,cellLines:b,lines:l}=vt(m,s),k=a.map((v,$)=>s&&$>=x?$+1:$);return{size:m,free:s,items:a,itemCell:k,center:x,cellLines:b,lines:l}}function Ye(n,a=!1){return xt(n,a),vt(n,a).lines}var Je={title:"\u6301\u3061\u3082\u306E\u30D3\u30F3\u30B4",tag:"",subtitle:"",packed:"\u305D\u308D\u3063\u305F",bingo:"BINGO",score:"SCORE",combo:n=>`${n} COMBO`,comboPop:n=>`${n} COMBO!`,reset:"\u30EA\u30BB\u30C3\u30C8",shuffle:"\u{1F500} \u30B7\u30E3\u30C3\u30D5\u30EB",soundOn:"\u{1F50A} \u97F3\u3042\u308A",soundOff:"\u{1F507} \u97F3\u306A\u3057",stamp:"OK",free:"FREE",reachBadge:"\u30EA\u30FC\u30C1",reachPop:"\u30EA\u30FC\u30C1!",bannerSingle:"BINGO!",bannerDouble:"\u30C0\u30D6\u30EB\u30D3\u30F3\u30B4!",bannerTriple:"\u30C8\u30EA\u30D7\u30EB\u30D3\u30F3\u30B4!",bannerNth:n=>`${n} \u30E9\u30A4\u30F3\u76EE\uFF01`,bannerMulti:n=>`\u4E00\u6C17\u306B ${n} \u30E9\u30A4\u30F3\uFF01`,statusStart:()=>"",statusLines:(n,a)=>`\u30D3\u30F3\u30B4 ${n} \u30E9\u30A4\u30F3\uFF01 \u306E\u3053\u308A ${a} \u3053`,statusReach:()=>"",statusDone:"\u{1F389} \u30D1\u30FC\u30D5\u30A7\u30AF\u30C8\uFF01\u5FD8\u308C\u7269\u30BC\u30ED\u3067\u51FA\u767A\u3067\u304D\u307E\u3059",perfectTag:"\u{1F3C6} PERFECT",perfectStamp:`\u6E96\u5099
2
+ \u5B8C\u4E86`,perfectTitle:"\u30D1\u30FC\u30D5\u30A7\u30AF\u30C8\uFF01",perfectBody:n=>`${n}\u3053 \u305C\u3093\u3076\u305D\u308D\u3063\u305F\uFF01
3
+ \u5FD8\u308C\u7269\u30BC\u30ED\u3067\u3001\u3044\u3063\u3066\u3089\u3063\u3057\u3083\u3044\uFF01`,perfectBonus:n=>`PERFECT BONUS +${n}`,statScore:"SCORE",statCombo:"MAX COMBO",statLines:"BINGO",close:"\u3068\u3058\u308B",demoLabel:"\u30C7\u30E2\uFF1A",demoBingo:"\u25B6 \u30D3\u30F3\u30B4\u3092\u898B\u308B",demoPerfect:"\u25B6 \u30B3\u30F3\u30DC \u2192 \u30D1\u30FC\u30D5\u30A7\u30AF\u30C8",demoRestore:"\u6700\u521D\u306B\u623B\u3059"},wt={title:"Packing Bingo",tag:"",subtitle:"",packed:"PACKED",bingo:"BINGO",score:"SCORE",combo:n=>`${n} COMBO`,comboPop:n=>`${n} COMBO!`,reset:"Reset",shuffle:"\u{1F500} Shuffle",soundOn:"\u{1F50A} Sound on",soundOff:"\u{1F507} Muted",stamp:"OK",free:"FREE",reachBadge:"REACH",reachPop:"Reach!",bannerSingle:"BINGO!",bannerDouble:"DOUBLE BINGO!",bannerTriple:"TRIPLE BINGO!",bannerNth:n=>`Line ${n}!`,bannerMulti:n=>`${n} lines at once!`,statusStart:()=>"",statusLines:(n,a)=>`${n} bingo line${n===1?"":"s"}! ${a} to go`,statusReach:()=>"",statusDone:"\u{1F389} Perfect! Nothing left behind.",perfectTag:"\u{1F3C6} PERFECT",perfectStamp:`ALL
4
+ SET`,perfectTitle:"Perfect!",perfectBody:n=>`All ${n} packed!
5
+ Have a great trip!`,perfectBonus:n=>`PERFECT BONUS +${n}`,statScore:"SCORE",statCombo:"MAX COMBO",statLines:"BINGO",close:"Close",demoLabel:"Demo:",demoBingo:"\u25B6 Show a bingo",demoPerfect:"\u25B6 Combo \u2192 perfect",demoRestore:"Restore"};var Et=[0,2,4,7,9,12,14,16,19,21,24,26,28,31,33,36],D=n=>523.25*Math.pow(2,n/12);function Lt(n){let a=null,s=null;function m(){if(n()||typeof window>"u")return null;let l=navigator.userActivation;if(!a&&l&&!l.hasBeenActive)return null;if(!a){let k=window.AudioContext??window.webkitAudioContext;if(!k)return null;a=new k;let v=a.createDynamicsCompressor();s=a.createGain(),s.gain.value=.6,s.connect(v).connect(a.destination)}return a.state==="suspended"&&a.resume(),a}function c(l,k=0,v=.15,$="triangle",u=.2,M=0){let E=m();if(!E||!s)return;let T=E.currentTime+k,q=E.createOscillator(),P=E.createGain();q.type=$,q.frequency.setValueAtTime(l,T),M&&q.frequency.exponentialRampToValueAtTime(M,T+v),P.gain.setValueAtTime(1e-4,T),P.gain.exponentialRampToValueAtTime(u,T+.01),P.gain.exponentialRampToValueAtTime(1e-4,T+v),q.connect(P).connect(s),q.start(T),q.stop(T+v+.05)}function x(l=0,k=.3,v=.25,$=1200){let u=m();if(!u||!s)return;let M=u.currentTime+l,E=Math.ceil(u.sampleRate*k),T=u.createBuffer(1,E,u.sampleRate),q=T.getChannelData(0);for(let g=0;g<E;g++)q[g]=(Math.random()*2-1)*Math.pow(1-g/E,2.5);let P=u.createBufferSource(),ee=u.createBiquadFilter(),ve=u.createGain();P.buffer=T,ee.type="bandpass",ee.frequency.value=$,ee.Q.value=.7,ve.gain.value=v,P.connect(ee).connect(ve).connect(s),P.start(M)}let b=l=>D(Et[Math.min(Math.max(l,0),Et.length-1)]);return{pop(l){let k=b(l);c(k,0,.16,"triangle",.22),c(k*2,0,.08,"sine",.06),c(150,0,.09,"sine",.25,60)},off:()=>c(392,0,.1,"sine",.1,262),reach(){c(988,0,.08,"square",.05),c(1319,.09,.14,"square",.05)},bingo(l){[0,4,7,12,16,19].forEach((k,v)=>c(D(k),v*.06,.22,"square",.06)),[12,16,19].forEach(k=>c(D(k),.38,.6,"triangle",.12)),l>1&&[24,28,31].forEach(k=>c(D(k),.55,.6,"triangle",.08)),x(0,.25,.12,3e3)},perfect(){[0,4,7,12,16,19,24].forEach((l,k)=>c(D(l-12),k*.07,.25,"square",.06)),[0,4,7,12].forEach(l=>c(D(l),.55,1.2,"triangle",.12)),[12,16,19].forEach(l=>c(D(l),.55,1.2,"sawtooth",.03)),c(D(-12),.55,1.2,"sine",.2)},boom(){x(0,.5,.3,500),c(90,0,.3,"sine",.25,40)},tick:()=>c(1760,0,.03,"square",.03),note:(l,k=0)=>c(b(l),k,.12,"square",.05),shuffle(){for(let l=0;l<7;l++)x(l*.042,.05,.16,1600+l*260);c(D(7),.34,.12,"triangle",.14),c(D(12),.42,.2,"triangle",.14)},close(){a&&a.close().catch(()=>{}),a=null,s=null}}}function St(n){return n.controlled?null:n.storageKey!==void 0?n.storageKey||null:n.demo?null:en(Xe(n))}function en(n){let a=n.map(m=>`${m.emoji}\0${m.label}`).join(""),s=2166136261;for(let m=0;m<a.length;m++)s^=a.charCodeAt(m),s=Math.imul(s,16777619);return`packing-bingo:${(s>>>0).toString(36)}`}var Mt=`
6
+ .pkb{--pk-sun:var(--pkb-sun,#FFD54F);--pk-ink:var(--pkb-ink,#2A1F14);--pk-paper:var(--pkb-paper,#FFFDF6);--pk-red:var(--pkb-red,#E8473B);--pk-mint:var(--pkb-mint,#BDEBD2);--pk-display:"Dela Gothic One",var(--pkb-font-fallback,sans-serif);--pk-body:"M PLUS Rounded 1c","Hiragino Maru Gothic ProN",var(--pkb-font-fallback,sans-serif);--pk-n:4;--pk-s:1;--pk-d:1;container-type:inline-size;isolation:isolate;width:100%}
7
7
  .pkb,.pkb *{box-sizing:border-box;margin:0;padding:0}
8
8
  .pkb-board{position:relative;overflow:hidden;max-width:720px;margin:0 auto;padding:22px 26px 20px;border-radius:24px;background-color:var(--pk-sun);background-image:radial-gradient(rgba(42,31,20,.12) 1.3px,transparent 1.6px);background-size:16px 16px;border:2.5px solid var(--pk-ink);color:var(--pk-ink);font-family:var(--pk-body);line-height:1.4;text-align:left}
9
9
  .pkb-board.pkb-shake{animation:pkb-shake .45s cubic-bezier(.36,.07,.19,.97)}
10
10
  @keyframes pkb-shake{10%,90%{transform:translate(-1px,1px)}20%,80%{transform:translate(3px,-2px)}30%,50%,70%{transform:translate(-6px,2px)}40%,60%{transform:translate(6px,-1px)}}
11
11
  .pkb-board.pkb-punch{animation:pkb-punch .4s cubic-bezier(.3,1.6,.5,1)}
12
12
  @keyframes pkb-punch{30%{transform:scale(1.018)}}
13
- .pkb-head{display:flex;justify-content:space-between;align-items:center;gap:16px;margin-bottom:18px}
13
+ .pkb-head{display:flex;flex-wrap:wrap;justify-content:space-between;align-items:center;gap:12px 16px;margin-bottom:18px}
14
14
  .pkb-tags{display:flex;gap:8px;align-items:center}
15
15
  .pkb-kicker{display:inline-block;background:var(--pk-ink);color:var(--pk-sun);font-weight:800;font-size:11px;letter-spacing:.14em;padding:4px 10px;border-radius:999px}
16
+ .pkb-kicker:empty{display:none}
16
17
  .pkb-kicker.pkb-gold{color:#fff;background:linear-gradient(90deg,#E8473B,#FF9F1C,#1FA971,#2F6FED,#E8473B);background-size:200% 100%;animation:pkb-rb 2s linear infinite}
17
18
  @keyframes pkb-rb{to{background-position:-200% 0}}
18
19
  .pkb button{font-family:var(--pk-body)}
19
20
  .pkb-snd{appearance:none;border:2px solid var(--pk-ink);background:var(--pk-paper);border-radius:999px;padding:2px 9px;font-weight:800;font-size:11px;line-height:1.4;color:var(--pk-ink);cursor:pointer}
20
21
  .pkb-title{font-family:var(--pk-display);font-weight:400;font-size:34px;line-height:1.15;margin-top:8px;letter-spacing:.02em;color:inherit}
21
- .pkb-sub{font-weight:800;font-size:13px;margin-top:4px}
22
+ .pkb-sub{font-weight:800;font-size:13px;margin-top:4px;word-break:auto-phrase}
22
23
  .pkb-side{display:flex;flex-direction:column;gap:8px;flex:none}
23
24
  .pkb-score{display:flex;gap:10px}
24
25
  .pkb-pill{min-width:78px;background:var(--pk-paper);border:2.5px solid var(--pk-ink);border-radius:14px;padding:6px 10px 5px;text-align:center;box-shadow:3px 3px 0 var(--pk-ink)}
@@ -37,16 +38,18 @@ Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",stat
37
38
  .pkb-combo.pkb-on .pkb-bar i{animation:pkb-drain 2.5s linear forwards}
38
39
  @keyframes pkb-drain{from{transform:scaleX(1)}to{transform:scaleX(0)}}
39
40
  .pkb-gw{position:relative}
40
- .pkb-grid{display:grid;grid-template-columns:repeat(4,1fr);gap:12px}
41
- .pkb-tile{position:relative;aspect-ratio:1/.82;background:var(--pk-paper);border:2.5px solid var(--pk-ink);border-radius:16px;box-shadow:4px 4px 0 var(--pk-ink);display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;cursor:pointer;user-select:none;-webkit-tap-highlight-color:transparent;transition:transform .1s,box-shadow .1s,background-color .25s}
42
- .pkb-tile:active{transform:translate(3px,3px);box-shadow:1px 1px 0 var(--pk-ink)}
41
+ .pkb-grid{display:grid;grid-template-columns:repeat(var(--pk-n),minmax(0,1fr));gap:calc(12px*var(--pk-d))}
42
+ .pkb-tile{position:relative;min-width:0;place-self:stretch;aspect-ratio:1/.82;background:var(--pk-paper);border:2.5px solid var(--pk-ink);border-radius:calc(16px*var(--pk-d));box-shadow:4px 4px 0 var(--pk-ink);display:flex;flex-direction:column;align-items:center;justify-content:center;gap:calc(6px*var(--pk-d));cursor:pointer;user-select:none;-webkit-tap-highlight-color:transparent;transition:transform .1s,box-shadow .1s,background-color .25s}
43
+ .pkb-tile:active:not(.pkb-free){transform:translate(3px,3px);box-shadow:1px 1px 0 var(--pk-ink)}
43
44
  .pkb-tile input{position:absolute;opacity:0;pointer-events:none;width:1px;height:1px}
44
45
  .pkb-tile:has(input:focus-visible){outline:3px solid var(--pk-ink);outline-offset:3px}
45
- .pkb-emo{font-size:32px;line-height:1;transition:opacity .2s}
46
- .pkb-lbl{font-weight:800;font-size:13px;line-height:1.25;text-align:center;padding:0 6px;transition:opacity .2s;word-break:keep-all;overflow-wrap:anywhere}
47
- .pkb-stamp{position:absolute;left:50%;top:50%;width:64%;aspect-ratio:1;border-radius:50%;border:3px solid var(--pk-red);box-shadow:inset 0 0 0 2px var(--pk-paper),inset 0 0 0 4px var(--pk-red);color:var(--pk-red);display:grid;place-items:center;font-family:var(--pk-display);font-size:20px;letter-spacing:.04em;opacity:0;transform:translate(-50%,-50%) rotate(-16deg) scale(1.7);transition:transform .25s cubic-bezier(.3,1.5,.5,1),opacity .15s;pointer-events:none}
46
+ .pkb-emo{font-size:max(14px,calc(32px*var(--pk-s)));line-height:1;transition:opacity .2s}
47
+ .pkb-lbl{font-weight:800;font-size:max(9px,calc(13px*var(--pk-s)));line-height:1.25;text-align:center;padding:0 calc(6px*var(--pk-d));transition:opacity .2s;word-break:keep-all;overflow-wrap:anywhere}
48
+ .pkb-stamp{position:absolute;left:50%;top:50%;width:64%;aspect-ratio:1;border-radius:50%;border:3px solid var(--pk-red);box-shadow:inset 0 0 0 2px var(--pk-paper),inset 0 0 0 4px var(--pk-red);color:var(--pk-red);display:grid;place-items:center;font-family:var(--pk-display);font-size:max(9px,calc(20px*var(--pk-s)));letter-spacing:.04em;opacity:0;transform:translate(-50%,-50%) rotate(-16deg) scale(1.7);transition:transform .25s cubic-bezier(.3,1.5,.5,1),opacity .15s;pointer-events:none}
48
49
  .pkb-tile.pkb-on .pkb-stamp{opacity:.9;transform:translate(-50%,-50%) rotate(-16deg) scale(1)}
49
50
  .pkb-tile.pkb-on .pkb-emo,.pkb-tile.pkb-on .pkb-lbl{opacity:.35}
51
+ .pkb-tile.pkb-free{cursor:default;container-type:inline-size}
52
+ .pkb-tile.pkb-free .pkb-stamp{width:72%;opacity:1;transition:none;font-size:17cqi;letter-spacing:.02em;line-height:1;text-align:center;background:var(--pk-red);color:var(--pk-paper);border-color:var(--pk-red);box-shadow:inset 0 0 0 2px var(--pk-red),inset 0 0 0 4px var(--pk-paper)}
50
53
  .pkb-tile.pkb-line{background-color:var(--pk-mint)}
51
54
  .pkb-tile.pkb-line::before{content:"";position:absolute;inset:0;border-radius:inherit;pointer-events:none;background:linear-gradient(110deg,transparent 30%,rgba(255,255,255,.9) 45%,transparent 60%) no-repeat;background-size:250% 100%;background-position:200% 0;animation:pkb-glint 3.2s ease-in-out var(--pkb-gd,0s) infinite}
52
55
  @keyframes pkb-glint{0%{background-position:200% 0}30%,100%{background-position:-100% 0}}
@@ -63,12 +66,17 @@ Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",stat
63
66
  .pkb-lines{position:absolute;inset:0;width:100%;height:100%;pointer-events:none;overflow:visible;z-index:2;transition:opacity .4s}
64
67
  .pkb-board.pkb-all .pkb-lines{opacity:0}
65
68
  .pkb-lines line{fill:none;stroke-linecap:round;stroke-dasharray:1;stroke-dashoffset:0}
66
- .pkb-lines .pkb-u{stroke:var(--pk-paper);stroke-width:13}
67
- .pkb-lines .pkb-o{stroke:var(--pk-ink);stroke-width:6}
69
+ .pkb-lines .pkb-u{stroke:var(--pk-paper);stroke-width:calc(13px*var(--pk-d))}
70
+ .pkb-lines .pkb-o{stroke:var(--pk-ink);stroke-width:calc(6px*var(--pk-d))}
68
71
  .pkb-lines .pkb-draw line{animation:pkb-draw .45s ease-out .3s both}
69
72
  @keyframes pkb-draw{from{stroke-dashoffset:1}}
70
- .pkb-foot{display:flex;justify-content:space-between;align-items:center;gap:10px;margin-top:18px;font-weight:800;font-size:13px}
71
- .pkb-reset{appearance:none;flex:none;border:2px solid var(--pk-ink);background:transparent;border-radius:999px;padding:5px 12px;font-weight:800;font-size:12px;line-height:1.4;color:var(--pk-ink);cursor:pointer}
73
+ .pkb-foot{display:flex;flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 10px;margin-top:18px;font-weight:800;font-size:13px;word-break:auto-phrase}
74
+ .pkb-foot>span{flex:1 1 14em}
75
+ .pkb-foot>span:empty{flex-basis:0}
76
+ .pkb-acts{display:flex;gap:8px;flex:none;margin-left:auto}
77
+ .pkb-reset,.pkb-shuf{appearance:none;flex:none;border:2px solid var(--pk-ink);background:transparent;border-radius:999px;padding:5px 12px;font-weight:800;font-size:12px;line-height:1.4;color:var(--pk-ink);cursor:pointer}
78
+ .pkb-shuf{background:var(--pk-paper);box-shadow:2px 2px 0 var(--pk-ink)}
79
+ .pkb-shuf:active{transform:translate(2px,2px);box-shadow:none}
72
80
  .pkb-flash{position:absolute;inset:0;z-index:7;background:#fff;opacity:0;pointer-events:none}
73
81
  .pkb-flash.pkb-go{animation:pkb-flash .4s ease-out}
74
82
  @keyframes pkb-flash{0%{opacity:.8}100%{opacity:0}}
@@ -82,7 +90,7 @@ Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",stat
82
90
  .pkb-float{position:absolute;z-index:11;pointer-events:none;white-space:nowrap;font-family:var(--pk-display);font-weight:400;line-height:1;-webkit-text-stroke:4px var(--pk-ink);paint-order:stroke fill;transform:translate(-50%,-50%);animation:pkb-rise .95s cubic-bezier(.2,.9,.3,1) both}
83
91
  .pkb-float.pkb-pt{font-size:22px;color:var(--pk-paper)}
84
92
  .pkb-float.pkb-cmb{font-size:17px}
85
- .pkb-float.pkb-big{font-size:clamp(20px,6cqi,34px);color:#FFE066}
93
+ .pkb-float.pkb-big{font-size:clamp(14px,5.6cqi,34px);color:#FFE066}
86
94
  .pkb-float.pkb-rch{font-size:20px;color:var(--pk-red);-webkit-text-stroke:4px var(--pk-paper)}
87
95
  @keyframes pkb-rise{0%{opacity:0;transform:translate(-50%,-20%) scale(.4)}18%{opacity:1;transform:translate(-50%,-60%) scale(1.2)}30%{transform:translate(-50%,-70%) scale(1)}75%{opacity:1}100%{opacity:0;transform:translate(-50%,-190%) scale(1)}}
88
96
  .pkb-perfect{position:absolute;inset:0;z-index:8;display:grid;place-items:center;padding:20px;background:rgba(42,31,20,.5);opacity:0;visibility:hidden;transition:opacity .3s,visibility .3s}
@@ -93,7 +101,7 @@ Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",stat
93
101
  .pkb-perfect.pkb-show .pkb-medal{animation:pkb-slam .38s cubic-bezier(.5,0,.75,0) .35s forwards}
94
102
  @keyframes pkb-slam{to{opacity:1;transform:rotate(-14deg) scale(1)}}
95
103
  .pkb-ptitle{font-family:var(--pk-display);font-weight:400;font-size:30px;line-height:1.3;color:inherit}
96
- .pkb-pbody{font-weight:800;font-size:13.5px;line-height:1.6;margin:6px 0 14px;white-space:pre-line}
104
+ .pkb-pbody{font-weight:800;font-size:13.5px;line-height:1.6;margin:6px 0 14px;white-space:pre-line;word-break:auto-phrase}
97
105
  .pkb-stats{display:grid;grid-template-columns:repeat(3,1fr);gap:8px;margin-bottom:16px}
98
106
  .pkb-stats>div{border:2px solid var(--pk-ink);border-radius:12px;padding:6px 4px 5px;background:#fff}
99
107
  .pkb-stats small{display:block;font-size:9.5px;font-weight:800;letter-spacing:.1em}
@@ -103,24 +111,26 @@ Have a great trip!`,perfectBonus:o=>`PERFECT BONUS +${o}`,statScore:"SCORE",stat
103
111
  .pkb-fx{position:absolute;inset:0;width:100%;height:100%;z-index:10;pointer-events:none}
104
112
  .pkb-demo{max-width:720px;margin:12px auto 4px;display:flex;flex-wrap:wrap;align-items:center;gap:8px;font-family:var(--pk-body);font-size:12px;color:#666}
105
113
  .pkb-demo button{appearance:none;border:1px solid #ccc;background:#f3f3f3;color:#222;border-radius:999px;padding:5px 12px;font-size:12px;cursor:pointer}
106
- @container (max-width:560px){.pkb-board{padding:18px 14px 16px}.pkb-head{flex-direction:column;align-items:stretch;gap:12px}.pkb-score{display:grid;grid-template-columns:repeat(3,1fr);gap:8px}.pkb-pill,.pkb-pill.pkb-sc{min-width:0;padding:5px 4px 4px}.pkb-pill b{font-size:19px}.pkb-title{font-size:26px}.pkb-grid{gap:8px}.pkb-tile{border-radius:12px;box-shadow:3px 3px 0 var(--pk-ink);gap:3px;aspect-ratio:1/1}.pkb-emo{font-size:24px}.pkb-lbl{font-size:10.5px;padding:0 2px}.pkb-stamp{font-size:14px}.pkb-tile.pkb-reach::after{font-size:9px;padding:2px 5px;top:-9px;right:-5px}.pkb-lines .pkb-u{stroke-width:10}.pkb-lines .pkb-o{stroke-width:5}.pkb-banner::before{width:380px;height:380px;margin:-190px 0 0 -190px}.pkb-banner span{font-size:12px}.pkb-medal{width:96px;height:96px;font-size:20px}.pkb-card{padding:20px 14px 16px}.pkb-ptitle{font-size:24px}.pkb-stats b{font-size:17px}.pkb-float.pkb-pt{font-size:17px}.pkb-float.pkb-cmb{font-size:13px}}
114
+ @container (max-width:560px){.pkb-board{padding:18px 14px 16px}.pkb-head{flex-direction:column;align-items:stretch;gap:12px}.pkb-score{display:grid;grid-template-columns:repeat(3,1fr);gap:8px}.pkb-pill,.pkb-pill.pkb-sc{min-width:0;padding:5px 4px 4px}.pkb-pill b{font-size:19px}.pkb-title{font-size:26px}.pkb-grid{gap:max(3px,calc(8px*var(--pk-d)))}.pkb-tile{border-radius:calc(12px*var(--pk-d));box-shadow:3px 3px 0 var(--pk-ink);gap:calc(3px*var(--pk-d));aspect-ratio:1/1}.pkb-emo{font-size:max(13px,calc(24px*var(--pk-s)))}.pkb-lbl{font-size:max(8.5px,calc(10.5px*var(--pk-s)));padding:0 calc(2px*var(--pk-d))}.pkb-stamp{font-size:max(9px,calc(14px*var(--pk-s)))}.pkb-tile.pkb-reach::after{font-size:9px;padding:2px 5px;top:-9px;right:-5px}.pkb-lines .pkb-u{stroke-width:calc(10px*var(--pk-d))}.pkb-lines .pkb-o{stroke-width:calc(5px*var(--pk-d))}.pkb-banner::before{width:380px;height:380px;margin:-190px 0 0 -190px}.pkb-banner span{font-size:12px}.pkb-medal{width:96px;height:96px;font-size:20px}.pkb-card{padding:20px 14px 16px}.pkb-ptitle{font-size:24px}.pkb-stats b{font-size:17px}.pkb-float.pkb-pt{font-size:17px}.pkb-float.pkb-cmb{font-size:13px}}
115
+ @container (max-width:400px){.pkb-board{padding:16px 10px 14px}.pkb-grid{gap:max(3px,calc(6px*var(--pk-d)))}.pkb-lbl{font-size:max(8.5px,calc(10px*var(--pk-s)));padding:0 calc(1px*var(--pk-d))}.pkb-emo{font-size:max(12px,calc(22px*var(--pk-s)))}.pkb-stamp{font-size:max(9px,calc(13px*var(--pk-s)))}.pkb-foot{margin-top:14px;font-size:12px}.pkb-perfect{padding:12px}.pkb-stats{gap:6px}.pkb-stats>div{padding:6px 2px 5px}.pkb-stats small{letter-spacing:.02em}}
116
+ @container (max-width:320px){.pkb-board{padding-inline:8px}.pkb-grid{gap:max(3px,calc(5px*var(--pk-d)))}.pkb-lbl{font-size:max(8.5px,calc(9.5px*var(--pk-s)));padding:0}}
107
117
  @media (prefers-reduced-motion:reduce){.pkb-board.pkb-shake,.pkb-board.pkb-punch,.pkb-flash.pkb-go,.pkb-tile.pkb-hop,.pkb-tile.pkb-squash,.pkb-tile.pkb-reach,.pkb-tile.pkb-line::before,.pkb-pill.pkb-hot,.pkb-bump,.pkb-tile.pkb-reach::after,.pkb-banner::before,.pkb-lines .pkb-draw line,.pkb-kicker.pkb-gold{animation:none}.pkb-banner.pkb-show{animation:pkb-fade 1.8s forwards}.pkb-float{animation:pkb-fade 1s both}.pkb-perfect.pkb-show .pkb-medal{animation:none;opacity:1;transform:rotate(-14deg)}.pkb-card{transition:none}}
108
118
  @keyframes pkb-fade{0%,100%{opacity:0}15%,80%{opacity:1}}
109
- `;var F=[[0,1,2,3],[4,5,6,7],[8,9,10,11],[12,13,14,15],[0,4,8,12],[1,5,9,13],[2,6,10,14],[3,7,11,15],[0,5,10,15],[3,6,9,12]],ht=[0,1,2,3,5,10],Ye=["#E8473B","#2F6FED","#1FA971","#FFFDF6","#2A1F14","#FF9F1C"],Xe=["#FF9F1C","#1FA971","#2F6FED","#9B5DE5","#E8473B"],xt=2500,Je="packing-bingo-muted",g=o=>o.replace(/[&<>"']/g,n=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#39;"})[n]),K=o=>Array.from({length:16},(n,m)=>!!o?.[m]),Qe=()=>Array.from({length:16},(o,n)=>ht.includes(n));function Ze(o){try{return localStorage.getItem(o)}catch{return null}}function et(o,n){try{localStorage.setItem(o,n)}catch{}}function vt(o){if(!document.getElementById("pkb-styles")){let n=document.createElement("style");n.id="pkb-styles",n.textContent=Ve,document.head.appendChild(n)}if(o&&!document.getElementById("pkb-fonts")){let n=document.createElement("link");n.id="pkb-fonts",n.rel="stylesheet",n.href=We,document.head.appendChild(n)}}function yt(o,n,m){let l=o.map((P,R)=>`<label class="pkb-tile" data-reach="${g(n.reachBadge)}" style="--pkb-gd:${((R>>2)+(R&3))*.12}s"><input type="checkbox"><span class="pkb-emo" aria-hidden="true">${g(P.emoji)}</span><span class="pkb-lbl">${g(P.label).replace(/・/g,"\u30FB<wbr>")}</span><span class="pkb-stamp" aria-hidden="true">${g(n.stamp)}</span></label>`).join(""),f=m?`<div class="pkb-demo"><span>${g(n.demoLabel)}</span><button type="button" data-r="dB">${g(n.demoBingo)}</button><button type="button" data-r="dP">${g(n.demoPerfect)}</button><button type="button" data-r="dR">${g(n.demoRestore)}</button></div>`:"";return`<div class="pkb"><div class="pkb-board">
119
+ `;var tn=Ye(4),Bt=["#E8473B","#2F6FED","#1FA971","#FFFDF6","#2A1F14","#FF9F1C"],$t=["#FF9F1C","#1FA971","#2F6FED","#9B5DE5","#E8473B"],nn=2500,Ct="packing-bingo-muted",an="packing-bingo-order:",h=n=>n.replace(/[&<>"']/g,a=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#39;"})[a]);function Ze(n){try{return localStorage.getItem(n)}catch{return null}}function Qe(n,a){try{localStorage.setItem(n,a)}catch{}}var Tt=(n,a)=>`${+((Math.floor(n/a)+n%a)*.36/Math.max(1,a-1)).toFixed(3)}s`,Oe=n=>n.slice().sort((a,s)=>a-s).join(","),zt=560;function rn(){if(document.getElementById("pkb-styles"))return;let n=document.createElement("style");n.id="pkb-styles",n.textContent=Mt,document.head.appendChild(n)}function on(n,a,{demo:s,shuffle:m,vibrate:c}){let x=n.size,b=c?'<input type="checkbox" switch role="checkbox">':'<input type="checkbox">',l=Array.from({length:x*x},($,u)=>{let M=`--pkb-gd:${Tt(u,x)}`;if(u===n.center)return`<div class="pkb-tile pkb-free pkb-on" style="${M}"><span class="pkb-stamp">${h(a.free)}</span></div>`;let E=n.items[n.itemCell.indexOf(u)];return`<label class="pkb-tile" data-reach="${h(a.reachBadge)}" style="${M}">${b}<span class="pkb-emo" aria-hidden="true">${h(E.emoji)}</span><span class="pkb-lbl">${h(E.label).replace(/・/g,"\u30FB<wbr>")}</span><span class="pkb-stamp" aria-hidden="true">${h(a.stamp)}</span></label>`}).join(""),k=`--pk-n:${x};--pk-s:${+Math.min(1.35,4/x).toFixed(3)};--pk-d:${+Math.min(1,4/x).toFixed(3)}`,v=s?`<div class="pkb-demo"><span>${h(a.demoLabel)}</span><button type="button" data-r="dB">${h(a.demoBingo)}</button><button type="button" data-r="dP">${h(a.demoPerfect)}</button><button type="button" data-r="dR">${h(a.demoRestore)}</button></div>`:"";return`<div class="pkb" style="${k}"><div class="pkb-board">
110
120
  <div class="pkb-head"><div>
111
- <div class="pkb-tags"><span class="pkb-kicker" data-r="kick">${g(n.tag)}</span><button type="button" class="pkb-snd" data-r="snd"></button></div>
112
- <h2 class="pkb-title">${g(n.title)}</h2><p class="pkb-sub">${g(n.subtitle)}</p></div>
121
+ <div class="pkb-tags"><span class="pkb-kicker" data-r="kick">${h(a.tag)}</span><button type="button" class="pkb-snd" data-r="snd"></button></div>
122
+ <h2 class="pkb-title">${h(a.title)}</h2>${a.subtitle?`<p class="pkb-sub">${h(a.subtitle)}</p>`:""}</div>
113
123
  <div class="pkb-side"><div class="pkb-score">
114
- <div class="pkb-pill"><small>${g(n.packed)}</small><b data-r="cnt"></b></div>
115
- <div class="pkb-pill" data-r="bp"><small>${g(n.bingo)}</small><b data-r="bng"></b></div>
116
- <div class="pkb-pill pkb-sc" data-r="sp"><small>${g(n.score)}</small><b data-r="sc">0</b></div></div>
124
+ <div class="pkb-pill"><small>${h(a.packed)}</small><b data-r="cnt"></b></div>
125
+ <div class="pkb-pill" data-r="bp"><small>${h(a.bingo)}</small><b data-r="bng"></b></div>
126
+ <div class="pkb-pill pkb-sc" data-r="sp"><small>${h(a.score)}</small><b data-r="sc">0</b></div></div>
117
127
  <div class="pkb-combo" data-r="combo"><b data-r="cmbN"></b><span class="pkb-bar"><i data-r="cbar"></i></span></div></div></div>
118
128
  <div class="pkb-gw"><div class="pkb-grid">${l}</div><svg class="pkb-lines" aria-hidden="true"></svg>
119
129
  <div class="pkb-banner" data-r="banner" aria-hidden="true"><b data-r="bT"></b><span data-r="bS"></span></div></div>
120
- <div class="pkb-foot"><span data-r="msg" aria-live="polite"></span><button type="button" class="pkb-reset" data-r="reset">${g(n.reset)}</button></div>
130
+ <div class="pkb-foot"><span data-r="msg" aria-live="polite"></span><div class="pkb-acts">${m?`<button type="button" class="pkb-shuf" data-r="shuf">${h(a.shuffle)}</button>`:""}<button type="button" class="pkb-reset" data-r="reset">${h(a.reset)}</button></div></div>
121
131
  <div class="pkb-flash" data-r="flash"></div>
122
- <div class="pkb-perfect" data-r="perfect"><div class="pkb-card" role="dialog" aria-label="${g(n.perfectTitle)}">
123
- <div class="pkb-medal">${g(n.perfectStamp)}</div><h3 class="pkb-ptitle">${g(n.perfectTitle)}</h3><p class="pkb-pbody">${g(n.perfectBody)}</p>
124
- <div class="pkb-stats"><div><small>${g(n.statScore)}</small><b data-r="sScore">0</b></div><div><small>${g(n.statCombo)}</small><b data-r="sCombo">\xD70</b></div><div><small>${g(n.statLines)}</small><b data-r="sBingo">0</b></div></div>
125
- <button type="button" class="pkb-close" data-r="close">${g(n.close)}</button></div></div>
126
- <canvas class="pkb-fx"></canvas></div>${f}</div>`}function wt(o,n={}){let m=n.items??re;if(m.length!==16)throw new Error(`[packing-bingo] "items" must have exactly 16 entries (got ${m.length}).`);let l={...Be,...n.messages};n.title!=null&&(l.title=n.title),n.tag!=null&&(l.tag=n.tag),n.subtitle!=null&&(l.subtitle=n.subtitle);let f=!!n.controlled,P=_e(n),R=!!n.demo,b=typeof matchMedia=="function"&&matchMedia("(prefers-reduced-motion: reduce)").matches,d=!1,y=new Set,E=(e,t)=>{let a=window.setTimeout(()=>{y.delete(a),d||e()},t);y.add(a)},M=e=>new Promise(t=>window.setTimeout(t,e)),A=0;vt(n.fonts!==!1),o.innerHTML=yt(m,l,R);let p=e=>{let t=o.querySelector(`[data-r="${e}"]`);if(!t)throw new Error(`[packing-bingo] internal: missing element "${e}"`);return t},x=o.querySelector(".pkb-board"),B=o.querySelector(".pkb-gw"),C=o.querySelector(".pkb-grid"),_=o.querySelector(".pkb-lines"),j=o.querySelector(".pkb-fx"),k=j.getContext("2d"),S=Array.from(C.children),ie=S.map(e=>e.querySelector("input")),Le=p("kick"),de=p("snd"),N=p("perfect"),h=K(void 0),w=[],se=new Set,me=new Set,pe=!1,Me=0,z=0,ne=0,L=0,X=0,Ce=0,fe=!1,ae=new Set,J=new Set,ze=Ze(Je),W=ze!=null?ze==="1":n.sound===!1,T=Ke(()=>W),Te=()=>{de.textContent=W?l.soundOff:l.soundOn,de.setAttribute("aria-pressed",String(!W))};de.addEventListener("click",()=>{W=!W,et(Je,W?"1":"0"),Te(),W||T.pop(4)}),Te();let D=[],V=0,oe=1,H=0,G=0,$e=()=>{let e=x.getBoundingClientRect();oe=Math.min(2,window.devicePixelRatio||1),H=e.width,G=e.height,j.width=Math.round(H*oe),j.height=Math.round(G*oe)},ke=(e,t,a,r,s,i,c,v)=>({x:e,y:t,vx:a,vy:r,g:s,life:c,shape:v,w:(5+Math.random()*6)*i,h:(3+Math.random()*5)*i,r:Math.random()*6,vr:(Math.random()-.5)*.35,c:Ye[Math.random()*Ye.length|0]}),ue=()=>{!V&&k&&(V=requestAnimationFrame(Pe))};function Q(e,t,a,r={}){if(!b){for(let s=0;s<a;s++){let i=(r.angle??-Math.PI/2)+(Math.random()-.5)*(r.spread??Math.PI*2),c=(r.speed??10)*(.35+Math.random()*.85),v=Math.random()<(r.star??.15)?"star":Math.random()<.3?"round":"rect";D.push(ke(e,t,Math.cos(i)*c,Math.sin(i)*c,r.g??.28,r.size??1,(r.life??110)+Math.random()*40,v))}ue()}}function tt(e){if(b)return;let t=performance.now()+e,a=()=>{for(let r=0;r<4;r++)D.push(ke(Math.random()*H,-12,(Math.random()-.5)*2,2+Math.random()*3,.045,1,420,Math.random()<.2?"star":"rect"));ue(),performance.now()<t&&E(a,45)};a()}function nt(e){if(b)return;let t=performance.now()+e,a=()=>{let r=ke(Math.random()*H,-30,(Math.random()-.5)*1.5,1.5+Math.random()*2,.05,1,500,"emoji");r.e=m[Math.random()*m.length|0].emoji,r.w=22+Math.random()*12,r.vr=(Math.random()-.5)*.06,D.push(r),ue(),performance.now()<t&&E(a,110)};a()}function at(e,t){Q(e,t,80,{speed:7.5,g:.06,life:85,star:.4}),T.boom()}function ot(e,t){e.beginPath();for(let a=0;a<10;a++){let r=a*Math.PI/5-Math.PI/2,s=a%2?t*.45:t;e.lineTo(Math.cos(r)*s,Math.sin(r)*s)}e.closePath(),e.fill()}function Pe(){if(V=0,!(d||!k)){k.setTransform(oe,0,0,oe,0,0),k.clearRect(0,0,H,G),D=D.filter(e=>e.life>0&&e.y<G+40);for(let e of D)e.vx*=.985,e.vy=e.vy*.985+e.g,e.x+=e.vx,e.y+=e.vy,e.r+=e.vr,e.life--,k.save(),k.globalAlpha=Math.min(1,e.life/25),k.translate(e.x,e.y),k.rotate(e.r),k.fillStyle=e.c,e.shape==="round"?(k.beginPath(),k.arc(0,0,e.h/1.6,0,7),k.fill()):e.shape==="star"?ot(k,e.w*.8):e.shape==="emoji"?(k.font=`${e.w}px "Apple Color Emoji","Segoe UI Emoji","Noto Color Emoji",sans-serif`,k.textAlign="center",k.textBaseline="middle",k.fillText(e.e??"",0,0)):(k.scale(1,Math.cos(e.r*2.3)),k.fillRect(-e.w/2,-e.h/2,e.w,e.h)),k.restore();D.length&&(V=requestAnimationFrame(Pe))}}let le=e=>{let t=x.getBoundingClientRect(),a=e.getBoundingClientRect();return{x:a.left-t.left+a.width/2,y:a.top-t.top+a.height/2}},$=(e,t)=>{e.classList.remove(t),e.offsetWidth,e.classList.add(t)},Ae=(e,t)=>{b||(S[e].classList.remove("pkb-squash"),S[e].style.setProperty("--pkb-d",t+"ms"),$(S[e],"pkb-hop"))};C.addEventListener("animationend",e=>{let t=e.target;t.classList.contains("pkb-tile")&&(e.animationName==="pkb-hop"||e.animationName==="pkb-squash")&&t.classList.remove(e.animationName)});let rt=e=>{let t=document.createElement("span");t.className="pkb-ring",e.appendChild(t),t.addEventListener("animationend",()=>t.remove())},ge=e=>{let t=navigator.userActivation;if(!(t&&!t.hasBeenActive))try{navigator.vibrate?.(e)}catch{}},ce=(e,t,a,r,s=0,i)=>{let c=document.createElement("div");c.className="pkb-float pkb-"+r,c.textContent=e,c.style.left=t+"px",c.style.top=a+"px",s&&(c.style.animationDelay=s+"ms"),i&&(c.style.color=i),x.appendChild(c),c.addEventListener("animationend",()=>c.remove())},Oe=(e,t,a)=>Math.max(0,Math.min(1,(e-t)/a)),Fe=e=>1-Math.pow(1-e,3),be=0;function he(){cancelAnimationFrame(be);let e=ne,t=z,a=performance.now(),r=s=>{if(d)return;let i=Oe(s,a,450);ne=Math.round(e+(t-e)*Fe(i)),p("sc").textContent=ne.toLocaleString(),i<1&&(be=requestAnimationFrame(r))};r(a),b||$(p("sp"),"pkb-bump")}let Re=(e,t,a,r="pt")=>{ce(`+${e}`,t,a,r),he()};function xe(e,t,a,r,s,i=!1){let c=performance.now(),v=A,q=0,I=Y=>{if(d||v!==A)return;let te=Oe(Y,c,r);e.textContent=s(Math.round(t+(a-t)*Fe(te))),i&&te<1&&Y-q>55&&(T.tick(),q=Y),te<1?requestAnimationFrame(I):b||$(e,"pkb-bump")};I(c)}let qe=e=>{let t=S[e];return{x:t.offsetLeft+t.offsetWidth/2,y:t.offsetTop+t.offsetHeight/2}};function Ie(e=[]){_.setAttribute("viewBox",`0 0 ${B.clientWidth} ${B.clientHeight}`),_.innerHTML=w.map(t=>{let a=qe(F[t][0]),r=qe(F[t][3]),s=r.x-a.x,i=r.y-a.y,c=Math.hypot(s,i)||1,v=s/c*26,q=i/c*26,I=`x1="${a.x-v}" y1="${a.y-q}" x2="${r.x+v}" y2="${r.y+q}" pathLength="1"`;return`<g${e.includes(t)?' class="pkb-draw"':""}><line class="pkb-u" ${I}/><line class="pkb-o" ${I}/></g>`}).join("")}function it(e,t){let a=le(S[e]);if(!t){L=0,p("combo").classList.remove("pkb-on"),T.off();return}let r=performance.now();L=r-Ce<xt?L+1:1,Ce=r,X=Math.max(X,L),T.pop(L-1),b||($(S[e],"pkb-squash"),rt(S[e])),Q(a.x,a.y,18,{speed:6,g:.2,life:30,size:.6,star:.5}),ae.has(e)||(ae.add(e),z+=10*L,Re(10*L,a.x,a.y-12)),L>=2&&(ce(l.comboPop(L),a.x,a.y+22,"cmb",90,Xe[(L-2)%Xe.length]),p("cmbN").textContent=l.combo(L),$(p("combo"),"pkb-on")),ge(12)}p("cbar").addEventListener("animationend",()=>{p("combo").classList.remove("pkb-on"),L=0});function st(e){e.forEach(t=>{let a=le(S[t]);ce(l.reachPop,a.x,a.y-34,"rch",150)}),E(()=>T.reach(),150)}function pt(e,t){let a=e.length,r=[...new Set(e.flatMap(i=>F[i]))],s=Math.min(70,300/r.length);r.forEach((i,c)=>E(()=>{Ae(i,0);let v=le(S[i]);Q(v.x,v.y,14,{speed:5,g:.15,life:30,size:.7,star:.8}),T.note(c+3)},c*s)),E(()=>{p("bT").textContent=a>=3?l.bannerTriple:a===2?l.bannerDouble:l.bannerSingle,p("bS").textContent=a>1?l.bannerMulti(a):l.bannerNth(w.length),$(p("banner"),"pkb-show"),b||($(p("flash"),"pkb-go"),$(x,"pkb-punch"));let i=le(B);Q(i.x,i.y,a>1?180:110,{speed:a>1?16:13,star:.3}),T.bingo(a),ge(a>1?[40,60,40,60,90]:[40,60,40]),t&&E(()=>Re(t,i.x,i.y+105,"big"),350)},r.length*s+60)}function lt(e){let t=fe?0:1e3;fe=!0,z+=t,S.forEach((r,s)=>Ae(s,((s>>2)+(s&3))*60)),T.perfect(),b||$(p("flash"),"pkb-go"),p("sScore").textContent="0",p("sCombo").textContent="\xD70",p("sBingo").textContent="0",E(()=>{$(N,"pkb-show"),p("close").focus({preventScroll:!0}),E(()=>{b||$(x,"pkb-shake"),T.boom(),Q(0,G,90,{angle:-Math.PI/3,spread:.8,speed:22,g:.32,star:.3}),Q(H,G,90,{angle:-Math.PI*2/3,spread:.8,speed:22,g:.32,star:.3}),tt(3500),ge([60,80,60,80,200]),t&&ce(l.perfectBonus(t),H/2,G*.16,"big"),xe(p("sScore"),0,z,1300,r=>r.toLocaleString(),!0),xe(p("sCombo"),0,X,700,r=>"\xD7"+r),xe(p("sBingo"),0,w.length,700,String),he()},720),[1300,1650,2e3,2350,2700].forEach(r=>E(()=>at(H*(.15+Math.random()*.7),G*(.12+Math.random()*.3)),r)),E(()=>nt(3e3),1500)},520);let a={score:z,maxCombo:X};e.push(()=>n.onPerfect?.(a))}function je(){A++,y.forEach(e=>clearTimeout(e)),y.clear(),cancelAnimationFrame(be),ne=z,p("sc").textContent=z.toLocaleString()}function ct(){D=[],cancelAnimationFrame(V),V=0,k?.clearRect(0,0,j.width,j.height),x.querySelectorAll(".pkb-float, .pkb-ring").forEach(e=>e.remove()),p("banner").classList.remove("pkb-show"),p("flash").classList.remove("pkb-go"),p("combo").classList.remove("pkb-on"),N.classList.remove("pkb-show")}function ve(e,t){let a=[],r=h,s=r.filter(Boolean).length;w=F.flatMap((u,O)=>u.every(Ee=>r[Ee])?[O]:[]);let i=w.filter(u=>!se.has(u));[...se].some(u=>!w.includes(u))&&(je(),s<16&&N.classList.remove("pkb-show"));let c=new Set(w.flatMap(u=>F[u])),v=new Set;for(let u of F){let O=u.filter(Ee=>!r[Ee]);O.length===1&&v.add(O[0])}S.forEach((u,O)=>{u.classList.toggle("pkb-on",r[O]),u.classList.toggle("pkb-line",c.has(O)),u.classList.toggle("pkb-reach",v.has(O))}),x.classList.toggle("pkb-all",s===16),Le.classList.toggle("pkb-gold",s===16),Le.textContent=s===16?l.perfectTag:l.tag,p("cnt").textContent=`${s}/16`,p("bng").textContent=String(w.length);let q=p("bp");w.length>Me&&(q.classList.remove("pkb-hot"),q.offsetWidth),q.classList.toggle("pkb-hot",w.length>0),Me=w.length,Ie(i),e!==null&&it(e,r[e]);let I=i.filter(u=>!J.has(u));I.forEach(u=>J.add(u));let Y=100*I.length*I.length;if(z+=Y,t)Y&&he();else if(s===16&&!pe)lt(a);else if(i.length){pt(i,Y);let u={newLines:i,totalLines:w.length,score:z};a.push(()=>n.onBingo?.(u))}else if(e!==null&&r[e]){let u=[...v].filter(O=>!me.has(O));u.length&&st(u)}se=new Set(w),me=v,pe=s===16;let te=[...v].map(u=>m[u].label);return p("msg").textContent=s===16?l.statusDone:te.length?l.statusReach(te):w.length?l.statusLines(w.length,16-s):l.statusStart(16-s),a}let Ne=e=>{for(let t of e){if(d)return;t()}},De=()=>{P&&et(P,JSON.stringify(h))};function He(e,t,a){h=e,ie.forEach((s,i)=>s.checked=h[i]);let r=ve(t,a);return De(),r}function ye(e){je(),ct(),h=e,ie.forEach((t,a)=>t.checked=h[a]),ae.clear(),J.clear(),h.forEach((t,a)=>t&&ae.add(a)),F.forEach((t,a)=>t.every(r=>h[r])&&J.add(a)),se=new Set(J),me=new Set,pe=h.every(Boolean),fe=pe,z=ne=ae.size*10+J.size*100,L=0,X=0,p("sc").textContent=z.toLocaleString(),ve(null,!0),De()}function Z(e,t,a={}){if(f){ie.forEach((s,i)=>s.checked=h[i]),n.onChange?.(e.slice());return}let r=[];a.reset?ye(e):r=He(e,t,!!a.quiet),n.onChange?.(h.slice()),Ne(r)}if(C.addEventListener("change",e=>{let t=ie.indexOf(e.target);if(t<0)return;let a=h.slice();a[t]=!a[t],Z(a,t)}),p("reset").addEventListener("click",()=>Z(K(void 0),null,{reset:!0})),p("close").addEventListener("click",()=>N.classList.remove("pkb-show")),N.addEventListener("click",e=>{e.target===N&&N.classList.remove("pkb-show")}),R){let e=!1,t=()=>{h.every(Boolean)?Z(K(void 0),null,{reset:!0}):N.classList.remove("pkb-show")},a=async r=>{if(!e){e=!0;try{t();let s=A;for(let i of r){if(await M(i.delay),d||s!==A)return;let c=h.slice();c[i.i]=!0,Z(c,i.i,{quiet:i.quiet})}}finally{e=!1}}};p("dB").addEventListener("click",()=>{let r=()=>F.map(i=>i.filter(c=>!h[c])).filter(i=>i.length).sort((i,c)=>i.length-c.length)[0]??[],s=h.every(Boolean)?[...F[0]]:r();a(s.map(i=>({i,delay:320})))}),p("dP").addEventListener("click",()=>{let r=h.every(Boolean)?S.map((s,i)=>i):S.map((s,i)=>i).filter(s=>!h[s]);a(r.map((s,i)=>i<r.length-1?{i:s,delay:170,quiet:!0}:{i:s,delay:450}))}),p("dR").addEventListener("click",()=>{e||Z(Qe(),null,{reset:!0})})}let ee=null;if(P)try{let e=JSON.parse(Ze(P)??"null");Array.isArray(e)&&(ee=K(e))}catch{}!ee&&n.defaultChecked&&(ee=K(n.defaultChecked)),!ee&&R&&(ee=Qe()),$e(),ye(ee??K(void 0));let we=typeof ResizeObserver=="function"?new ResizeObserver(()=>{$e(),Ie()}):null;return we?.observe(x),we?.observe(B),{setChecked(e,t={}){if(d)return;let a=K(e),r=a.flatMap((s,i)=>s!==h[i]?[i]:[]);if(r.length){if(!t.animate||r.length!==1){ye(a);return}Ne(He(a,r[0],!1))}},reset(){d||Z(K(void 0),null,{reset:!0})},refresh(){d||ve(null,!0)},getState(){return{checked:h.slice(),lines:w.slice(),score:z,maxCombo:X,complete:h.every(Boolean)}},destroy(){d||(d=!0,y.forEach(e=>clearTimeout(e)),y.clear(),cancelAnimationFrame(V),cancelAnimationFrame(be),we?.disconnect(),T.close(),o.innerHTML="")}}}return ut(Et);})();
132
+ <div class="pkb-perfect" data-r="perfect"><div class="pkb-card" role="dialog" aria-label="${h(a.perfectTitle)}">
133
+ <div class="pkb-medal">${h(a.perfectStamp)}</div><h3 class="pkb-ptitle">${h(a.perfectTitle)}</h3><p class="pkb-pbody" data-r="pbody">${h(Ot(a,n.items.length))}</p>
134
+ <div class="pkb-stats"><div><small>${h(a.statScore)}</small><b data-r="sScore">0</b></div><div><small>${h(a.statCombo)}</small><b data-r="sCombo">\xD70</b></div><div><small>${h(a.statLines)}</small><b data-r="sBingo">0</b></div></div>
135
+ <button type="button" class="pkb-close" data-r="close">${h(a.close)}</button></div></div>
136
+ <canvas class="pkb-fx"></canvas></div>${v}</div>`}var Ot=(n,a)=>typeof n.perfectBody=="function"?n.perfectBody(a):n.perfectBody;function sn(n,a={}){let s=yt(a),{items:m,cellLines:c}=s,x=s.size,b=m.length,l=e=>Array.from({length:b},(t,r)=>!!e?.[r]),k=()=>Array.from({length:b},(e,t)=>t),v=e=>e.every((t,r)=>t===r),$=e=>Array.isArray(e)&&e.length===b&&e.every(t=>Number.isInteger(t)&&t>=0&&t<b)&&new Set(e).size===b,u=k(),M=k(),E=s.lines,T=[...c[0],...c[2*x].slice(1,-1)],q=s.itemCell.flatMap((e,t)=>T.includes(e)?[t]:[]),P=()=>{let e=l(void 0);return q.forEach(t=>e[u[t]]=!0),e},ee=e=>Math.floor(e/x)+e%x,ve=Math.min(1,4/x),g={...Je,...a.messages};a.title!=null&&(g.title=a.title),a.tag!=null&&(g.tag=a.tag),a.subtitle!=null&&(g.subtitle=a.subtitle);let At=!!a.controlled,te=St(a),ye=te&&an+te,Ae=!!a.demo,et=a.vibrate!==!1,I=typeof matchMedia=="function"&&matchMedia("(prefers-reduced-motion: reduce)").matches,C=!1,ne=new Set,N=(e,t)=>{let r=window.setTimeout(()=>{ne.delete(r),C||e()},t);ne.add(r)},Ft=e=>new Promise(t=>window.setTimeout(t,e)),be=0;rn(),n.innerHTML=on(s,g,{demo:Ae,shuffle:a.shuffle!==!1,vibrate:et});let f=e=>{let t=n.querySelector(`[data-r="${e}"]`);if(!t)throw new Error(`[packing-bingo] internal: missing element "${e}"`);return t},_=n.querySelector(".pkb-board"),we=n.querySelector(".pkb-gw"),de=n.querySelector(".pkb-grid"),Ee=n.querySelector(".pkb-lines"),fe=n.querySelector(".pkb-fx"),L=fe.getContext("2d"),K=Array.from(de.children),H=s.itemCell.map(e=>K[e]),Pt=s.center>=0?K[s.center]:null,Le=H.map(e=>e.querySelector("input")),tt=f("kick"),Fe=f("snd"),U=f("perfect"),w=l(void 0),B=[],me=new Set,Pe=new Set,Se=!1,nt=0,O=0,ue=0,z=0,ae=0,at=0,Ie=!1,re=new Set,J=new Set,rt=Ze(Ct),Z=rt!=null?rt==="1":a.sound===!1,A=Lt(()=>Z),ot=()=>{Fe.textContent=Z?g.soundOff:g.soundOn,Fe.setAttribute("aria-pressed",String(!Z))};Fe.addEventListener("click",()=>{Z=!Z,Qe(Ct,Z?"1":"0"),ot(),Z||A.pop(4)}),ot();let W=[],Q=0,ke=1,V=0,X=0,it=()=>{let e=_.getBoundingClientRect();ke=Math.min(2,window.devicePixelRatio||1),V=e.width,X=e.height,fe.width=Math.round(V*ke),fe.height=Math.round(X*ke)},Re=(e,t,r,o,p,i,d,S)=>({x:e,y:t,vx:r,vy:o,g:p,life:d,shape:S,w:(5+Math.random()*6)*i,h:(3+Math.random()*5)*i,r:Math.random()*6,vr:(Math.random()-.5)*.35,c:Bt[Math.random()*Bt.length|0]}),qe=()=>{!Q&&L&&(Q=requestAnimationFrame(st))};function oe(e,t,r,o={}){if(!I){for(let p=0;p<r;p++){let i=(o.angle??-Math.PI/2)+(Math.random()-.5)*(o.spread??Math.PI*2),d=(o.speed??10)*(.35+Math.random()*.85),S=Math.random()<(o.star??.15)?"star":Math.random()<.3?"round":"rect";W.push(Re(e,t,Math.cos(i)*d,Math.sin(i)*d,o.g??.28,o.size??1,(o.life??110)+Math.random()*40,S))}qe()}}function It(e){if(I)return;let t=performance.now()+e,r=()=>{for(let o=0;o<4;o++)W.push(Re(Math.random()*V,-12,(Math.random()-.5)*2,2+Math.random()*3,.045,1,420,Math.random()<.2?"star":"rect"));qe(),performance.now()<t&&N(r,45)};r()}function Rt(e){if(I)return;let t=performance.now()+e,r=()=>{let o=Re(Math.random()*V,-30,(Math.random()-.5)*1.5,1.5+Math.random()*2,.05,1,500,"emoji");o.e=m[Math.random()*m.length|0].emoji,o.w=22+Math.random()*12,o.vr=(Math.random()-.5)*.06,W.push(o),qe(),performance.now()<t&&N(r,110)};r()}function qt(e,t){oe(e,t,80,{speed:7.5,g:.06,life:85,star:.4}),A.boom()}function Nt(e,t){e.beginPath();for(let r=0;r<10;r++){let o=r*Math.PI/5-Math.PI/2,p=r%2?t*.45:t;e.lineTo(Math.cos(o)*p,Math.sin(o)*p)}e.closePath(),e.fill()}function st(){if(Q=0,!(C||!L)){L.setTransform(ke,0,0,ke,0,0),L.clearRect(0,0,V,X),W=W.filter(e=>e.life>0&&e.y<X+40);for(let e of W)e.vx*=.985,e.vy=e.vy*.985+e.g,e.x+=e.vx,e.y+=e.vy,e.r+=e.vr,e.life--,L.save(),L.globalAlpha=Math.min(1,e.life/25),L.translate(e.x,e.y),L.rotate(e.r),L.fillStyle=e.c,e.shape==="round"?(L.beginPath(),L.arc(0,0,e.h/1.6,0,7),L.fill()):e.shape==="star"?Nt(L,e.w*.8):e.shape==="emoji"?(L.font=`${e.w}px "Apple Color Emoji","Segoe UI Emoji","Noto Color Emoji",sans-serif`,L.textAlign="center",L.textBaseline="middle",L.fillText(e.e??"",0,0)):(L.scale(1,Math.cos(e.r*2.3)),L.fillRect(-e.w/2,-e.h/2,e.w,e.h)),L.restore();W.length&&(Q=requestAnimationFrame(st))}}let Me=e=>{let t=_.getBoundingClientRect(),r=e.getBoundingClientRect();return{x:r.left-t.left+r.width/2,y:r.top-t.top+r.height/2}},R=(e,t)=>{e.classList.remove(t),e.offsetWidth,e.classList.add(t)},pt=(e,t)=>{I||(e.classList.remove("pkb-squash"),e.style.setProperty("--pkb-d",t+"ms"),R(e,"pkb-hop"))};de.addEventListener("animationend",e=>{let t=e.target;t.classList.contains("pkb-tile")&&(e.animationName==="pkb-hop"||e.animationName==="pkb-squash")&&t.classList.remove(e.animationName)});let jt=e=>{let t=document.createElement("span");t.className="pkb-ring",e.appendChild(t),t.addEventListener("animationend",()=>t.remove())},ge=e=>{if(!et)return;let t=navigator.userActivation;if(!(t&&!t.hasBeenActive))try{navigator.vibrate?.(e)}catch{}},Be=(e,t,r,o,p=0,i)=>{let d=document.createElement("div");d.className="pkb-float pkb-"+o,d.textContent=e,d.style.left=t+"px",d.style.top=r+"px",p&&(d.style.animationDelay=p+"ms"),i&&(d.style.color=i),_.appendChild(d),d.addEventListener("animationend",()=>d.remove())},lt=(e,t,r)=>Math.max(0,Math.min(1,(e-t)/r)),ct=e=>1-Math.pow(1-e,3),$e=0;function Ne(){cancelAnimationFrame($e);let e=ue,t=O,r=performance.now(),o=p=>{if(C)return;let i=lt(p,r,450);ue=Math.round(e+(t-e)*ct(i)),f("sc").textContent=ue.toLocaleString(),i<1&&($e=requestAnimationFrame(o))};o(r),I||R(f("sp"),"pkb-bump")}let bt=(e,t,r,o="pt")=>{Be(`+${e}`,t,r,o),Ne()};function je(e,t,r,o,p,i=!1){let d=performance.now(),S=be,F=0,G=j=>{if(C||S!==be)return;let le=lt(j,d,o);e.textContent=p(Math.round(t+(r-t)*ct(le))),i&&le<1&&j-F>55&&(A.tick(),F=j),le<1?requestAnimationFrame(G):I||R(e,"pkb-bump")};G(d)}let dt=e=>({x:e.offsetLeft+e.offsetWidth/2,y:e.offsetTop+e.offsetHeight/2}),he=0;function De(e=[]){if(he){Ee.innerHTML="";return}Ee.setAttribute("viewBox",`0 0 ${we.clientWidth} ${we.clientHeight}`),Ee.innerHTML=B.map(t=>{let r=dt(K[c[t][0]]),o=dt(K[c[t][x-1]]),p=o.x-r.x,i=o.y-r.y,d=Math.hypot(p,i)||1,S=26*ve,F=p/d*S,G=i/d*S,j=`x1="${r.x-F}" y1="${r.y-G}" x2="${o.x+F}" y2="${o.y+G}" pathLength="1"`;return`<g${e.includes(t)?' class="pkb-draw"':""}><line class="pkb-u" ${j}/><line class="pkb-o" ${j}/></g>`}).join("")}function Dt(e,t){let r=Me(H[e]);if(!t){z=0,f("combo").classList.remove("pkb-on"),A.off(),ge(8);return}let o=performance.now();z=o-at<nn?z+1:1,at=o,ae=Math.max(ae,z),A.pop(z-1),I||(R(H[e],"pkb-squash"),jt(H[e])),oe(r.x,r.y,18,{speed:6,g:.2,life:30,size:.6,star:.5}),re.has(e)||(re.add(e),O+=10*z,bt(10*z,r.x,r.y-12)),z>=2&&(Be(g.comboPop(z),r.x,r.y+22,"cmb",90,$t[(z-2)%$t.length]),f("cmbN").textContent=g.combo(z),R(f("combo"),"pkb-on")),ge(18)}f("cbar").addEventListener("animationend",()=>{f("combo").classList.remove("pkb-on"),z=0});function Ht(e){e.forEach(t=>{let r=Me(H[t]);Be(g.reachPop,r.x,r.y-34,"rch",150)}),N(()=>A.reach(),150)}function Gt(e,t){let r=e.length,o=[...new Set(e.flatMap(i=>c[i]))].map(i=>K[i]),p=Math.min(70,300/o.length);o.forEach((i,d)=>N(()=>{pt(i,0);let S=Me(i);oe(S.x,S.y,14,{speed:5,g:.15,life:30,size:.7,star:.8}),A.note(d+3)},d*p)),N(()=>{f("bT").textContent=r>=3?g.bannerTriple:r===2?g.bannerDouble:g.bannerSingle,f("bS").textContent=r>1?g.bannerMulti(r):g.bannerNth(B.length),R(f("banner"),"pkb-show"),I||(R(f("flash"),"pkb-go"),R(_,"pkb-punch"));let i=Me(we);oe(i.x,i.y,r>1?180:110,{speed:r>1?16:13,star:.3}),A.bingo(r),ge(r>1?[40,60,40,60,90]:[40,60,40]),t&&N(()=>bt(t,i.x,i.y+105,"big"),350)},o.length*p+60)}function _t(e){let t=Ie?0:1e3;Ie=!0,O+=t,K.forEach((o,p)=>pt(o,ee(p)*180/Math.max(1,x-1))),A.perfect(),I||R(f("flash"),"pkb-go"),f("pbody").textContent=Ot(g,b),f("sScore").textContent="0",f("sCombo").textContent="\xD70",f("sBingo").textContent="0",N(()=>{R(U,"pkb-show"),f("close").focus({preventScroll:!0}),N(()=>{I||R(_,"pkb-shake"),A.boom(),oe(0,X,90,{angle:-Math.PI/3,spread:.8,speed:22,g:.32,star:.3}),oe(V,X,90,{angle:-Math.PI*2/3,spread:.8,speed:22,g:.32,star:.3}),It(3500),ge([60,80,60,80,200]),t&&Be(g.perfectBonus(t),V/2,X*.16,"big"),je(f("sScore"),0,O,1300,o=>o.toLocaleString(),!0),je(f("sCombo"),0,ae,700,o=>"\xD7"+o),je(f("sBingo"),0,B.length,700,String),Ne()},720),[1300,1650,2e3,2350,2700].forEach(o=>N(()=>qt(V*(.15+Math.random()*.7),X*(.12+Math.random()*.3)),o)),N(()=>Rt(3e3),1500)},520);let r={score:O,maxCombo:ae};e.push(()=>a.onPerfect?.(r))}function He(){be++,ne.forEach(e=>clearTimeout(e)),ne.clear(),cancelAnimationFrame($e),ue=O,f("sc").textContent=O.toLocaleString()}function Kt(){W=[],cancelAnimationFrame(Q),Q=0,L?.clearRect(0,0,fe.width,fe.height),_.querySelectorAll(".pkb-float, .pkb-ring").forEach(e=>e.remove()),f("banner").classList.remove("pkb-show"),f("flash").classList.remove("pkb-go"),f("combo").classList.remove("pkb-on"),U.classList.remove("pkb-show")}let Ge=()=>E.flatMap((e,t)=>e.every(r=>w[r])?[t]:[]);function Ce(e,t){let r=[],o=w,p=o.filter(Boolean).length;B=Ge();let i=B.filter(y=>!me.has(y));[...me].some(y=>!B.includes(y))&&(He(),p<b&&U.classList.remove("pkb-show"));let d=new Set(B.flatMap(y=>c[y])),S=new Set;for(let y of E){let Y=y.filter(Wt=>!o[Wt]);Y.length===1&&S.add(Y[0])}H.forEach((y,Y)=>{y.classList.toggle("pkb-on",o[Y]),y.classList.toggle("pkb-line",d.has(s.itemCell[M[Y]])),y.classList.toggle("pkb-reach",S.has(Y))}),Pt?.classList.toggle("pkb-line",d.has(s.center)),_.classList.toggle("pkb-all",p===b),tt.classList.toggle("pkb-gold",p===b),tt.textContent=p===b?g.perfectTag:g.tag,f("cnt").textContent=`${p}/${b}`,f("bng").textContent=String(B.length);let F=f("bp");B.length>nt&&(F.classList.remove("pkb-hot"),F.offsetWidth),F.classList.toggle("pkb-hot",B.length>0),nt=B.length,De(i),e!==null&&Dt(e,o[e]);let G=i.map(y=>Oe(E[y])).filter(y=>!J.has(y));G.forEach(y=>J.add(y));let j=100*G.length*G.length;if(O+=j,t)j&&Ne();else if(p===b&&!Se)_t(r);else if(i.length){Gt(i,j);let y={newLines:i,totalLines:B.length,score:O};r.push(()=>a.onBingo?.(y))}else if(e!==null&&o[e]){let y=[...S].filter(Y=>!Pe.has(Y));y.length&&Ht(y)}me=new Set(B),Pe=S,Se=p===b;let le=[...S].map(y=>m[y].label);return f("msg").textContent=p===b?g.statusDone:le.length?g.statusReach(le):B.length?g.statusLines(B.length,b-p):g.statusStart(b-p),r}let ft=e=>{for(let t of e){if(C)return;t()}},mt=()=>{te&&Qe(te,JSON.stringify(w))};function ut(e,t,r){w=e,Le.forEach((p,i)=>p.checked=w[i]);let o=Ce(t,r);return mt(),o}function _e(e){He(),Kt(),w=e,Le.forEach((r,o)=>r.checked=w[o]),re.clear(),J.clear(),w.forEach((r,o)=>r&&re.add(o));let t=Ge();t.forEach(r=>J.add(Oe(E[r]))),me=new Set(t),Pe=new Set,Se=w.every(Boolean),Ie=Se,O=ue=re.size*10+J.size*100,z=0,ae=0,f("sc").textContent=O.toLocaleString(),Ce(null,!0),mt()}function ie(e,t,r={}){if(At){Le.forEach((p,i)=>p.checked=w[i]),a.onChange?.(e.slice());return}let o=[];r.reset?_e(e):o=ut(e,t,!!r.quiet),a.onChange?.(w.slice()),ft(o)}function kt(e){u=e,u.forEach((r,o)=>{M[r]=o,K[s.itemCell[o]]=H[r]}),E=s.lines.map(r=>r.map(o=>u[o]));let t=document.activeElement;K.forEach((r,o)=>{r.style.setProperty("--pkb-gd",Tt(o,x)),de.appendChild(r)}),t instanceof HTMLElement&&de.contains(t)&&document.activeElement!==t&&t.focus({preventScroll:!0})}let Ut=()=>{ye&&Qe(ye,JSON.stringify(u))},xe=[];function gt(e){w.every(Boolean)||He();let t=I?null:H.map(o=>o.getBoundingClientRect());xe.forEach(o=>o.cancel()),xe=[],kt(e),E.forEach(o=>{o.every(p=>re.has(p))&&J.add(Oe(o))});let r=Ge();r.forEach(o=>J.add(Oe(E[o]))),me=new Set(r),Ce(null,!0),Ut(),!(!t||typeof Element.prototype.animate!="function")&&(H.forEach((o,p)=>{let i=t[p],d=o.getBoundingClientRect(),S=i.left-d.left,F=i.top-d.top;Math.abs(S)+Math.abs(F)<1||xe.push(o.animate([{transform:`translate(${S}px,${F}px)`},{transform:"none"}],{duration:zt-140,delay:Math.random()*140,easing:"cubic-bezier(.3,1.25,.5,1)",fill:"backwards"}))}),clearTimeout(he),he=window.setTimeout(()=>{he=0,xe=[],C||De(B)},zt),Ee.innerHTML="")}function ht(){let e=u.slice();do for(let t=b-1;t>0;t--){let r=Math.floor(Math.random()*(t+1));[e[t],e[r]]=[e[r],e[t]]}while(e.every((t,r)=>t===u[r]));gt(e),A.shuffle(),ge([10,40,10,40,10,40,24])}let Ke=()=>{v(u)||gt(k())};if(de.addEventListener("change",e=>{let t=Le.indexOf(e.target);if(t<0)return;let r=w.slice();r[t]=!r[t],ie(r,t)}),n.querySelector('[data-r="shuf"]')?.addEventListener("click",ht),f("reset").addEventListener("click",()=>{Ke(),ie(l(void 0),null,{reset:!0})}),f("close").addEventListener("click",()=>U.classList.remove("pkb-show")),U.addEventListener("click",e=>{e.target===U&&U.classList.remove("pkb-show")}),Ae){let e=!1,t=()=>{w.every(Boolean)?ie(l(void 0),null,{reset:!0}):U.classList.remove("pkb-show")},r=async o=>{if(!e){e=!0;try{t();let p=be;for(let i of o){if(await Ft(i.delay),C||p!==be)return;let d=w.slice();d[i.i]=!0,ie(d,i.i,{quiet:i.quiet})}}finally{e=!1}}};f("dB").addEventListener("click",()=>{let o=()=>E.map(i=>i.filter(d=>!w[d])).filter(i=>i.length).sort((i,d)=>i.length-d.length)[0]??[],p=w.every(Boolean)?[...E[0]]:o();r(p.map(i=>({i,delay:320})))}),f("dP").addEventListener("click",()=>{let o=m.map((i,d)=>d),p=w.every(Boolean)?o:o.filter(i=>!w[i]);r(p.map((i,d)=>d<p.length-1?{i,delay:170,quiet:!0}:{i,delay:450}))}),f("dR").addEventListener("click",()=>{e||(Ke(),ie(P(),null,{reset:!0}))})}let se=null;if(ye)try{let e=JSON.parse(Ze(ye)??"null");$(e)&&(se=e)}catch{}!se&&$(a.defaultOrder)&&(se=a.defaultOrder.slice()),se&&!v(se)&&kt(se);let pe=null;if(te)try{let e=JSON.parse(Ze(te)??"null");Array.isArray(e)&&(pe=l(e))}catch{}!pe&&a.defaultChecked&&(pe=l(a.defaultChecked)),!pe&&Ae&&(pe=P()),it(),_e(pe??l(void 0));let Ue=typeof ResizeObserver=="function"?new ResizeObserver(()=>{it(),De()}):null;return Ue?.observe(_),Ue?.observe(we),{setChecked(e,t={}){if(C)return;let r=l(e),o=r.flatMap((p,i)=>p!==w[i]?[i]:[]);if(o.length){if(!t.animate||o.length!==1){_e(r);return}ft(ut(r,o[0],!1))}},reset(){C||(Ke(),ie(l(void 0),null,{reset:!0}))},shuffle(){C||ht()},refresh(){C||Ce(null,!0)},getState(){return{checked:w.slice(),lines:B.slice(),score:O,maxCombo:ae,complete:w.every(Boolean),size:x,free:s.free,order:u.slice()}},destroy(){C||(C=!0,ne.forEach(e=>clearTimeout(e)),ne.clear(),clearTimeout(he),xe.forEach(e=>e.cancel()),cancelAnimationFrame(Q),cancelAnimationFrame($e),Ue?.disconnect(),A.close(),n.innerHTML="")}}}return Qt(pn);})();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "packing-bingo",
3
- "version": "0.2.0",
3
+ "version": "0.4.0",
4
4
  "description": "A school-trip packing checklist that plays like bingo, as a React component (or plain JS): combos, fanfares and fireworks.",
5
5
  "license": "MIT",
6
6
  "author": "Jin-hiroo",
@@ -8,7 +8,7 @@
8
8
  "type": "git",
9
9
  "url": "git+https://github.com/Jin-hiroo/packing-bingo.git"
10
10
  },
11
- "homepage": "https://github.com/Jin-hiroo/packing-bingo#readme",
11
+ "homepage": "https://jin-hiroo.github.io/packing-bingo/",
12
12
  "bugs": "https://github.com/Jin-hiroo/packing-bingo/issues",
13
13
  "keywords": [
14
14
  "react",