@cahyo-dimas/freeday 3.12.1 → 3.14.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/CHANGELOG.md +133 -9
- package/COMPONENTS.md +76 -1
- package/README.id.md +1 -1
- package/README.md +1 -1
- package/adapters/react/components/FdyDrawer.tsx +4 -0
- package/adapters/react/index.d.ts +2 -0
- package/adapters/vue/components/FdyDrawer.vue +4 -0
- package/adapters/vue/index.d.ts +2 -0
- package/dist/freeday-app-shell.js +1 -0
- package/dist/freeday-autocomplete.js +1 -0
- package/dist/freeday-breakpoint.js +12 -2
- package/dist/freeday-carousel.js +1 -0
- package/dist/freeday-cascade.js +1 -0
- package/dist/freeday-cfl.js +5 -1
- package/dist/freeday-chart.js +1 -0
- package/dist/freeday-chip.js +12 -4
- package/dist/freeday-datepicker.js +2 -0
- package/dist/freeday-datetime.js +1 -0
- package/dist/freeday-drawer.js +2 -0
- package/dist/freeday-form.js +1 -0
- package/dist/freeday-mask.js +2 -0
- package/dist/freeday-menu.js +1 -0
- package/dist/freeday-number.js +1 -0
- package/dist/freeday-rating.js +1 -0
- package/dist/freeday-search.js +1 -0
- package/dist/freeday-select.js +1 -0
- package/dist/freeday-slider.js +1 -0
- package/dist/freeday-sortable.js +222 -0
- package/dist/freeday-stepper.js +1 -0
- package/dist/freeday-table.js +1 -0
- package/dist/freeday-tabs.js +1 -0
- package/dist/freeday-timepicker.js +1 -0
- package/dist/freeday-tree.js +1 -0
- package/dist/freeday-unhydrated.js +83 -0
- package/dist/freeday-upload.js +6 -3
- package/dist/freeday.bundle.css +20 -1
- package/dist/freeday.css +20 -1
- package/dist/freeday.js +366 -10
- package/docs/agent-onboarding.md +4 -1
- package/docs/getting-started.md +1 -1
- package/docs/integrations.md +3 -2
- package/package.json +2 -2
- package/src/components/input.css +2 -1
- package/src/components/sortable.css +17 -0
package/CHANGELOG.md
CHANGED
|
@@ -9,19 +9,143 @@ benar. Perubahan seperti itu ditulis di bawah `### Changed: BREAKING (types)`
|
|
|
9
9
|
lama → tipe baru, dan cara menyempitkannya — bukan di bawah `### Added`, betapapun aditifnya dari
|
|
10
10
|
sisi kit.
|
|
11
11
|
|
|
12
|
+
## [3.14.0] - 2026-10-29
|
|
13
|
+
|
|
14
|
+
**Daftar terurut lewat seret dan papan ketik, dan satu atribut untuk berkata "ini bukan urusan
|
|
15
|
+
kit".** Dua butir dari `CATATAN-FREEDAY.md` app ronda (§14 dan §15). Mengaudit §14 menemukan satu
|
|
16
|
+
cacat yang tak dilaporkan: `FdyDrawer` Vue dan React bisa ditutup lewat backdrop walau
|
|
17
|
+
`dismissible=false`.
|
|
18
|
+
|
|
19
|
+
### Added
|
|
20
|
+
- **`data-fdy-sortable`, enhancer ke-32** (`#103`), `src/freeday-sortable.js` plus
|
|
21
|
+
`.fdy-sortable__handle`. Baris diseret lewat pegangannya, atau dipindah satu langkah dengan ↑ / ↓
|
|
22
|
+
saat pegangannya terfokus. Lima layar di app ronda menyuruh orang mengetik nomor urut di kotak
|
|
23
|
+
angka, dan app itu akhirnya menulis sendiri SortableJS plus jalur papan ketiknya. Selama diseret,
|
|
24
|
+
garis menunjukkan tempat baris akan mendarat dan tak ada elemen yang berpindah sebelum tombol
|
|
25
|
+
dilepas; Escape membatalkan. `fdy-sort-change` (`{key, from, to, order}`) dapat dibatalkan,
|
|
26
|
+
dengan pola yang sama seperti chip di 3.13.0: halaman statis membiarkannya dan kit memindah
|
|
27
|
+
elemennya, sedangkan framework membatalkannya lalu mengurutkan state-nya sendiri, sebab DOM-nya
|
|
28
|
+
milik framework. Sesudah langkah papan ketik, fokus kembali ke pegangan baris yang sama, dicari
|
|
29
|
+
lewat `data-key` supaya tetap ketemu walau render ulang mengganti elemennya. Perpindahan
|
|
30
|
+
diumumkan di live region. `data-fdy-sort-fixed` menandai baris yang tak bisa dilewati, dan
|
|
31
|
+
`data-disabled` mematikan pengurutan selama daftar dicari atau disaring. Yang sengaja tidak
|
|
32
|
+
dibuat: gulir otomatis saat seretan mendekati tepi halaman, dan memindah baris antar-daftar.
|
|
33
|
+
- **`data-fdy-ignore`** (`#102`). Di elemen atau leluhur mana pun, setiap enhancer melewati
|
|
34
|
+
subtree itu, termasuk di bawah `initAll(document)` yang eksplisit, dan peringatan hook dari 3.13.0
|
|
35
|
+
ikut diam. Pesan peringatannya kini menyebut atribut ini sebagai jalan keluar yang sah. Pemicunya
|
|
36
|
+
matriks chip di layar Pola rotasi, yang perilakunya dikelola app sendiri, sehingga setiap klik di
|
|
37
|
+
situ mencetak peringatan untuk sesuatu yang memang disengaja. Nama yang diusulkan catatannya,
|
|
38
|
+
`data-fdy-raw`, tidak dipakai: di dokumen kit "raw" berarti jalur markup + enhancer, kebalikan
|
|
39
|
+
dari maksud atribut ini.
|
|
40
|
+
|
|
41
|
+
### Fixed
|
|
42
|
+
- **`FdyDrawer` Vue dan React tertutup lewat backdrop walau `dismissible=false`** (`#102`), begitu
|
|
43
|
+
`useFreeday()` dipasang di seluruh halaman. Wrapper itu merender `.fdy-drawer`, yang merupakan hook
|
|
44
|
+
enhancer drawer, sehingga enhancer memasang handler backdrop kedua yang memanggil `close()`
|
|
45
|
+
langsung. Dialognya tertutup, `open` di state app tetap `true`, dan tak ada event `close`. Di luar
|
|
46
|
+
cakupan pemindai, wrapper yang sama memicu peringatan 3.13.0 setiap kali diklik. Keduanya kini
|
|
47
|
+
membawa `data-fdy-ignore`. `FdyChart` juga merender hook, tetapi sejak awal sudah mencap penanda
|
|
48
|
+
siapnya sendiri; ia kini dijaga uji supaya tetap begitu.
|
|
49
|
+
|
|
50
|
+
### Catatan
|
|
51
|
+
- **Angka 9 menit di §14 bukan ongkos pemindaian.** Catatannya mengukur `useFreeday()` di seluruh
|
|
52
|
+
halaman pada 9 menit 6 detik untuk sepuluh uji e2e, dibanding 19,1 detik untuk cakupan modal saja,
|
|
53
|
+
dan mempersempit cakupannya karena itu. Pada bentuk matriks yang sama (38 baris × 4 shift, dua chip
|
|
54
|
+
per sel, 304 tombol), satu `rehydrate()` di seluruh halaman memakan 1,1 ms dan satu update reaktif
|
|
55
|
+
end-to-end 2,1 ms. Sekitar 55 detik per uji lebih mirip uji yang menunggu sampai timeout. Kalau
|
|
56
|
+
angka itu diambil sebelum 3.13.0, waktu itu kit masih menghapus chip yang diklik, dan itu cukup
|
|
57
|
+
menjelaskannya. Ini dugaan; pengukuran ulangnya ada di sisi app.
|
|
58
|
+
|
|
59
|
+
### Gerbang
|
|
60
|
+
- `docs.test.mjs`: setiap fungsi init yang mencap penanda hook wajib memeriksa `data-fdy-ignore`
|
|
61
|
+
sebelum mencap, dan setiap wrapper Vue/React yang merender hook enhancer wajib menandainya
|
|
62
|
+
`data-fdy-ignore` atau mencap penanda siapnya sendiri. Snapshot string enhancer mendapat dua
|
|
63
|
+
string sortable.
|
|
64
|
+
- `browser/app-owned.mjs`: `useFreeday()` di seluruh halaman atas matriks itu, dengan ambang longgar
|
|
65
|
+
(25 ms per rehydrate, 50 ms per update) yang menangkap pemindaian yang meledak, bukan runner yang
|
|
66
|
+
lambat. Drawer `dismissible=false` bertahan dari klik backdrop, chart ter-render sekali, subtree
|
|
67
|
+
yang diabaikan tetap tak tersentuh, dan tak ada satu pun peringatan.
|
|
68
|
+
- `browser/sortable.mjs`, dengan mouse dan papan ketik asli: tanda pendaratan di tengah seretan,
|
|
69
|
+
Escape, klik yang bukan seretan, baris tetap, keadaan nonaktif, perubahan yang dibatalkan tak
|
|
70
|
+
menyentuh DOM, dan list Vue ber-key yang mengurutkan state-nya sendiri.
|
|
71
|
+
- `browser/harness.mjs` mendapat `dragFromTo` dan mengekspos `clickAt`.
|
|
72
|
+
- Dua belas mutasi diverifikasi merah. Satu mutasi yang tetap hijau membuang ambang jarak seret dari
|
|
73
|
+
enhancer: tekanan yang tak meninggalkan barisnya sendiri sudah ditolak `allowed()`.
|
|
74
|
+
|
|
75
|
+
## [3.13.0] - 2026-10-29
|
|
76
|
+
|
|
77
|
+
**Kit berhenti memutuskan hal yang bukan urusannya, dan markup yang tak pernah dihidrasi kini
|
|
78
|
+
bersuara.** Lima butir dari `CATATAN-FREEDAY.md` app ronda (§9 sampai §13), dikerjakan dalam satu
|
|
79
|
+
rilis. Tiga di antaranya gagal tanpa galat apa pun: chip yang hilang sesudah Batal, tombol simpan
|
|
80
|
+
yang mati, dan kelas yang tak cocok dengan aturan mana pun.
|
|
81
|
+
|
|
82
|
+
### Changed
|
|
83
|
+
- **`fdy-chip-remove` dan `fdy-upload-remove` kini dapat dibatalkan** (`#098`). Begitu
|
|
84
|
+
`.fdy-chip__remove` ditekan, enhancer chip langsung menghapus chip-nya, padahal kit tak tahu
|
|
85
|
+
apakah penghapusan itu perlu ditanyakan dulu. Matriks pola rotasi di app ronda memakai chip
|
|
86
|
+
sebagai tampilan dan punya dialog konfirmasi sendiri. Chip-nya hilang ketika dialog masih
|
|
87
|
+
terbuka, dan tetap hilang sesudah **Batal** ditekan. Datanya utuh, layarnya yang salah. Sekarang
|
|
88
|
+
event-nya `cancelable`, dan elemennya baru dihapus kalau tak ada listener yang memanggil
|
|
89
|
+
`preventDefault()`. Perubahan ini aditif: app yang tidak membatalkan mendapat perilaku yang persis
|
|
90
|
+
sama. Baris upload ikut diubah karena bentuknya sama, dan berkas yang sudah dipegang server
|
|
91
|
+
memang layak ditanyakan dulu sebelum dibuang.
|
|
92
|
+
|
|
93
|
+
### Added
|
|
94
|
+
- **Peringatan konsol untuk hook yang tak pernah dihidrasi** (`#099`): `src/freeday-unhydrated.js`,
|
|
95
|
+
sudah termasuk di import akar. Klik, fokus atau submit pertama di dalam elemen ber-hook yang tak
|
|
96
|
+
punya penanda siap mencetak satu `console.warn` per elemen. Pesannya menyebut hook-nya, dan
|
|
97
|
+
elemennya ikut sebagai argumen kedua supaya devtools menautkannya. Pemicunya §10: `useFreeday()`
|
|
98
|
+
yang dipasang di pembungkus yang salah membuat `data-fdy-validate` di luar pembungkus itu diam
|
|
99
|
+
total, tanpa kalimat validasi dan tanpa `fdy-form-valid`. Yang memberi tahu cuma dua uji e2e yang
|
|
100
|
+
merah. Catatannya meminta peringatan ini untuk form, tetapi kegagalannya berlaku untuk setiap
|
|
101
|
+
hook, jadi tabelnya memuat 29 hook dari 24 enhancer. Peringatan dipicu interaksi, bukan saat
|
|
102
|
+
halaman dimuat, karena framework me-mount dan menghidrasi di antara keduanya.
|
|
103
|
+
- **`fdy-help--danger`** (`#100`), alias `fdy-help--error` di dalam aturan yang sama. Kit memakai
|
|
104
|
+
`--danger` sebagai kata nada di mana-mana (tombol, alert, lencana, toast), sehingga app menebak
|
|
105
|
+
`fdy-help--danger`. Kelas itu tak cocok dengan aturan apa pun, dan kalimat peringatannya tampil
|
|
106
|
+
abu-abu. Kontrol form sengaja tidak diberi alias. Keadaannya digerakkan `aria-invalid`, jadi
|
|
107
|
+
`--error` di sana jarang ditulis tangan. Aturan penamaannya kini tertulis di COMPONENTS.md.
|
|
108
|
+
|
|
109
|
+
### Fixed
|
|
110
|
+
- **`FreedayCfl` dan `FreedayBreakpoint` tak punya `initAll`** (`#099`), padahal hanya nama itu
|
|
111
|
+
yang dicari ketiga helper stack (`useFreeday` di Vue dan React, `FreedayBlazor.initAll`). Markup
|
|
112
|
+
CFL mentah di dalam subtree framework dilewati ketiganya dan dialognya tak pernah terbuka. Label
|
|
113
|
+
breakpoint yang di-mount belakangan tetap kosong sampai breakpoint berganti. Tak ada yang
|
|
114
|
+
melaporkan ini; keduanya ketemu saat mengaudit kelas cacat §10.
|
|
115
|
+
|
|
116
|
+
### Docs
|
|
117
|
+
- **`<ul>` polos adalah daftar berbutir yang didukung** (`#101`). `base.css` memang tak pernah
|
|
118
|
+
mereset daftar. Sekarang COMPONENTS.md menjanjikannya, dan sebuah uji menjaga janji itu.
|
|
119
|
+
- §13 (`required` di `FdyCombo`) sudah terkirim di 3.12.0 (`#096`). Tak ada kode baru; app tinggal
|
|
120
|
+
memakainya.
|
|
121
|
+
|
|
122
|
+
### Gerbang
|
|
123
|
+
- `docs.test.mjs`: setiap penanda siap yang dicap enhancer wajib ada di tabel peringatan, dicap di
|
|
124
|
+
berkas milik namespace yang disebut tabel, dan berkas itu wajib benar-benar meng-query selektor
|
|
125
|
+
pasangannya. Setiap enhancer yang menghidrasi markup wajib mengekspos `initAll`. Penjaga string
|
|
126
|
+
kini melewati teks `console.warn` (untuk devtools, tak pernah masuk DOM) dan identifier
|
|
127
|
+
PascalCase.
|
|
128
|
+
- `css.test.mjs`: `fdy-help--danger` harus satu aturan dengan `--error`, dan tak boleh ada aturan
|
|
129
|
+
tanpa cakupan yang mereset `ul`/`ol`/`li`.
|
|
130
|
+
- `browser/app-owned.mjs`, dengan mouse asli: chip dan baris upload yang dibatalkan tetap di
|
|
131
|
+
tempatnya, form yatim memperingatkan sekali sementara form yang terhidrasi diam, dan CFL serta
|
|
132
|
+
label breakpoint yang di-mount belakangan terhidrasi lewat `FreedayBlazor.initAll`.
|
|
133
|
+
- Tiga belas mutasi diverifikasi merah sebelum dipulihkan: enam pada perilaku, lima pada tabel dan
|
|
134
|
+
ekspor, dua pada CSS.
|
|
135
|
+
|
|
12
136
|
## [3.12.1] - 2026-10-27
|
|
13
137
|
|
|
14
138
|
**Modal dan drawer kembali beranimasi di bawah Safari 17.4, termasuk di iPhone 7 pemiliknya.**
|
|
15
139
|
|
|
16
140
|
### Fixed
|
|
17
141
|
- **Empat shorthand `transition` dipecah jadi longhand** (`#097`), di `modal.css` dan `drawer.css`.
|
|
18
|
-
Shorthand yang membawa satu keyword yang tak dikenal mesin **tidak sah saat parse**, jadi
|
|
19
|
-
deklarasinya dibuang
|
|
142
|
+
Shorthand yang membawa satu keyword yang tak dikenal mesin **tidak sah saat parse**, jadi seluruh
|
|
143
|
+
deklarasinya dibuang, dan `allow-discrete` tak dikenal di bawah Safari 17.4, yang ada di bawah
|
|
20
144
|
lantai dukungan kit. Akibatnya modal dan drawer buka-tutup tanpa animasi apa pun. Dipecah begini,
|
|
21
145
|
yang hilang di bawah lantai hanya `transition-behavior`, dan paruh opacity/transform-nya bertahan.
|
|
22
146
|
`overlay` dan `display` tetap terdaftar di `transition-property`, tempat nama yang tak cocok tetap
|
|
23
147
|
sah secara sintaks dan sekadar tak pernah cocok, jadi tak ada lagi yang ikut jatuh. Keluarnya
|
|
24
|
-
tetap seketika di sana sebab `display` memang tak dapat ditransisikan di bawah lantai
|
|
148
|
+
tetap seketika di sana sebab `display` memang tak dapat ditransisikan di bawah lantai, sama
|
|
25
149
|
seperti sebelumnya, jadi pemecahan ini tidak mengambil apa pun.
|
|
26
150
|
|
|
27
151
|
Ekuivalensinya di atas lantai **diukur, bukan dinalar**: `transition-property`,
|
|
@@ -94,7 +218,7 @@ perbaikan ini terdengar jauh lebih mahal daripada yang ternyata.
|
|
|
94
218
|
|
|
95
219
|
**Audit kontrol native di seluruh layar sebuah aplikasi konsumen, bukan di satu layar yang
|
|
96
220
|
mengeluh.** Pemiliknya melaporkan tampilan HP aslinya tak cocok dengan peramban di lebar yang sama,
|
|
97
|
-
dan dugaan pertama
|
|
221
|
+
dan dugaan pertama, termasuk dugaan saya, adalah CSS. Pengukuran menyangkalnya: dengan
|
|
98
222
|
stylesheet aplikasi yang sebenarnya, pada 375x667, Chromium dan WebKit menata `date`, `time`,
|
|
99
223
|
`number`, `search` dan `text` **identik**, 293x44 keenamnya, selisih satu piksel pada `y` yang
|
|
100
224
|
cuma pembulatan. Jadi yang berbeda bukan tata letaknya, melainkan **widget native-nya**: `date` dan
|
|
@@ -106,7 +230,7 @@ layar yang selebihnya sama.
|
|
|
106
230
|
Kit sudah mengatakan ini di tabelnya sendiri ("Use `.fdy-datepicker` / `.fdy-timepicker` /
|
|
107
231
|
`.fdy-datetimepicker` instead") dan sudah mengirim CSS plus enhancer-nya. Yang belum ada adalah
|
|
108
232
|
wrapper bertipe untuk timepicker, jadi aplikasi Vue/React/Blazor harus merakit sendiri
|
|
109
|
-
plumbing custom-event-nya
|
|
233
|
+
plumbing custom-event-nya, dan merakit sendiri adalah yang membuat empat `<input type="time">`
|
|
110
234
|
bertahan di satu formulir shift.
|
|
111
235
|
|
|
112
236
|
Catatan kejujuran: perbedaan iOS itu **tidak** direproduksi di sini. WebKit desktop bukan Mobile
|
|
@@ -116,8 +240,8 @@ lokal, dan kini diuji, adalah perilaku penggantinya.
|
|
|
116
240
|
|
|
117
241
|
### Added
|
|
118
242
|
- **`FdyTimepicker`** (`#094`), wrapper bertipe di **ketiga** stack, menjadikannya tiga belas.
|
|
119
|
-
Vue dan React mengimplementasikan listbox-nya secara native sebab ia kontrol form
|
|
120
|
-
|
|
243
|
+
Vue dan React mengimplementasikan listbox-nya secara native sebab ia kontrol form. Alasannya sama
|
|
244
|
+
dengan `FdyCombo`, dan `FdyChart` menyatakannya dari sisi sebaliknya: enhancer yang
|
|
121
245
|
menguasai DOM berkelahi dengan render framework dan tak menyisakan `v-model`. Blazor
|
|
122
246
|
menjembatani enhancer lewat seed, seperti `FdyDatepicker`. Sorotannya **dijepit, bukan
|
|
123
247
|
berputar**: pada daftar 48 opsi, ArrowUp di `00:00` yang melompat ke `23:30` terbaca sebagai
|
|
@@ -126,7 +250,7 @@ lokal, dan kini diuji, adalah perilaku penggantinya.
|
|
|
126
250
|
- **`data-id` dan `data-describedby` pada seed timepicker** (`#094`). Keduanya tak terbaca
|
|
127
251
|
sebelumnya, jadi host yang menampilkan teks galat tak punya cara menautkannya. Pemicunya
|
|
128
252
|
`<button>`, yang **bukan** elemen labelable, sehingga `<label for>` memang tak akan pernah
|
|
129
|
-
mengaktifkannya
|
|
253
|
+
mengaktifkannya, dan itu kini didokumentasikan.
|
|
130
254
|
- **`FreedayTimepicker.setState(root, { disabled, readonly, invalid })`** (`#094`), bentuknya sama
|
|
131
255
|
dengan `FreedayDatepicker.setState`. Tanpa ini, host yang merender seed-nya sekali lalu tidak
|
|
132
256
|
pernah lagi (Blazor, `ShouldRender => false`) memiliki tiga parameter keadaan yang tak ada yang
|
|
@@ -136,7 +260,7 @@ lokal, dan kini diuji, adalah perilaku penggantinya.
|
|
|
136
260
|
- **`FdyDateRange` membuang kedelapan prop label navigasi kalender** (`#095`), di ketiga stack.
|
|
137
261
|
`FdyDatepicker` menerimanya sejak 2.1.1; rentangnya tidak meneruskannya, sehingga rentang tanggal
|
|
138
262
|
adalah **satu-satunya** kontrol tanggal di kit yang navigasinya tak bisa dinamai dalam bahasa
|
|
139
|
-
halamannya sendiri
|
|
263
|
+
halamannya sendiri: aplikasi berbahasa Indonesia mendapat "Previous month" tepat di tempat yang
|
|
140
264
|
tak dapat ia jangkau. Diteruskan apa adanya ke kedua pemilih. Prop datar `xxxLabel`, bukan objek
|
|
141
265
|
`labels`, sebab bentuk itulah yang sudah dipakai setiap komponen lain di kit. Blazor menambah
|
|
142
266
|
`BackToMonthsLabel`, karena seed yang kedua pemilihnya dibangun dari situ punya tombol itu.
|
package/COMPONENTS.md
CHANGED
|
@@ -32,6 +32,10 @@ live docs.
|
|
|
32
32
|
state *and* the screen-reader state. Pair it with `aria-describedby` → the `id` of a
|
|
33
33
|
`.fdy-help.fdy-help--error`. The `--error` class modifiers exist only for the case where the
|
|
34
34
|
invalid state does not belong to the control itself.
|
|
35
|
+
**`--error` names a field's validation state, `--danger` names a tone** (button, alert, badge,
|
|
36
|
+
toast, menu item). `.fdy-help` is the one block that takes both, `--danger` being the same
|
|
37
|
+
colour, because help text is where either reading is natural: a sentence that warns without
|
|
38
|
+
any field being invalid.
|
|
35
39
|
6. **Interactive components need their enhancer script.** Static ones (button, card, badge, table,
|
|
36
40
|
alert, breadcrumb, timeline, accordion, tree-without-cascade…) are CSS-only.
|
|
37
41
|
7. **On Vue, React or Blazor, thirteen components have a typed wrapper. Use it.** `FdyCombo` ·
|
|
@@ -44,6 +48,15 @@ live docs.
|
|
|
44
48
|
breaks quietly: later-rendered DOM is never hydrated and the widget's state sits in the DOM
|
|
45
49
|
instead of your framework's. Everything else is the same markup everywhere; hydrate the other
|
|
46
50
|
interactive components with `useFreeday` (Vue/React) or `FreedayBlazor.initAll` (Blazor).
|
|
51
|
+
**Markup no `initAll` reached says so.** The first click, focus or submit inside a hook the kit
|
|
52
|
+
never enhanced logs one `console.warn` naming it, with the element attached. The usual cause is
|
|
53
|
+
a `useFreeday()` ref on a wrapper that does not contain it. `freeday-unhydrated.js` does this,
|
|
54
|
+
and it ships in the root import.
|
|
55
|
+
**`data-fdy-ignore` says "not yours".** On an element or any ancestor, every enhancer skips that
|
|
56
|
+
subtree, even under an explicit `initAll(document)`, and the warning above stays quiet. Use it
|
|
57
|
+
where the app drives kit-styled markup itself, such as a chip matrix with its own removal flow.
|
|
58
|
+
The Vue and React `FdyDrawer` carry it already, so a page-wide `useFreeday()` cannot hand the
|
|
59
|
+
drawer enhancer a second backdrop handler.
|
|
47
60
|
|
|
48
61
|
### Containment — why the kit's containers are `position:relative`
|
|
49
62
|
|
|
@@ -93,6 +106,7 @@ element is fine. Events are bubbling
|
|
|
93
106
|
| `data-fdy-tree` | `freeday-tree.js` | `FreedayTree` | — |
|
|
94
107
|
| `data-fdy-rating` | `freeday-rating.js` | `FreedayRating` | — (native `change`) |
|
|
95
108
|
| `data-fdy-slider` | `freeday-slider.js` | `FreedaySlider` | — (native `input`) |
|
|
109
|
+
| `data-fdy-sortable` | `freeday-sortable.js` | `FreedaySortable` | `fdy-sort-change` |
|
|
96
110
|
| `data-fdy-number` | `freeday-number.js` | `FreedayNumber` | — (native `input`, `change`) |
|
|
97
111
|
| `data-fdy-search` | `freeday-search.js` | `FreedaySearch` | `fdy-search` (+ native `input` on clear) |
|
|
98
112
|
| `data-fdy-copy="value"` (delegated, no hydration) | `freeday-copy.js` | `FreedayCopy` | `fdy-copy` |
|
|
@@ -562,7 +576,7 @@ native control, otherwise a `<div>` + explicitly associated label.
|
|
|
562
576
|
`.fdy-field--full` on the fields — **not** a `max-width` override on the container. Both of this
|
|
563
577
|
kit's own consoles wrote that override, once per form, before this modifier reached outside the
|
|
564
578
|
grid.
|
|
565
|
-
- `.fdy-label` (+`--required`) · `.fdy-input` (+`--error`) · `.fdy-textarea` · `.fdy-help` (+`--error`)
|
|
579
|
+
- `.fdy-label` (+`--required`) · `.fdy-input` (+`--error`) · `.fdy-textarea` · `.fdy-help` (+`--error`, or its alias `--danger`)
|
|
566
580
|
|
|
567
581
|
**Grouped controls are a `<fieldset>`, not a new block.** Put `.fdy-field` on the fieldset and
|
|
568
582
|
`.fdy-label` on the legend. The kit already resets the UA border/padding and supplies the spacing:
|
|
@@ -1214,6 +1228,9 @@ zone.addEventListener('fdy-upload-add', (e) => {
|
|
|
1214
1228
|
zone.addEventListener('fdy-upload-remove', (e) => forget(e.detail.file)); // same element
|
|
1215
1229
|
```
|
|
1216
1230
|
|
|
1231
|
+
`fdy-upload-remove` is **cancelable** too: `preventDefault()` keeps the row, for a file the server
|
|
1232
|
+
already holds and the user should confirm losing. Remove it yourself afterwards with `row.el.remove()`.
|
|
1233
|
+
|
|
1217
1234
|
**Bring your own row:** omit the file list entirely (no `data-filelist`, and no `.fdy-filelist`
|
|
1218
1235
|
sibling) and the enhancer renders nothing while still dispatching `fdy-upload-add`, where `detail.row`
|
|
1219
1236
|
still works, its element simply isn't attached. Note the fallback when `data-filelist` is absent is
|
|
@@ -1757,6 +1774,10 @@ responsive `.fdy-datatable` should become below `md`, rather than a stack of `.f
|
|
|
1757
1774
|
control in the kit. Do not hand-roll it: an undimmed row that still lights up under the pointer
|
|
1758
1775
|
reads as clickable while it is refusing input.
|
|
1759
1776
|
- Not `.fdy-list-reset`, which only strips UA bullets/indent from a semantic list.
|
|
1777
|
+
- Not for three bullet points in a dialog either. **A plain bulleted list is a plain `<ul>`/`<ol>`,
|
|
1778
|
+
no class**, and that is supported: `base.css` deliberately leaves lists alone, so native bullets
|
|
1779
|
+
and indent survive (a test keeps it that way). The exception is a utility framework run with its
|
|
1780
|
+
preflight on, which strips them.
|
|
1760
1781
|
|
|
1761
1782
|
```html
|
|
1762
1783
|
<ul class="fdy-list">
|
|
@@ -2335,8 +2356,62 @@ Three roles inside a `.fdy-chips` row:
|
|
|
2335
2356
|
|
|
2336
2357
|
Interactive chips are managed by `freeday-chip.js`: wrap the row in `data-fdy-chips` (+
|
|
2337
2358
|
`data-single` for pick-one, `data-label` for the group name), give each `data-value`.
|
|
2359
|
+
|
|
2360
|
+
**Removal is cancelable.** Pressing `.fdy-chip__remove` fires `fdy-chip-remove` (`detail.value`) on
|
|
2361
|
+
the chip, then removes the chip only if no listener called `preventDefault()`. Cancel it whenever
|
|
2362
|
+
the removal is the app's call: a confirm step, or chips rendered from framework state, which
|
|
2363
|
+
should leave the DOM when the state changes and not before. Without that, Cancel in your own
|
|
2364
|
+
confirm dialog leaves the data intact and the chip gone.
|
|
2365
|
+
|
|
2366
|
+
```js
|
|
2367
|
+
row.addEventListener('fdy-chip-remove', async (e) => {
|
|
2368
|
+
e.preventDefault(); // the kit leaves the chip alone
|
|
2369
|
+
if (await Freeday.confirm({ title: `Remove ${e.detail.value}?`, tone: 'danger' })) {
|
|
2370
|
+
removeFromState(e.detail.value); // your render takes it out
|
|
2371
|
+
}
|
|
2372
|
+
});
|
|
2373
|
+
```
|
|
2338
2374
|
`--tone-1`…`--tone-8` for non-semantic category colours.
|
|
2339
2375
|
|
|
2376
|
+
## Sortable list — `data-fdy-sortable`
|
|
2377
|
+
Reorder a list by dragging a handle, or by focusing the handle and pressing ↑ / ↓. Needs
|
|
2378
|
+
`freeday-sortable.js`. The kit draws the handle and the drag states; the list keeps whatever look it
|
|
2379
|
+
already had (`.fdy-list`, a table body, plain rows).
|
|
2380
|
+
|
|
2381
|
+
- Container: `.fdy-sortable` + `data-fdy-sortable` on a `<ul>`/`<ol>`, a `<tbody>` or a `<div>`.
|
|
2382
|
+
Its element children are the items.
|
|
2383
|
+
- Item: `data-key` (the id the event reports, **required** when a framework renders the list),
|
|
2384
|
+
`data-label` (the name read out, the item's text otherwise), and `data-fdy-sort-fixed` for an item
|
|
2385
|
+
that never moves and that nothing can pass, such as a system row pinned to one end.
|
|
2386
|
+
- Handle: `<button class="fdy-sortable__handle" type="button">` inside the item, icon inside. With no
|
|
2387
|
+
`aria-label` of your own it gets *Move {label}. Drag, or press the up and down arrow keys.*
|
|
2388
|
+
- `data-disabled` on the container switches reordering off, and the handles follow through
|
|
2389
|
+
`aria-disabled`. Set it while the list is searched or filtered, where a row's visible position is
|
|
2390
|
+
not its stored one.
|
|
2391
|
+
- States, set by the enhancer: `is-sorting` on the container, `is-dragging` on the item, and
|
|
2392
|
+
`is-drop-before` / `is-drop-after` on the item it will land against. Nothing moves until the
|
|
2393
|
+
pointer is released, and Escape cancels.
|
|
2394
|
+
- Event: `fdy-sort-change` on the container, `detail {key, from, to, order}`, **cancelable**. Left
|
|
2395
|
+
alone, the kit moves the element. Under Vue, React or Blazor, cancel it and reorder your state,
|
|
2396
|
+
because the DOM is the framework's. Either way the kit announces *{label} moved to position {n} of
|
|
2397
|
+
{total}.* in a polite live region, and after a keyboard step it puts focus back on the moved
|
|
2398
|
+
item's handle, found by `data-key` so a re-render that replaced the element still gets it.
|
|
2399
|
+
- Strings: `data-fdy-text-handle`, `data-fdy-text-moved` on the container.
|
|
2400
|
+
- Not in the kit: scrolling the page while a drag nears its edge, and moving items between lists.
|
|
2401
|
+
Keep a sortable list short enough to see whole, or paginate it.
|
|
2402
|
+
|
|
2403
|
+
```vue
|
|
2404
|
+
<ul ref="list" class="fdy-list fdy-sortable" data-fdy-sortable
|
|
2405
|
+
:data-disabled="filtered ? '' : undefined"
|
|
2406
|
+
@fdy-sort-change.prevent="(e) => saveOrder(e.detail.order)">
|
|
2407
|
+
<li v-for="r in rows" :key="r.id" class="fdy-list__row" :data-key="r.id" :data-label="r.name">
|
|
2408
|
+
<button class="fdy-sortable__handle" type="button"><IconGrip class="fdy-icon" aria-hidden="true" /></button>
|
|
2409
|
+
{{ r.name }}
|
|
2410
|
+
</li>
|
|
2411
|
+
</ul>
|
|
2412
|
+
<!-- useFreeday(list) in <script setup> -->
|
|
2413
|
+
```
|
|
2414
|
+
|
|
2340
2415
|
## Timeline — `.fdy-timeline`
|
|
2341
2416
|
Vertical event feed, pure CSS. `<ol class="fdy-timeline">` of `.fdy-timeline__item` (`--muted`
|
|
2342
2417
|
`--success` `--warning` `--danger`) with `__marker` `__time` `__title` `__text`. Status is carried
|
package/README.id.md
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
> **Lebih banyak _free day_ buat dev. UI kit-nya sudah siap pakai.**
|
|
6
6
|
|
|
7
7
|
[](https://cahyo-dimas.github.io/freeday-ui-kit/)
|
|
8
|
-
[](https://github.com/cahyo-dimas/freeday-ui-kit/tree/v3.14.0)
|
|
9
9
|
|
|
10
10
|
UI KIT yang token-driven & framework-agnostic. Satu sumber kebenaran untuk warna, tipografi,
|
|
11
11
|
spasi, dan komponen. Blueprint: `docs/superpowers/specs/2026-07-21-freeday-ui-kit-design.md`.
|
package/README.md
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
> **More free days for devs. The UI kit is ready to use.**
|
|
6
6
|
|
|
7
7
|
[](https://cahyo-dimas.github.io/freeday-ui-kit/)
|
|
8
|
-
[](https://github.com/cahyo-dimas/freeday-ui-kit/tree/v3.14.0)
|
|
9
9
|
|
|
10
10
|
A token-driven, framework-agnostic UI kit. One source of truth for color, typography,
|
|
11
11
|
spacing, and components. Blueprint: `docs/superpowers/specs/2026-07-21-freeday-ui-kit-design.md`.
|
|
@@ -7,6 +7,9 @@ import { useEffect, useId, useRef } from 'react';
|
|
|
7
7
|
// through app state, backdrop-click via `event.target === dialogEl`) applied to a drawer that anchors
|
|
8
8
|
// left (default) or right. Native <dialog> supplies the focus trap, focus restore, top-layer stacking
|
|
9
9
|
// and inert background; `dismissible` (default true) gates Esc + backdrop dismissal.
|
|
10
|
+
// `data-fdy-ignore` on the root: this component owns the behaviour, so a page-wide useFreeday() must
|
|
11
|
+
// not hand `.fdy-drawer` to the enhancer as well. Its backdrop handler calls close() past
|
|
12
|
+
// `dismissible` and leaves `open` true on a dialog that is already closed.
|
|
10
13
|
|
|
11
14
|
export interface FdyDrawerProps {
|
|
12
15
|
open: boolean;
|
|
@@ -37,6 +40,7 @@ export function FdyDrawer(props: FdyDrawerProps): JSX.Element {
|
|
|
37
40
|
<dialog
|
|
38
41
|
ref={dialogRef}
|
|
39
42
|
className={drawerClass}
|
|
43
|
+
data-fdy-ignore=""
|
|
40
44
|
aria-labelledby={titleId}
|
|
41
45
|
onCancel={(e): void => {
|
|
42
46
|
e.preventDefault();
|
|
@@ -23,6 +23,8 @@ export interface FdyMaskDetail { value: string; raw: string }
|
|
|
23
23
|
export interface FdyFormInvalidDetail { invalid: HTMLElement[] }
|
|
24
24
|
export interface FdyChipChangeDetail { value: string; pressed: boolean; selected: string[] }
|
|
25
25
|
export interface FdyChipRemoveDetail { value: string }
|
|
26
|
+
/** `fdy-sort-change`, cancelable: `order` is every item's `data-key` in the new order. */
|
|
27
|
+
export interface FdySortChangeDetail { key: string; from: number; to: number; order: string[] }
|
|
26
28
|
export interface FdyCflSelectDetail { row?: unknown; rows?: unknown[] }
|
|
27
29
|
export interface FdyTableChangeDetail { page: number; sort: string | null; query: string }
|
|
28
30
|
|
|
@@ -7,6 +7,9 @@ import { computed, onMounted, useId, watch, type ComputedRef, type Ref, ref } fr
|
|
|
7
7
|
// dialogEl`, applied to a drawer that anchors left (default) or right. Native <dialog> supplies the
|
|
8
8
|
// focus trap, focus restore, top-layer stacking and inert background; `dismissible` (default true)
|
|
9
9
|
// gates Esc + backdrop dismissal.
|
|
10
|
+
// `data-fdy-ignore` on the root: this component owns the behaviour, so a page-wide useFreeday() must
|
|
11
|
+
// not hand `.fdy-drawer` to the enhancer as well. Its backdrop handler calls close() past
|
|
12
|
+
// `dismissible` and leaves `open` true on a dialog that is already closed.
|
|
10
13
|
|
|
11
14
|
// dismissible MUST go through withDefaults: Vue's boolean-cast gives an omitted Boolean prop
|
|
12
15
|
// `false`, not `undefined`, so a bare `props.dismissible !== false` would make an un-annotated
|
|
@@ -53,6 +56,7 @@ function onClick(e: MouseEvent): void {
|
|
|
53
56
|
<dialog
|
|
54
57
|
ref="dialogEl"
|
|
55
58
|
:class="drawerClass"
|
|
59
|
+
data-fdy-ignore
|
|
56
60
|
:aria-labelledby="titleId"
|
|
57
61
|
@cancel.prevent="onCancel"
|
|
58
62
|
@click="onClick"
|
package/adapters/vue/index.d.ts
CHANGED
|
@@ -93,5 +93,7 @@ export interface FdyMaskDetail { value: string; raw: string }
|
|
|
93
93
|
export interface FdyFormInvalidDetail { invalid: HTMLElement[] }
|
|
94
94
|
export interface FdyChipChangeDetail { value: string; pressed: boolean; selected: string[] }
|
|
95
95
|
export interface FdyChipRemoveDetail { value: string }
|
|
96
|
+
/** `fdy-sort-change`, cancelable: `order` is every item's `data-key` in the new order. */
|
|
97
|
+
export interface FdySortChangeDetail { key: string; from: number; to: number; order: string[] }
|
|
96
98
|
export interface FdyCflSelectDetail { row?: unknown; rows?: unknown[] }
|
|
97
99
|
export interface FdyTableChangeDetail { page: number; sort: string | null; query: string }
|
|
@@ -18,6 +18,7 @@
|
|
|
18
18
|
|
|
19
19
|
function initAutocomplete(root) {
|
|
20
20
|
if (root.dataset.fdyAcReady === '1') return;
|
|
21
|
+
if (root.closest('[data-fdy-ignore]')) return;
|
|
21
22
|
root.dataset.fdyAcReady = '1';
|
|
22
23
|
|
|
23
24
|
var input = root.querySelector('input[role="combobox"]') || root.querySelector('input');
|
|
@@ -26,10 +26,19 @@
|
|
|
26
26
|
if (bp === last) return;
|
|
27
27
|
last = bp;
|
|
28
28
|
root.setAttribute('data-breakpoint', bp);
|
|
29
|
-
|
|
29
|
+
fillLabels(document);
|
|
30
|
+
root.dispatchEvent(new CustomEvent('fdy-breakpoint-change', { bubbles: true, detail: { breakpoint: bp } }));
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/* Also run over late-mounted markup by the stack helpers, which find it through initAll: a label
|
|
34
|
+
rendered after load otherwise stayed empty until the next breakpoint change. */
|
|
35
|
+
function fillLabels(context) {
|
|
36
|
+
var ctx = context || document;
|
|
37
|
+
var bp = last || current();
|
|
38
|
+
if (ctx.matches && ctx.matches('[data-fdy-breakpoint-label]')) ctx.textContent = bp;
|
|
39
|
+
Array.prototype.forEach.call(ctx.querySelectorAll('[data-fdy-breakpoint-label]'), function (el) {
|
|
30
40
|
el.textContent = bp;
|
|
31
41
|
});
|
|
32
|
-
root.dispatchEvent(new CustomEvent('fdy-breakpoint-change', { bubbles: true, detail: { breakpoint: bp } }));
|
|
33
42
|
}
|
|
34
43
|
|
|
35
44
|
window.addEventListener('resize', update, { passive: true });
|
|
@@ -40,6 +49,7 @@
|
|
|
40
49
|
}
|
|
41
50
|
|
|
42
51
|
window.FreedayBreakpoint = {
|
|
52
|
+
initAll: fillLabels,
|
|
43
53
|
get: function () { return last || current(); },
|
|
44
54
|
current: current,
|
|
45
55
|
// true if the current breakpoint is `name` or wider (e.g. is('md') → md, lg, or xl)
|
package/dist/freeday-carousel.js
CHANGED
package/dist/freeday-cascade.js
CHANGED
package/dist/freeday-cfl.js
CHANGED
|
@@ -207,6 +207,7 @@
|
|
|
207
207
|
|
|
208
208
|
function bindGroup(group) {
|
|
209
209
|
if (group.dataset.fdyCflBound === '1') return;
|
|
210
|
+
if (group.closest('[data-fdy-ignore]')) return;
|
|
210
211
|
var dialog = document.getElementById(group.getAttribute('data-fdy-cfl'));
|
|
211
212
|
if (!dialog) return;
|
|
212
213
|
initDialog(dialog);
|
|
@@ -218,6 +219,7 @@
|
|
|
218
219
|
|
|
219
220
|
function bindOpener(opener) {
|
|
220
221
|
if (opener.dataset.fdyCflBound === '1') return;
|
|
222
|
+
if (opener.closest('[data-fdy-ignore]')) return;
|
|
221
223
|
var dialog = document.getElementById(opener.getAttribute('data-fdy-cfl-open'));
|
|
222
224
|
if (!dialog) return;
|
|
223
225
|
initDialog(dialog);
|
|
@@ -240,5 +242,7 @@
|
|
|
240
242
|
initTriggers();
|
|
241
243
|
}
|
|
242
244
|
|
|
243
|
-
|
|
245
|
+
/* initAll is what every stack helper looks for (useFreeday in Vue and React, FreedayBlazor.initAll):
|
|
246
|
+
without it they skipped this enhancer, and raw CFL markup rendered by a framework never opened. */
|
|
247
|
+
window.FreedayCfl = { init: initTriggers, initAll: initTriggers };
|
|
244
248
|
})();
|
package/dist/freeday-chart.js
CHANGED
|
@@ -489,6 +489,7 @@
|
|
|
489
489
|
// Auto-init renders once; explicit update() re-renders after data changes.
|
|
490
490
|
function initChart(el) {
|
|
491
491
|
if (el.dataset.fdyChartReady === '1') return;
|
|
492
|
+
if (el.closest('[data-fdy-ignore]')) return;
|
|
492
493
|
el.dataset.fdyChartReady = '1';
|
|
493
494
|
renderChart(el);
|
|
494
495
|
}
|
package/dist/freeday-chip.js
CHANGED
|
@@ -1,8 +1,10 @@
|
|
|
1
1
|
/* Freeday, chip enhancer (optional, zero-dependency).
|
|
2
2
|
* Two behaviours, both progressive enhancement:
|
|
3
3
|
*
|
|
4
|
-
* 1. Removable chips, any .fdy-chip__remove button
|
|
5
|
-
*
|
|
4
|
+
* 1. Removable chips, any .fdy-chip__remove button emits a bubbling, CANCELABLE
|
|
5
|
+
* "fdy-chip-remove" (detail {value}) and then removes its chip, unless a listener called
|
|
6
|
+
* preventDefault(). Cancel it whenever the app owns the removal: a confirm step, or a chip
|
|
7
|
+
* rendered from framework state, which should leave the DOM when the state does.
|
|
6
8
|
* 2. Choice / filter groups, a [data-fdy-chips] container of interactive chips
|
|
7
9
|
* (.fdy-chip--choice / .fdy-chip--filter, each a <button>) toggles aria-pressed
|
|
8
10
|
* on click. Add data-single for one-at-a-time (radio-like) selection; filter
|
|
@@ -16,6 +18,7 @@
|
|
|
16
18
|
|
|
17
19
|
function initRemove(btn) {
|
|
18
20
|
if (btn.dataset.fdyChipRmReady === '1') return;
|
|
21
|
+
if (btn.closest('[data-fdy-ignore]')) return;
|
|
19
22
|
btn.dataset.fdyChipRmReady = '1';
|
|
20
23
|
btn.addEventListener('click', function () {
|
|
21
24
|
var chip = btn.closest('.fdy-chip');
|
|
@@ -28,13 +31,18 @@
|
|
|
28
31
|
if (rm) rm.remove();
|
|
29
32
|
value = (clone.textContent || '').trim();
|
|
30
33
|
}
|
|
31
|
-
|
|
32
|
-
|
|
34
|
+
/* Cancelable, because the kit cannot know whether this removal needs asking first. Removing
|
|
35
|
+
unconditionally made a chip vanish while the app's own confirm dialog was still open, and
|
|
36
|
+
stay gone after Cancel, with the data intact and the screen wrong (CATATAN-FREEDAY §9). */
|
|
37
|
+
var ev = new CustomEvent('fdy-chip-remove', { bubbles: true, cancelable: true, detail: { value: value } });
|
|
38
|
+
chip.dispatchEvent(ev);
|
|
39
|
+
if (!ev.defaultPrevented) chip.remove();
|
|
33
40
|
});
|
|
34
41
|
}
|
|
35
42
|
|
|
36
43
|
function initGroup(group) {
|
|
37
44
|
if (group.dataset.fdyChipsReady === '1') return;
|
|
45
|
+
if (group.closest('[data-fdy-ignore]')) return;
|
|
38
46
|
group.dataset.fdyChipsReady = '1';
|
|
39
47
|
var single = group.hasAttribute('data-single');
|
|
40
48
|
if (!group.getAttribute('role')) group.setAttribute('role', 'group');
|
|
@@ -118,6 +118,7 @@
|
|
|
118
118
|
|
|
119
119
|
function initPicker(wrap) {
|
|
120
120
|
if (wrap.dataset.fdyDpReady === '1') return wrap._fdyDp || null;
|
|
121
|
+
if (wrap.closest('[data-fdy-ignore]')) return null;
|
|
121
122
|
wrap.dataset.fdyDpReady = '1';
|
|
122
123
|
wrap.classList.add('fdy-datepicker');
|
|
123
124
|
|
|
@@ -647,6 +648,7 @@
|
|
|
647
648
|
|
|
648
649
|
function initRange(root) {
|
|
649
650
|
if (root.dataset.fdyDrReady === '1') return;
|
|
651
|
+
if (root.closest('[data-fdy-ignore]')) return;
|
|
650
652
|
root.dataset.fdyDrReady = '1';
|
|
651
653
|
var fromEl = root.querySelector('[data-fdy-datepicker][data-role="from"]');
|
|
652
654
|
var toEl = root.querySelector('[data-fdy-datepicker][data-role="to"]');
|
package/dist/freeday-datetime.js
CHANGED
package/dist/freeday-drawer.js
CHANGED
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
|
|
9
9
|
function initDrawer(dialog) {
|
|
10
10
|
if (dialog.dataset.fdyDrawerReady === '1') return;
|
|
11
|
+
if (dialog.closest('[data-fdy-ignore]')) return;
|
|
11
12
|
dialog.dataset.fdyDrawerReady = '1';
|
|
12
13
|
// Click on the backdrop (target is the dialog box itself) closes it.
|
|
13
14
|
dialog.addEventListener('click', function (e) { if (e.target === dialog) dialog.close(); });
|
|
@@ -18,6 +19,7 @@
|
|
|
18
19
|
|
|
19
20
|
function bindTrigger(btn) {
|
|
20
21
|
if (btn.dataset.fdyDrawerBound === '1') return;
|
|
22
|
+
if (btn.closest('[data-fdy-ignore]')) return;
|
|
21
23
|
var dialog = document.getElementById(btn.getAttribute('data-fdy-drawer'));
|
|
22
24
|
if (!dialog) return;
|
|
23
25
|
initDrawer(dialog);
|
package/dist/freeday-form.js
CHANGED
|
@@ -186,6 +186,7 @@
|
|
|
186
186
|
|
|
187
187
|
function initForm(form) {
|
|
188
188
|
if (form.dataset.fdyFormReady === '1') return;
|
|
189
|
+
if (form.closest('[data-fdy-ignore]')) return;
|
|
189
190
|
form.dataset.fdyFormReady = '1';
|
|
190
191
|
form.setAttribute('novalidate', '');
|
|
191
192
|
var eager = form.hasAttribute('data-fdy-eager');
|
package/dist/freeday-mask.js
CHANGED
|
@@ -79,6 +79,7 @@
|
|
|
79
79
|
|
|
80
80
|
function initMask(el) {
|
|
81
81
|
if (el.dataset.fdyMaskReady === '1') return;
|
|
82
|
+
if (el.closest('[data-fdy-ignore]')) return;
|
|
82
83
|
el.dataset.fdyMaskReady = '1';
|
|
83
84
|
var pattern = el.getAttribute('data-fdy-mask') || '';
|
|
84
85
|
if (!pattern) return;
|
|
@@ -101,6 +102,7 @@
|
|
|
101
102
|
|
|
102
103
|
function initReveal(input) {
|
|
103
104
|
if (input.dataset.fdyPwReady === '1') return;
|
|
105
|
+
if (input.closest('[data-fdy-ignore]')) return;
|
|
104
106
|
input.dataset.fdyPwReady = '1';
|
|
105
107
|
|
|
106
108
|
var group = document.createElement('span');
|
package/dist/freeday-menu.js
CHANGED
|
@@ -19,6 +19,7 @@
|
|
|
19
19
|
|
|
20
20
|
function initMenu(wrap) {
|
|
21
21
|
if (wrap.dataset.fdyMenuReady === '1') return;
|
|
22
|
+
if (wrap.closest('[data-fdy-ignore]')) return;
|
|
22
23
|
wrap.dataset.fdyMenuReady = '1';
|
|
23
24
|
var trigger = wrap.querySelector('[aria-haspopup="menu"]');
|
|
24
25
|
var menu = wrap.querySelector('.fdy-menu, [role="menu"]');
|
package/dist/freeday-number.js
CHANGED
|
@@ -27,6 +27,7 @@
|
|
|
27
27
|
|
|
28
28
|
function initNumber(root) {
|
|
29
29
|
if (root.dataset.fdyNumberReady === '1') return;
|
|
30
|
+
if (root.closest('[data-fdy-ignore]')) return;
|
|
30
31
|
|
|
31
32
|
var input = root.querySelector('input[type="number"]');
|
|
32
33
|
var buttons = Array.prototype.slice.call(root.querySelectorAll('[data-fdy-number-step]'));
|
package/dist/freeday-rating.js
CHANGED