@kashi-ui/elements 0.0.0-stage → 0.25.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/README.md +45 -2
- package/dist/base.d.ts +47 -0
- package/dist/base.js +148 -0
- package/dist/calendar.d.ts +86 -0
- package/dist/calendar.js +439 -0
- package/dist/cdn/base-Cmq7zeIG.js +1 -0
- package/dist/cdn/calendar-Dm3fq2bs.js +16 -0
- package/dist/cdn/charts-DNOWi4sJ.js +1 -0
- package/dist/cdn/combobox-ZGrZ5okg.js +1 -0
- package/dist/cdn/controls-K-OZcjg4.js +1 -0
- package/dist/cdn/digits-DE1YGT94.js +1 -0
- package/dist/cdn/display-C975tS7j.js +1 -0
- package/dist/cdn/dist-D670Gw0K.js +1 -0
- package/dist/cdn/fields-BUTaSN8m.js +1 -0
- package/dist/cdn/forms-C-effPKn.js +1 -0
- package/dist/cdn/inputs-BjOddAM7.js +1 -0
- package/dist/cdn/jalali-BiM5Kfep.js +1 -0
- package/dist/cdn/kashi-elements.js +1 -0
- package/dist/cdn/map-BHuusa4t.js +12 -0
- package/dist/cdn/menu-DhrqyLgy.js +1 -0
- package/dist/cdn/nav-D_w5BV_K.js +1 -0
- package/dist/cdn/overlay-DX9un2xm.js +1 -0
- package/dist/cdn/pickers-BFLpUruK.js +1 -0
- package/dist/cdn/table-DPQfDMs-.js +1 -0
- package/dist/cdn/text-D1U32D6K.js +1 -0
- package/dist/cdn/words-9OdzG7y6.js +1 -0
- package/dist/cdn.d.ts +3 -0
- package/dist/cdn.js +44 -0
- package/dist/charts.d.ts +106 -0
- package/dist/charts.js +436 -0
- package/dist/combobox.d.ts +106 -0
- package/dist/combobox.js +439 -0
- package/dist/controls.d.ts +82 -0
- package/dist/controls.js +425 -0
- package/dist/display.d.ts +41 -0
- package/dist/display.js +144 -0
- package/dist/fields.d.ts +24 -0
- package/dist/fields.js +103 -0
- package/dist/forms.d.ts +186 -0
- package/dist/forms.js +902 -0
- package/dist/index.d.ts +86 -0
- package/dist/index.js +32 -0
- package/dist/inputs.d.ts +107 -0
- package/dist/inputs.js +371 -0
- package/dist/iranMapData.d.ts +6 -0
- package/dist/iranMapData.js +37 -0
- package/dist/map.d.ts +64 -0
- package/dist/map.js +416 -0
- package/dist/menu.d.ts +45 -0
- package/dist/menu.js +281 -0
- package/dist/nav.d.ts +163 -0
- package/dist/nav.js +918 -0
- package/dist/overlay.d.ts +79 -0
- package/dist/overlay.js +420 -0
- package/dist/pickers.d.ts +108 -0
- package/dist/pickers.js +655 -0
- package/dist/table.d.ts +53 -0
- package/dist/table.js +267 -0
- package/dist/toast.d.ts +45 -0
- package/dist/toast.js +141 -0
- package/package.json +63 -4
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
// مرز ۳۱ استان ایران برای IranMap — این فایل خودکار ساخته شده است.
|
|
2
|
+
// منبع: Natural Earth (۱:۱۰ میلیون، مالکیت عمومی / public domain)، سادهشده با mapshaper و تصویر مرکاتور.
|
|
3
|
+
// کلید هر استان همان نام فارسی PROVINCES در @kashi-ui/persian است؛ x و y نقطهٔ درونی برای راهنما.
|
|
4
|
+
export const IRAN_VIEWBOX = "0 0 1000 907";
|
|
5
|
+
export const IRAN_PROVINCES = {
|
|
6
|
+
"آذربایجان شرقی": { x: 123, y: 128, d: "M163 199l1-7l10-12l11-8l17-2l20 2l7-4l-13-8l-2-7l-12-7l-1-7l2-10l-8-10l-5-17l-15 0l-10-6l10-13l7 0l2-16l-6-22l-13 8l-12 19l-8-2l-10 4l-5-5l5-9l5 1l12-6l6-7l-4-9l-8 1l-15 18l-10-1l-13 4l-33-8l-6 6l-3 10l0 14l-9 9l-3 10l5 7l4 34l4 7l2 15l16 10l12 1l8 8l11 7l5-7l13-5l8 5l2 13l7 3z" },
|
|
7
|
+
"آذربایجان غربی": { x: 39, y: 59, d: "M75 53l-8-13l-9-3l-6-11l-5-4l-4-11l-17-11l-5 5l-3 17l-7 4l-11-1l1 13l6 4l-3 10l7 10l-1 8l2 7l0 15l7 1l-5 18l-6 9l0 6l8 1l4 6l8 3l-2 18l13 10l-3 12l7 5l-3 16l9 3l2 6l-3 7l7 9l6 0l6 20l1 7l7-2l12-15l8-3l4-8l4-2l13 2l27-3l6 6l11 2l10-11l-7-16l-12 1l-7-3l-2-13l-8-5l-13 5l-5 7l-11-7l-8-8l-12-1l-16-10l-2-15l-4-7l-4-34l-5-7l3-10l9-9l0-14l3-10z" },
|
|
8
|
+
"اردبیل": { x: 202, y: 87, d: "M229 168l7 5l3-4l12 1l-1-10l-8-8l-8-13l-5-13l3-13l12-14l-7-7l-9-12l-7-2l-5-9l-10-6l2-8l10-2l3-5l-8-9l-1-8l11-5l-15-18l-11-3l-29 21l-10 5l-4 8l4 9l-6 7l-12 6l-5-1l-5 9l5 5l10-4l8 2l12-19l13-8l6 22l-2 16l-7 0l-10 13l10 6l15 0l5 17l8 10l-2 10l1 7l12 7l2 7z" },
|
|
9
|
+
"اصفهان": { x: 414, y: 418, d: "M296 467l10-6l9-1l6 4l10 0l6-4l15-2l6 10l1 10l15 12l4 11l-4 7l-1 18l5 16l0 7l3 11l14 12l5-1l0-11l7-21l-9-7l6-6l17-11l4 10l16 2l18-5l-3-9l5-25l-2-19l15-11l9-2l16 4l55-19l9-6l6-19l3-4l12-5l6-12l-1-42l-4-3l-125 4l-25-8l-23 0l-10-6l-17 5l-15 1l-8 6l-2 12l3 3l-7 19l-12 5l-22 6l-13 8l-1 9l-7 14l-8 2l-4 11l-8 7l2 6l13 3z" },
|
|
10
|
+
"البرز": { x: 353, y: 249, d: "M351 227l-12-1l-8 2l11 9l-5 13l-12 7l-3 7l2 5l16 1l11 3l13-13l4-11l12-3l0-6l-3-4l-14-6z" },
|
|
11
|
+
"ایلام": { x: 143, y: 429, d: "M87 397l8 0l8 16l6 7l1 6l-4 13l9 0l11 4l12 8l21 18l12 1l3 7l9 14l9-7l-1-7l9-16l-10-20l-13-15l-11-5l-22-20l7-9l18-5l6-6l-2-9l-11 1l1 12l-24 1l-13-4l-7-5l-16-5l-11 1z" },
|
|
12
|
+
"بوشهر": { x: 387, y: 698, d: "M312 606l4 5l1 11l5 5l8 12l13 12l0 19l10 0l4 4l-5 9l3 5l9 6l1 10l4 10l6 7l0 7l6 10l11 8l7 1l15 0l12 9l9 2l8 6l2 11l4 2l2-3l13-1l-10-7l-14-15l-7-16l-9-8l-9-27l-24-44l-8-6l-14-19l-21-5l-6-9l-1-7l-9-4l-11-2z" },
|
|
13
|
+
"تهران": { x: 384, y: 274, d: "M380 240l0 6l-12 3l-4 11l-13 13l4 10l-5 14l15 1l13 3l29 18l5-16l-8-12l2-15l6 1l13 8l24 5l11-5l8-7l2-6l-3-14l-11-2l-22-7l-11 12l-12-1l-10-13l-15-4z" },
|
|
14
|
+
"چهارمحال و بختیاری": { x: 346, y: 499, d: "M323 529l12 6l5 0l19 17l8 1l11-4l0-7l-5-16l1-18l4-7l-4-11l-15-12l-1-10l-6-10l-15 2l-6 4l-10 0l-6-4l-9 1l-10 6l1 5l9 17l6 4l6 14l8 9l1 6z" },
|
|
15
|
+
"خراسان جنوبی": { x: 802, y: 473, d: "M734 452l-3 11l7 13l-3 13l-7 9l-11 22l59 27l8 5l21 30l40-12l18 10l12 15l10-4l-3-12l1-20l6-17l0-11l-16-2l-3-33l3-14l-13-45l0-10l13-16l3-9l-12 0l-7-5l0-13l-2-15l-36 1l-7-3l-8-10l-10 4l-16 3l-2 2l-14-2l-3 22l-2 6l4 8l8 6l-7 11l-16 11l-7 11z" },
|
|
16
|
+
"خراسان رضوی": { x: 784, y: 272, d: "M657 206l6 6l-4 10l0 19l4 12l15 14l0 4l-13 22l-11 4l-13 10l-8 10l21-5l21-10l13-4l6 2l15 12l1 8l-5 5l-21 14l-3 6l-7 20l0 11l3 18l2 4l11 1l13-3l4 7l4 26l3 7l14 8l6 8l5-13l7-11l16-11l7-11l-8-6l-4-8l2-6l3-22l14 2l2-2l16-3l10-4l8 10l7 3l36-1l2-7l7-7l12-1l-9-14l12-6l6-11l3-16l0-13l9-18l-3-7l1-14l-4-8l3-7l-4-19l2-11l-6-4l-38 1l-17-26l-27-10l-7-9l-1-11l-7-2l-9-6l-9-4l-8 2l-10-3l-8 4l-8-3l-2-7l-23-8l-8 6l0 9l24 1l7 11l-1 9l-7 21l11 9l-4 5l1 9l-5 3l-15-2l-34-20l-9 0l-12 10z" },
|
|
17
|
+
"خراسان شمالی": { x: 674, y: 152, d: "M712 124l-20-4l0-8l-7-12l-9 5l-16-5l-8 2l-8-1l-14 11l0 21l7 5l-2 8l-15 6l-5 8l12 16l-2 15l13 14l11 3l8-2l3-11l12-10l9 0l34 20l15 2l5-3l-1-9l4-5l-11-9l7-21l1-9l-7-11l-24-1l0-9z" },
|
|
18
|
+
"خوزستان": { x: 253, y: 524, d: "M183 491l13 21l-8 22l0 25l18 1l0 31l7 2l13 12l3 14l8 2l1-5l13 1l3-3l-1-10l-3-6l6-10l10 0l-9 12l13 9l12 0l6 8l17-11l7 0l9-2l11 2l-4-19l2-10l-8-5l-6-7l-9 2l0-9l-2-9l2-7l6-3l10-10l4-7l-1-6l-8-9l-6-14l-6-4l-9-17l-1-5l0-10l-13-3l-2-6l-11 0l-12-8l-12-1l-11-5l-22 2l-3 2l-10 23l-9 16l1 7z" },
|
|
19
|
+
"زنجان": { x: 228, y: 211, d: "M170 215l2 1l26 6l4 7l1 15l-3 11l14 8l3 4l4 5l11 0l9 4l6-5l-11-12l10-5l13-3l9-6l9-3l0-8l-4-11l-8-3l-6-11l1-9l10-5l-3-11l-8-9l-8-5l-12-1l-3 4l-7-5l-7 4l-20-2l-17 2l-11 8l-10 12l-1 7z" },
|
|
20
|
+
"سمنان": { x: 554, y: 286, d: "M615 160l-12 17l-10 22l-18-3l-14 6l-12 11l-7 3l-18 0l-10 4l-6 8l-2 9l-10 12l-6 4l-8 1l-15 4l3 14l-2 6l-8 7l-11 5l-24-5l-13-8l-6-1l-2 15l8 12l-5 16l1 8l-6 13l10 6l23 0l25 8l125-4l4 3l19-1l6-3l19-32l8-10l13-10l11-4l13-22l0-4l-15-14l-4-12l0-19l4-10l-6-6l-8 2l-11-3l-13-14l2-15z" },
|
|
21
|
+
"سیستان و بلوچستان": { x: 863, y: 770, d: "M805 582l-11 50l0 5l5 8l2 12l-2 11l-4 7l0 13l2 7l-16 11l-9 3l8 10l-7 13l-1 27l-6 23l3 21l6 10l-3 7l0 9l3 8l-4 16l-2 4l13 11l9 14l0 4l11-2l4 4l12 0l7 4l9-2l7 2l8 0l3-5l7-2l4 10l21 4l8 5l12 3l4-8l6-5l2-27l6-4l2-19l3-5l20-6l2-9l7-3l9-1l8-4l21 1l2-12l4-3l-2-10l1-9l-4-3l-13 3l-6-1l-2-7l3-8l-2-20l-3-10l2-12l-10-1l-11-12l-16-3l-8-4l-13-12l-4-7l-5-13l-7-10l-3-9l-23-27l49-58l2-13l-4-16l-5-5l-27-4l0 11l-6 17l-1 20l3 12l-10 4l-12-15l-18-10z" },
|
|
22
|
+
"فارس": { x: 473, y: 666, d: "M464 773l5 7l12 1l8 5l5-1l16 2l5-2l3-13l8-5l27-2l14 2l9-5l4-8l17-6l2-5l-7-8l2-14l0-10l-16-15l1-6l-3-9l-10-26l-17-4l-9-20l-19-11l-3-17l-11-14l-8-16l-12-30l-15-16l-13-5l-18 5l-16-2l-4-10l-17 11l-6 6l9 7l-7 21l0 11l-5 1l0 13l-6 2l-16-7l-5-1l4 16l-1 6l-14 8l-16 1l1 7l6 9l21 5l14 19l8 6l24 44l9 27l9 8l7 16l14 15z" },
|
|
23
|
+
"قزوین": { x: 304, y: 239, d: "M270 195l-10 5l-1 9l6 11l8 3l4 11l0 8l-9 3l-9 6l-13 3l-10 5l11 12l8-1l8 10l17 3l9 0l4-5l31-9l-2-5l3-7l12-7l5-13l-11-9l8-2l12 1l-1-3l-25-20l-11 1l-15 6l-17-4z" },
|
|
24
|
+
"قم": { x: 368, y: 323, d: "M407 319l-29-18l-13-3l-15-1l-3 7l-2 13l-28 8l1 7l-6 6l13 9l1 7l6 6l14 1l17 6l-3-3l2-12l8-6l15-1l17-5l6-13z" },
|
|
25
|
+
"کردستان": { x: 152, y: 265, d: "M75 247l16 13l13-3l9 9l-10 1l-4 13l8 13l12 8l12 17l5 9l14-1l4-8l12-5l1-5l7-1l1-5l11 3l8 9l3 0l13-1l3-8l-1-6l-8-7l-9-18l8 1l14-8l-3-4l-14-8l3-11l-1-15l-4-7l-26-6l-2-1l-10 11l-11-2l-6-6l-27 3l-13-2l-4 2l-4 8l-8 3z" },
|
|
26
|
+
"کرمان": { x: 697, y: 622, d: "M717 520l-56-24l-6-1l-4 4l-14 10l-28 15l-2 4l-2 24l-9 4l-9 1l-11-1l-30 5l-7 10l-1 7l11 23l-1 19l2 8l-10 3l9 20l17 4l10 26l14 3l7 7l7 2l11-8l9-1l1 33l4 6l10 7l6 1l10-4l10-9l8 3l2 16l6 4l8 11l-2 6l5 10l3 25l21 11l9-5l11 9l-3 3l-4 30l16-1l7 2l5 8l7-2l7 5l4-16l-3-8l0-9l3-7l-6-10l-3-21l6-23l1-27l7-13l-8-10l9-3l16-11l-2-7l0-13l4-7l2-11l-2-12l-5-8l0-5l11-50l-21-30l-8-5z" },
|
|
27
|
+
"کرمانشاه": { x: 139, y: 357, d: "M107 293l3 6l-9 8l-7 3l-2 8l-8 5l-2 6l3 11l-10-3l-3 14l6 4l-1 11l-6 8l12 20l4 3l5-24l11-1l16 5l7 5l13 4l24-1l-1-12l11-1l1-8l9-3l0-8l6-1l3-4l13-1l0-7l-19-6l11-20l-3 0l-8-9l-11-3l-1 5l-7 1l-1 5l-12 5l-4 8l-14 1l-5-9l-12-17z" },
|
|
28
|
+
"کهگیلویه و بویراحمد": { x: 348, y: 570, d: "M332 606l9 4l16-1l14-8l1-6l-4-16l5 1l16 7l6-2l0-13l-14-12l-3-11l-11 4l-8-1l-19-17l-5 0l-12-6l-10 10l-6 3l-2 7l2 9l0 9l9-2l6 7l8 5l-2 10z" },
|
|
29
|
+
"گلستان": { x: 577, y: 168, d: "M630 112l-9 1l-14-3l-15 3l-16 8l-14 12l-3 8l-1 8l-8 6l-23 7l-14-1l6 25l-1 9l-16 0l3 6l11 6l8 9l18 0l7-3l12-11l14-6l18 3l10-22l12-17l5-8l15-6l2-8l-7-5z" },
|
|
30
|
+
"گیلان": { x: 295, y: 181, d: "M251 170l8 5l8 9l3 11l12 12l17 4l15-6l11-1l7-12l7-8l-13-11l-9-16l-11-4l-26-2l-16-9l-6-7l-6-23l-1-23l-14 3l7 7l-12 14l-3 13l5 13l8 13l8 8z" },
|
|
31
|
+
"لرستان": { x: 221, y: 403, d: "M173 372l2 9l-6 6l-18 5l-7 9l22 20l11 5l13 15l10 20l10-23l3-2l22-2l11 5l12 1l12 8l11 0l8-7l4-11l8-2l7-14l1-9l-9-10l-4 6l-9-8l1-6l-7-6l-7 4l-7 9l-14-4l3-15l-15-6l-10 3l-15-2l-27-18l-6 1l0 8l-9 3z" },
|
|
32
|
+
"مازندران": { x: 467, y: 227, d: "M325 204l25 20l1 3l12 3l14 6l3 4l6 3l15 4l10 13l12 1l11-12l22 7l11 2l15-4l8-1l6-4l10-12l2-9l6-8l10-4l-8-9l-11-6l-3-6l-2-4l-9-1l-20 5l-17 5l-45 10l-43-10l-27-16l-7 8z" },
|
|
33
|
+
"مرکزی": { x: 294, y: 357, d: "M280 283l2 8l-8 0l4 11l-7 7l11 4l5 13l-8-2l-1-7l-14 0l-2 10l0 9l-7 2l1 11l4 7l2 11l-6 8l-3 15l14 4l7-9l7-4l7 6l-1 6l9 8l4-6l9 10l13-8l22-6l12-5l7-19l-17-6l-14-1l-6-6l-1-7l-13-9l6-6l-1-7l28-8l2-13l3-7l5-14l-4-10l-11-3l-16-1l-31 9l-4 5z" },
|
|
34
|
+
"هرمزگان": { x: 651, y: 758, d: "M771 853l-7-5l-7 2l-5-8l-7-2l-16 1l4-30l3-3l-11-9l-9 5l-21-11l-3-25l-5-10l2-6l-8-11l-6-4l-2-16l-8-3l-10 9l-10 4l-6-1l-10-7l-4-6l-1-33l-9 1l-11 8l-7-2l-7-7l-14-3l3 9l-1 6l16 15l0 10l-2 14l7 8l-2 5l-17 6l-4 8l-9 5l-14-2l-27 2l-8 5l-3 13l-5 2l-16-2l-5 1l-8-5l-12-1l-5-7l-13 1l-2 3l20 13l18 6l4 8l12 8l14-2l17 2l4 6l9 2l3 4l9 1l25-17l6 1l8-2l3-9l4-3l14-1l9-8l12-2l12 3l12 0l8 10l6 21l0 10l3 10l4 6l-3 4l9 18l23 3l1 5l9-3l6 7l24-1l14 1l10 9l6 1l7-2l0-4l-9-14l-13-11zM633 795l-9 2l-13 8l-3 3l-20 8l8 3l10-6l9-3l4 3l7-5z" },
|
|
35
|
+
"همدان": { x: 235, y: 319, d: "M197 314l-11 20l19 6l0 7l-13 1l-3 4l27 18l15 2l10-3l15 6l6-8l-2-11l-4-7l-1-11l7-2l0-9l2-10l14 0l1 7l8 2l-5-13l-11-4l7-7l-4-11l8 0l-2-8l-17-3l-8-10l-8 1l-6 5l-9-4l-11 0l-4-5l-14 8l-8-1l9 18l8 7l1 6l-3 8z" },
|
|
36
|
+
"یزد": { x: 615, y: 452, d: "M633 317l-19 32l-6 3l-19 1l1 42l-6 12l-12 5l-3 4l-6 19l-9 6l-55 19l-16-4l-9 2l-15 11l2 19l-5 25l3 9l13 5l15 16l12 30l8 16l11 14l3 17l19 11l10-3l-2-8l1-19l-11-23l1-7l7-10l30-5l11 1l9-1l9-4l2-24l2-4l28-15l14-10l4-4l6 1l56 24l11-22l7-9l3-13l-7-13l3-11l-6-8l-14-8l-3-7l-4-26l-4-7l-13 3l-11-1l-2-4l-3-18l0-11l7-20l3-6l21-14l5-5l-1-8l-15-12l-6-2l-13 4l-21 10z" },
|
|
37
|
+
};
|
package/dist/map.d.ts
ADDED
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { type IranAddress } from "@kashi-ui/persian";
|
|
2
|
+
import { HTMLBase } from "./base.js";
|
|
3
|
+
import "./combobox.js";
|
|
4
|
+
import "./inputs.js";
|
|
5
|
+
/**
|
|
6
|
+
* نقشهٔ ۳۱ استان ایران: نقشهٔ رنگی برای داده (ویژگی data) و/یا انتخاب یک یا چند استان،
|
|
7
|
+
* با صفحهکلید (فوکوس گردشی و جهتنماها) و جدول همارز برای صفحهخوان.
|
|
8
|
+
*/
|
|
9
|
+
export declare class KashiIranMap extends HTMLBase {
|
|
10
|
+
static observedAttributes: string[];
|
|
11
|
+
private values;
|
|
12
|
+
private selected;
|
|
13
|
+
private active;
|
|
14
|
+
private rendered;
|
|
15
|
+
private valueSet;
|
|
16
|
+
private key;
|
|
17
|
+
connectedCallback(): void;
|
|
18
|
+
attributeChangedCallback(name: string, old: string | null, next: string | null): void;
|
|
19
|
+
private parseData;
|
|
20
|
+
/** داده برای نقشهٔ رنگی: نام استان ← عدد */
|
|
21
|
+
get data(): Record<string, number> | null;
|
|
22
|
+
set data(d: Record<string, number> | null);
|
|
23
|
+
/** استان انتخابشده؛ در حالت multiple، نامها با «,» جدا میشوند */
|
|
24
|
+
get value(): string;
|
|
25
|
+
set value(v: string);
|
|
26
|
+
/** استانهای انتخابشده بهشکل آرایه */
|
|
27
|
+
get selectedProvinces(): string[];
|
|
28
|
+
private get multiple();
|
|
29
|
+
private get selectable();
|
|
30
|
+
private fmt;
|
|
31
|
+
private level;
|
|
32
|
+
private get steps();
|
|
33
|
+
private shade;
|
|
34
|
+
private describe;
|
|
35
|
+
private render;
|
|
36
|
+
private paint;
|
|
37
|
+
private toggle;
|
|
38
|
+
private onKey;
|
|
39
|
+
private tip;
|
|
40
|
+
}
|
|
41
|
+
type Field = keyof IranAddress;
|
|
42
|
+
/**
|
|
43
|
+
* فرم نشانی ایرانی: استان، شهرِ همان استان، نشانی، پلاک، واحد و کد پستی دهرقمی؛ با map نقشهٔ ایران برای انتخاب استان.
|
|
44
|
+
* با انتخاب شهر بدون استان، استان خودکار پر میشود و با عوض شدن استان، شهرِ نامربوط پاک میشود.
|
|
45
|
+
* با name="shipping" فیلدها بهشکل shipping[province]، shipping[city]، … در فرم HTML ارسال میشوند.
|
|
46
|
+
*/
|
|
47
|
+
export declare class KashiAddressForm extends HTMLBase {
|
|
48
|
+
static observedAttributes: string[];
|
|
49
|
+
private address;
|
|
50
|
+
private built;
|
|
51
|
+
private key;
|
|
52
|
+
connectedCallback(): void;
|
|
53
|
+
attributeChangedCallback(_n: string, old: string | null, next: string | null): void;
|
|
54
|
+
/** نشانی کامل؛ مثل { province: "اصفهان", city: "کاشان", street, plaque, unit, postalCode } */
|
|
55
|
+
get value(): IranAddress;
|
|
56
|
+
set value(v: Partial<IranAddress>);
|
|
57
|
+
/** خطای هر فیلد، مثلاً از اعتبارسنجی سرور: { plaque: "پلاک را بنویسید." } */
|
|
58
|
+
set errors(e: Partial<Record<Field, string>>);
|
|
59
|
+
private label;
|
|
60
|
+
private render;
|
|
61
|
+
private changed;
|
|
62
|
+
private fieldError;
|
|
63
|
+
}
|
|
64
|
+
export {};
|
package/dist/map.js
ADDED
|
@@ -0,0 +1,416 @@
|
|
|
1
|
+
import { EMPTY_ADDRESS, PROVINCES, formatNumber, getCities } from "@kashi-ui/persian";
|
|
2
|
+
import { HTMLBase, afterParse, bool, define, emit, esc, uid } from "./base.js";
|
|
3
|
+
import { IRAN_PROVINCES, IRAN_VIEWBOX } from "./iranMapData.js";
|
|
4
|
+
// فرم نشانی از این عنصرها ساخته شده؛ با import همین فایل بهتنهایی هم ثبت شوند
|
|
5
|
+
import "./combobox.js";
|
|
6
|
+
import "./inputs.js";
|
|
7
|
+
const NAMES = PROVINCES.map((p) => p.name);
|
|
8
|
+
const CAPITAL = Object.fromEntries(PROVINCES.map((p) => [p.name, p.capital]));
|
|
9
|
+
const [, , VW, VH] = IRAN_VIEWBOX.split(" ").map(Number);
|
|
10
|
+
/**
|
|
11
|
+
* نقشهٔ ۳۱ استان ایران: نقشهٔ رنگی برای داده (ویژگی data) و/یا انتخاب یک یا چند استان،
|
|
12
|
+
* با صفحهکلید (فوکوس گردشی و جهتنماها) و جدول همارز برای صفحهخوان.
|
|
13
|
+
*/
|
|
14
|
+
export class KashiIranMap extends HTMLBase {
|
|
15
|
+
constructor() {
|
|
16
|
+
super(...arguments);
|
|
17
|
+
this.values = null;
|
|
18
|
+
this.selected = [];
|
|
19
|
+
this.active = 0;
|
|
20
|
+
this.rendered = false;
|
|
21
|
+
this.valueSet = false;
|
|
22
|
+
this.key = uid("kashi-map");
|
|
23
|
+
}
|
|
24
|
+
connectedCallback() {
|
|
25
|
+
if (!this.rendered) {
|
|
26
|
+
if (!this.valueSet)
|
|
27
|
+
this.selected = (this.getAttribute("value") ?? "").split(/[,،]/).map((s) => s.trim()).filter((s) => NAMES.includes(s));
|
|
28
|
+
if (this.values === null)
|
|
29
|
+
this.values = this.parseData(this.getAttribute("data"));
|
|
30
|
+
}
|
|
31
|
+
this.render();
|
|
32
|
+
}
|
|
33
|
+
attributeChangedCallback(name, old, next) {
|
|
34
|
+
if (!this.rendered || old === next)
|
|
35
|
+
return;
|
|
36
|
+
if (name === "data")
|
|
37
|
+
this.values = this.parseData(next);
|
|
38
|
+
if (name === "value") {
|
|
39
|
+
this.value = next ?? "";
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
this.render();
|
|
43
|
+
}
|
|
44
|
+
parseData(text) {
|
|
45
|
+
if (!text)
|
|
46
|
+
return null;
|
|
47
|
+
try {
|
|
48
|
+
return JSON.parse(text);
|
|
49
|
+
}
|
|
50
|
+
catch {
|
|
51
|
+
return null;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
/** داده برای نقشهٔ رنگی: نام استان ← عدد */
|
|
55
|
+
get data() {
|
|
56
|
+
return this.values;
|
|
57
|
+
}
|
|
58
|
+
set data(d) {
|
|
59
|
+
this.values = d;
|
|
60
|
+
if (this.rendered)
|
|
61
|
+
this.render();
|
|
62
|
+
}
|
|
63
|
+
/** استان انتخابشده؛ در حالت multiple، نامها با «,» جدا میشوند */
|
|
64
|
+
get value() {
|
|
65
|
+
return this.selected.join(",");
|
|
66
|
+
}
|
|
67
|
+
set value(v) {
|
|
68
|
+
this.valueSet = true;
|
|
69
|
+
this.selected = String(v ?? "").split(/[,،]/).map((s) => s.trim()).filter((s) => NAMES.includes(s));
|
|
70
|
+
if (!this.multiple)
|
|
71
|
+
this.selected = this.selected.slice(0, 1);
|
|
72
|
+
if (this.rendered)
|
|
73
|
+
this.paint();
|
|
74
|
+
}
|
|
75
|
+
/** استانهای انتخابشده بهشکل آرایه */
|
|
76
|
+
get selectedProvinces() {
|
|
77
|
+
return [...this.selected];
|
|
78
|
+
}
|
|
79
|
+
get multiple() {
|
|
80
|
+
return bool(this, "multiple");
|
|
81
|
+
}
|
|
82
|
+
get selectable() {
|
|
83
|
+
return this.multiple || bool(this, "selectable") || this.hasAttribute("value") || this.hasAttribute("name");
|
|
84
|
+
}
|
|
85
|
+
fmt(n) {
|
|
86
|
+
return formatNumber(n);
|
|
87
|
+
}
|
|
88
|
+
level(n) {
|
|
89
|
+
const data = this.values;
|
|
90
|
+
const v = data?.[n];
|
|
91
|
+
if (typeof v !== "number" || !data)
|
|
92
|
+
return undefined;
|
|
93
|
+
const steps = this.steps;
|
|
94
|
+
const vals = NAMES.map((x) => data[x]).filter((x) => typeof x === "number");
|
|
95
|
+
const min = Math.min(...vals), max = Math.max(...vals);
|
|
96
|
+
if (max === min)
|
|
97
|
+
return steps;
|
|
98
|
+
// رتبهٔ اولین مقدار برابر، تا استانهای هممقدار یک رنگ بگیرند
|
|
99
|
+
if (this.getAttribute("scale") !== "linear") {
|
|
100
|
+
const sorted = [...vals].sort((a, b) => a - b);
|
|
101
|
+
return 1 + Math.round((sorted.indexOf(v) * (steps - 1)) / (sorted.length - 1));
|
|
102
|
+
}
|
|
103
|
+
return Math.min(steps, 1 + Math.floor(((v - min) / (max - min)) * steps));
|
|
104
|
+
}
|
|
105
|
+
get steps() {
|
|
106
|
+
return Number(this.getAttribute("steps")) || 5;
|
|
107
|
+
}
|
|
108
|
+
// شدت رنگ هر پله؛ کمرنگترین پله هم از خاکستری «بدون داده» جدا دیده شود
|
|
109
|
+
shade(l) {
|
|
110
|
+
return `${Math.round(12 + (88 * l) / this.steps)}%`;
|
|
111
|
+
}
|
|
112
|
+
describe(n) {
|
|
113
|
+
const v = this.values?.[n];
|
|
114
|
+
const unit = this.getAttribute("unit");
|
|
115
|
+
return typeof v === "number" ? `${n}: ${this.fmt(v)}${unit ? ` ${unit}` : ""}` : n;
|
|
116
|
+
}
|
|
117
|
+
render() {
|
|
118
|
+
const label = this.getAttribute("label") ?? "نقشهٔ استانهای ایران";
|
|
119
|
+
const sel = this.selectable;
|
|
120
|
+
const multi = this.multiple;
|
|
121
|
+
const data = this.values;
|
|
122
|
+
const unit = this.getAttribute("unit");
|
|
123
|
+
const paths = NAMES.map((n, i) => {
|
|
124
|
+
const l = this.level(n);
|
|
125
|
+
return `<path d="${IRAN_PROVINCES[n].d}" class="k-iran-map__province" data-i="${i}"${l ? ` data-l="${l}" style="--_p: ${this.shade(l)}"` : ""}${sel ? ` role="${multi ? "checkbox" : "radio"}" aria-label="${esc(this.describe(n))}"` : ""}></path>`;
|
|
126
|
+
}).join("");
|
|
127
|
+
const vals = data ? NAMES.map((n) => data[n]).filter((v) => typeof v === "number") : [];
|
|
128
|
+
const showLegend = this.hasAttribute("legend") ? bool(this, "legend") : !!data;
|
|
129
|
+
const legend = showLegend && vals.length
|
|
130
|
+
? `<figcaption class="k-iran-map__legend"><span>${this.fmt(Math.min(...vals))}</span><span class="k-iran-map__scale" aria-hidden="true">${Array.from({ length: this.steps }, (_, i) => `<i style="--_p: ${this.shade(i + 1)}"></i>`).join("")}</span><span>${this.fmt(Math.max(...vals))}${unit ? ` ${esc(unit)}` : ""}</span></figcaption>`
|
|
131
|
+
: "";
|
|
132
|
+
const table = data
|
|
133
|
+
? `<table class="k-sr-only"><caption>${esc(label)}</caption><tbody>${NAMES.filter((n) => typeof data[n] === "number").sort((a, b) => data[b] - data[a]).map((n) => `<tr><th scope="row">${esc(n)}</th><td>${this.fmt(data[n])}${unit ? ` ${esc(unit)}` : ""}</td></tr>`).join("")}</tbody></table>`
|
|
134
|
+
: "";
|
|
135
|
+
// نسبت ابعاد با aspect-ratio، نه padding درصدی: در چیدمان flex ستونی ارتفاع padding درصدی صفر حساب میشود
|
|
136
|
+
this.innerHTML = `<figure class="k-iran-map${sel ? " k-iran-map--selectable" : ""}"><div class="k-iran-map__canvas" style="block-size: auto; aspect-ratio: ${VW} / ${VH}"><svg viewBox="${IRAN_VIEWBOX}" class="k-iran-map__svg" role="${sel ? (multi ? "group" : "radiogroup") : "img"}" aria-label="${esc(sel ? label : `${label}${data ? "؛ جدول داده در ادامه" : ""}`)}">${paths}</svg><div class="k-chart__tip" aria-hidden="true" style="display: none"></div></div>${legend}${table}</figure>`;
|
|
137
|
+
const svg = this.querySelector("svg");
|
|
138
|
+
const fig = this.querySelector("figure");
|
|
139
|
+
svg.addEventListener("pointerover", (e) => {
|
|
140
|
+
const i = e.target.getAttribute?.("data-i");
|
|
141
|
+
if (i !== null && i !== undefined)
|
|
142
|
+
this.tip(Number(i));
|
|
143
|
+
});
|
|
144
|
+
fig.addEventListener("pointerleave", () => this.tip(null));
|
|
145
|
+
if (sel) {
|
|
146
|
+
svg.addEventListener("click", (e) => {
|
|
147
|
+
const i = e.target.getAttribute?.("data-i");
|
|
148
|
+
if (i === null || i === undefined)
|
|
149
|
+
return;
|
|
150
|
+
this.active = Number(i);
|
|
151
|
+
this.toggle(NAMES[this.active]);
|
|
152
|
+
});
|
|
153
|
+
svg.addEventListener("keydown", (e) => this.onKey(e));
|
|
154
|
+
svg.addEventListener("focusin", (e) => {
|
|
155
|
+
const i = e.target.getAttribute?.("data-i");
|
|
156
|
+
if (i !== null && i !== undefined) {
|
|
157
|
+
this.active = Number(i);
|
|
158
|
+
this.tip(this.active);
|
|
159
|
+
}
|
|
160
|
+
});
|
|
161
|
+
svg.addEventListener("focusout", () => this.tip(null));
|
|
162
|
+
}
|
|
163
|
+
this.rendered = true;
|
|
164
|
+
this.paint();
|
|
165
|
+
}
|
|
166
|
+
paint() {
|
|
167
|
+
const sel = this.selectable;
|
|
168
|
+
const first = NAMES.findIndex((n) => this.selected.includes(n));
|
|
169
|
+
const inside = this.contains(document.activeElement);
|
|
170
|
+
const stop = inside || first < 0 ? this.active : first;
|
|
171
|
+
this.querySelectorAll(".k-iran-map__province").forEach((p, i) => {
|
|
172
|
+
const on = this.selected.includes(NAMES[i]);
|
|
173
|
+
p.toggleAttribute("data-selected", on);
|
|
174
|
+
if (sel) {
|
|
175
|
+
p.setAttribute("aria-checked", String(on));
|
|
176
|
+
p.setAttribute("tabindex", i === stop ? "0" : "-1");
|
|
177
|
+
}
|
|
178
|
+
});
|
|
179
|
+
const name = this.getAttribute("name");
|
|
180
|
+
this.querySelectorAll(":scope > input[type=hidden]").forEach((el) => el.remove());
|
|
181
|
+
if (name) {
|
|
182
|
+
for (const v of this.multiple ? this.selected : [this.selected[0] ?? ""]) {
|
|
183
|
+
const h = document.createElement("input");
|
|
184
|
+
h.type = "hidden";
|
|
185
|
+
h.name = name;
|
|
186
|
+
h.value = v;
|
|
187
|
+
this.append(h);
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
toggle(n) {
|
|
192
|
+
if (this.multiple)
|
|
193
|
+
this.selected = this.selected.includes(n) ? this.selected.filter((x) => x !== n) : [...this.selected, n];
|
|
194
|
+
else
|
|
195
|
+
this.selected = this.selected[0] === n ? [] : [n];
|
|
196
|
+
this.paint();
|
|
197
|
+
emit(this, "kashi-change", { value: this.multiple ? [...this.selected] : (this.selected[0] ?? null) });
|
|
198
|
+
}
|
|
199
|
+
// فوکوس گردشی: یک استان در ترتیب Tab است و جهتنماها بین استانها جابهجا میشوند
|
|
200
|
+
onKey(e) {
|
|
201
|
+
const i = this.active;
|
|
202
|
+
const move = { ArrowLeft: 1, ArrowDown: 1, ArrowRight: -1, ArrowUp: -1 }[e.key];
|
|
203
|
+
let next = i;
|
|
204
|
+
if (move)
|
|
205
|
+
next = (i + move + NAMES.length) % NAMES.length;
|
|
206
|
+
else if (e.key === "Home")
|
|
207
|
+
next = 0;
|
|
208
|
+
else if (e.key === "End")
|
|
209
|
+
next = NAMES.length - 1;
|
|
210
|
+
else if (e.key === "Enter" || e.key === " ") {
|
|
211
|
+
e.preventDefault();
|
|
212
|
+
this.toggle(NAMES[i]);
|
|
213
|
+
return;
|
|
214
|
+
}
|
|
215
|
+
else
|
|
216
|
+
return;
|
|
217
|
+
e.preventDefault();
|
|
218
|
+
this.active = next;
|
|
219
|
+
this.paint();
|
|
220
|
+
this.querySelector(`[data-i="${next}"]`)?.focus();
|
|
221
|
+
}
|
|
222
|
+
tip(i) {
|
|
223
|
+
const box = this.querySelector(".k-chart__tip");
|
|
224
|
+
if (!box)
|
|
225
|
+
return;
|
|
226
|
+
this.querySelector(".k-iran-map__province[data-active]")?.removeAttribute("data-active");
|
|
227
|
+
// display: grid در CSS بر hidden غلبه میکند؛ پس با style پنهان میشود
|
|
228
|
+
if (i === null) {
|
|
229
|
+
box.style.display = "none";
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
const n = NAMES[i];
|
|
233
|
+
this.querySelector(`[data-i="${i}"]`)?.setAttribute("data-active", "");
|
|
234
|
+
const p = IRAN_PROVINCES[n];
|
|
235
|
+
const w = this.querySelector("figure").clientWidth || VW;
|
|
236
|
+
const v = this.values?.[n];
|
|
237
|
+
const unit = this.getAttribute("unit");
|
|
238
|
+
const row = typeof v === "number" ? `${this.fmt(v)}${unit ? ` ${unit}` : ""}` : `مرکز: ${CAPITAL[n]}`;
|
|
239
|
+
box.innerHTML = `<span class="k-chart__tip-title">${esc(n)}</span><span class="k-chart__tip-row"><strong>${esc(row)}</strong></span>`;
|
|
240
|
+
// داخل ظرف بماند و راهنمای استانهای شمالی بالای نقشه بیرون نزند
|
|
241
|
+
box.style.left = `${Math.min(Math.max((p.x / VW) * w, 80), w - 80)}px`;
|
|
242
|
+
box.style.top = `${Math.max(64, (p.y / VH) * (w * (VH / VW)) - 6)}px`;
|
|
243
|
+
box.style.display = "";
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
KashiIranMap.observedAttributes = ["data", "value", "label", "unit", "steps", "scale", "legend", "selectable", "multiple", "name"];
|
|
247
|
+
const LABELS = { province: "استان", city: "شهر", street: "نشانی", plaque: "پلاک", unit: "واحد", postalCode: "کد پستی" };
|
|
248
|
+
/**
|
|
249
|
+
* فرم نشانی ایرانی: استان، شهرِ همان استان، نشانی، پلاک، واحد و کد پستی دهرقمی؛ با map نقشهٔ ایران برای انتخاب استان.
|
|
250
|
+
* با انتخاب شهر بدون استان، استان خودکار پر میشود و با عوض شدن استان، شهرِ نامربوط پاک میشود.
|
|
251
|
+
* با name="shipping" فیلدها بهشکل shipping[province]، shipping[city]، … در فرم HTML ارسال میشوند.
|
|
252
|
+
*/
|
|
253
|
+
export class KashiAddressForm extends HTMLBase {
|
|
254
|
+
constructor() {
|
|
255
|
+
super(...arguments);
|
|
256
|
+
this.address = { ...EMPTY_ADDRESS };
|
|
257
|
+
this.built = false;
|
|
258
|
+
this.key = uid("kashi-address");
|
|
259
|
+
}
|
|
260
|
+
connectedCallback() {
|
|
261
|
+
afterParse(() => {
|
|
262
|
+
if (!this.isConnected)
|
|
263
|
+
return;
|
|
264
|
+
if (!this.built) {
|
|
265
|
+
const v = Object.prototype.hasOwnProperty.call(this, "value") ? this.value : null;
|
|
266
|
+
delete this.value;
|
|
267
|
+
const attr = this.getAttribute("value");
|
|
268
|
+
let initial = v ?? {};
|
|
269
|
+
if (!v && attr)
|
|
270
|
+
try {
|
|
271
|
+
initial = JSON.parse(attr);
|
|
272
|
+
}
|
|
273
|
+
catch { /* قالب نادرست نادیده گرفته میشود */ }
|
|
274
|
+
this.address = { ...EMPTY_ADDRESS, ...initial };
|
|
275
|
+
}
|
|
276
|
+
this.render();
|
|
277
|
+
});
|
|
278
|
+
}
|
|
279
|
+
attributeChangedCallback(_n, old, next) {
|
|
280
|
+
if (this.built && old !== next)
|
|
281
|
+
this.render();
|
|
282
|
+
}
|
|
283
|
+
/** نشانی کامل؛ مثل { province: "اصفهان", city: "کاشان", street, plaque, unit, postalCode } */
|
|
284
|
+
get value() {
|
|
285
|
+
return { ...this.address };
|
|
286
|
+
}
|
|
287
|
+
set value(v) {
|
|
288
|
+
this.address = { ...EMPTY_ADDRESS, ...v };
|
|
289
|
+
if (this.built)
|
|
290
|
+
this.render();
|
|
291
|
+
}
|
|
292
|
+
/** خطای هر فیلد، مثلاً از اعتبارسنجی سرور: { plaque: "پلاک را بنویسید." } */
|
|
293
|
+
set errors(e) {
|
|
294
|
+
for (const f of Object.keys(LABELS)) {
|
|
295
|
+
const el = this.querySelector(`[data-field="${f}"]`);
|
|
296
|
+
if (!el)
|
|
297
|
+
continue;
|
|
298
|
+
if (el.matches("kashi-province-select, kashi-city-select, kashi-postal-code")) {
|
|
299
|
+
if (e[f])
|
|
300
|
+
el.setAttribute("error", e[f]);
|
|
301
|
+
else
|
|
302
|
+
el.removeAttribute("error");
|
|
303
|
+
}
|
|
304
|
+
else
|
|
305
|
+
this.fieldError(el, e[f] ?? null);
|
|
306
|
+
}
|
|
307
|
+
}
|
|
308
|
+
label(f) {
|
|
309
|
+
return this.getAttribute(`label-${f === "postalCode" ? "postal-code" : f}`) ?? LABELS[f];
|
|
310
|
+
}
|
|
311
|
+
render() {
|
|
312
|
+
const a = this.address;
|
|
313
|
+
const name = this.getAttribute("name");
|
|
314
|
+
const n = (f) => (name ? ` name="${esc(`${name}[${f}]`)}"` : "");
|
|
315
|
+
const req = bool(this, "required", true);
|
|
316
|
+
const r = req ? " required" : "";
|
|
317
|
+
const map = bool(this, "map");
|
|
318
|
+
const k = this.key;
|
|
319
|
+
const reqMark = req ? '<span class="k-label__required" aria-hidden="true">*</span>' : "";
|
|
320
|
+
const legend = this.getAttribute("legend") ?? "نشانی";
|
|
321
|
+
this.innerHTML = `<fieldset class="k-address${map ? " k-address--map" : ""}"${this.hasAttribute("disabled") ? " disabled" : ""}>
|
|
322
|
+
${legend ? `<legend class="k-address__legend">${esc(legend)}</legend>` : ""}
|
|
323
|
+
<div class="k-address__fields">
|
|
324
|
+
<kashi-province-select class="k-address__province" data-field="province" label="${esc(this.label("province"))}" show-capital="false" placeholder="جستجوی استان"${n("province")}${r}></kashi-province-select>
|
|
325
|
+
<kashi-city-select class="k-address__city" data-field="city" label="${esc(this.label("city"))}"${n("city")}${r}></kashi-city-select>
|
|
326
|
+
<div class="k-field k-address__street" data-field="street"><div class="k-field__label-row"><label class="k-label" for="${k}-street">${esc(this.label("street"))}${reqMark}</label></div><div class="k-input k-input--textarea k-input--autoresize"><textarea id="${k}-street" class="k-input__control" rows="2" autocomplete="street-address" placeholder="خیابان، کوچه، نام ساختمان"${n("street")}${r}></textarea></div></div>
|
|
327
|
+
<div class="k-field k-address__plaque" data-field="plaque"><div class="k-field__label-row"><label class="k-label" for="${k}-plaque">${esc(this.label("plaque"))}${reqMark}</label></div><div class="k-input"><input id="${k}-plaque" class="k-input__control" inputmode="numeric" autocomplete="address-line2"${n("plaque")}${r}></div></div>
|
|
328
|
+
<div class="k-field k-address__unit" data-field="unit"><div class="k-field__label-row"><label class="k-label" for="${k}-unit">${esc(this.label("unit"))}${req ? '<span class="k-label__optional">اختیاری</span>' : ""}</label></div><div class="k-input"><input id="${k}-unit" class="k-input__control" inputmode="numeric" autocomplete="address-line3"${n("unit")}></div></div>
|
|
329
|
+
<kashi-postal-code class="k-address__postal" data-field="postalCode" label="${esc(this.label("postalCode"))}"${n("postalCode")}${r}></kashi-postal-code>
|
|
330
|
+
</div>
|
|
331
|
+
${map ? `<kashi-iran-map class="k-address__map" selectable label="${esc(`${this.label("province")} روی نقشه`)}"></kashi-iran-map>` : ""}
|
|
332
|
+
</fieldset>`;
|
|
333
|
+
this.built = true;
|
|
334
|
+
const province = this.querySelector("kashi-province-select");
|
|
335
|
+
const city = this.querySelector("kashi-city-select");
|
|
336
|
+
const postal = this.querySelector("kashi-postal-code");
|
|
337
|
+
const mapEl = this.querySelector("kashi-iran-map");
|
|
338
|
+
const street = this.querySelector("textarea");
|
|
339
|
+
const plaque = this.querySelector(`#${k}-plaque`);
|
|
340
|
+
const unit = this.querySelector(`#${k}-unit`);
|
|
341
|
+
if (a.province)
|
|
342
|
+
province.value = a.province;
|
|
343
|
+
if (a.province)
|
|
344
|
+
city.setAttribute("province", a.province);
|
|
345
|
+
if (a.city)
|
|
346
|
+
city.value = a.city;
|
|
347
|
+
postal.value = a.postalCode;
|
|
348
|
+
street.value = a.street;
|
|
349
|
+
plaque.value = a.plaque;
|
|
350
|
+
unit.value = a.unit;
|
|
351
|
+
if (mapEl && a.province)
|
|
352
|
+
mapEl.value = a.province;
|
|
353
|
+
const setProvince = (p) => {
|
|
354
|
+
// شهر فقط وقتی میماند که در استان تازه هم باشد (شهرهای خارج از فهرست هم پاک میشوند)
|
|
355
|
+
const keep = p && this.address.city && getCities(p).includes(this.address.city);
|
|
356
|
+
this.address = { ...this.address, province: p, city: keep ? this.address.city : null };
|
|
357
|
+
if (province.value !== (p ?? ""))
|
|
358
|
+
province.value = p ?? "";
|
|
359
|
+
city.province = p;
|
|
360
|
+
if (!keep)
|
|
361
|
+
city.value = "";
|
|
362
|
+
if (mapEl)
|
|
363
|
+
mapEl.value = p ?? "";
|
|
364
|
+
this.changed();
|
|
365
|
+
};
|
|
366
|
+
const stop = (e) => e.stopPropagation();
|
|
367
|
+
province.addEventListener("kashi-change", (e) => {
|
|
368
|
+
stop(e);
|
|
369
|
+
setProvince(e.detail.value || null);
|
|
370
|
+
});
|
|
371
|
+
mapEl?.addEventListener("kashi-change", (e) => {
|
|
372
|
+
stop(e);
|
|
373
|
+
setProvince(e.detail.value);
|
|
374
|
+
});
|
|
375
|
+
city.addEventListener("kashi-change", (e) => {
|
|
376
|
+
stop(e);
|
|
377
|
+
const { value, province: p } = e.detail;
|
|
378
|
+
this.address = { ...this.address, city: value || null };
|
|
379
|
+
if (p && !this.address.province)
|
|
380
|
+
setProvince(p);
|
|
381
|
+
else
|
|
382
|
+
this.changed();
|
|
383
|
+
});
|
|
384
|
+
postal.addEventListener("kashi-change", (e) => {
|
|
385
|
+
stop(e);
|
|
386
|
+
this.address = { ...this.address, postalCode: e.detail.value };
|
|
387
|
+
this.changed();
|
|
388
|
+
});
|
|
389
|
+
for (const [el, f] of [[street, "street"], [plaque, "plaque"], [unit, "unit"]]) {
|
|
390
|
+
el.addEventListener("input", () => {
|
|
391
|
+
this.address = { ...this.address, [f]: el.value };
|
|
392
|
+
this.changed();
|
|
393
|
+
});
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
changed() {
|
|
397
|
+
emit(this, "kashi-change", { value: this.value });
|
|
398
|
+
}
|
|
399
|
+
fieldError(field, error) {
|
|
400
|
+
field.querySelector(".k-field__hint-row")?.remove();
|
|
401
|
+
const control = field.querySelector(".k-input__control");
|
|
402
|
+
field.toggleAttribute("data-invalid", !!error);
|
|
403
|
+
if (error) {
|
|
404
|
+
field.insertAdjacentHTML("beforeend", `<div class="k-field__hint-row"><div class="k-field__hints"><p class="k-hint k-hint--error" id="${control.id}-error">${esc(error)}</p></div></div>`);
|
|
405
|
+
control.setAttribute("aria-invalid", "true");
|
|
406
|
+
control.setAttribute("aria-describedby", `${control.id}-error`);
|
|
407
|
+
}
|
|
408
|
+
else {
|
|
409
|
+
control.removeAttribute("aria-invalid");
|
|
410
|
+
control.removeAttribute("aria-describedby");
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
}
|
|
414
|
+
KashiAddressForm.observedAttributes = ["legend", "name", "map", "required", "disabled"];
|
|
415
|
+
define("kashi-iran-map", KashiIranMap, "block");
|
|
416
|
+
define("kashi-address-form", KashiAddressForm, "block");
|
package/dist/menu.d.ts
ADDED
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { HTMLBase } from "./base.js";
|
|
2
|
+
/**
|
|
3
|
+
* منوی کشویی با الگوی Menu Button در WAI-ARIA. اولین فرزند دکمهٔ بازکننده است و بقیه گزینهها:
|
|
4
|
+
* <button> (با data-value، data-shortcut، data-tone="danger"، data-checked، disabled)، <a href>، <hr> برای جداکننده
|
|
5
|
+
* و هر عنصر data-label برای عنوان گروه. ↑↓ حرکت، Home/End، پرش با حرف اول، Esc بستن.
|
|
6
|
+
*/
|
|
7
|
+
export declare class KashiDropdownMenu extends HTMLBase {
|
|
8
|
+
static observedAttributes: string[];
|
|
9
|
+
private menu;
|
|
10
|
+
private trigger;
|
|
11
|
+
private key;
|
|
12
|
+
connectedCallback(): void;
|
|
13
|
+
disconnectedCallback(): void;
|
|
14
|
+
attributeChangedCallback(): void;
|
|
15
|
+
get open(): boolean;
|
|
16
|
+
private build;
|
|
17
|
+
private paintCheck;
|
|
18
|
+
private decorate;
|
|
19
|
+
/** باز کردن منو و فوکوس روی اولین یا آخرین گزینه */
|
|
20
|
+
show(focus?: "first" | "last"): void;
|
|
21
|
+
/** بستن منو؛ با focusTrigger فوکوس به دکمهٔ بازکننده برمیگردد */
|
|
22
|
+
close(focusTrigger?: boolean): void;
|
|
23
|
+
private onOutside;
|
|
24
|
+
private onKey;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* پنجرهٔ کوچک غیرمدال کنار یک دکمه؛ اولین فرزند دکمهٔ بازکننده است و بقیه محتوای پنجره.
|
|
28
|
+
* فوکوس به اولین عنصر قابل فوکوس داخل آن میرود، Esc میبندد و فوکوس را به دکمه برمیگرداند.
|
|
29
|
+
*/
|
|
30
|
+
export declare class KashiPopover extends HTMLBase {
|
|
31
|
+
static observedAttributes: string[];
|
|
32
|
+
private panel;
|
|
33
|
+
private trigger;
|
|
34
|
+
private key;
|
|
35
|
+
connectedCallback(): void;
|
|
36
|
+
disconnectedCallback(): void;
|
|
37
|
+
attributeChangedCallback(): void;
|
|
38
|
+
get open(): boolean;
|
|
39
|
+
set open(v: boolean);
|
|
40
|
+
private build;
|
|
41
|
+
private decorate;
|
|
42
|
+
show(): void;
|
|
43
|
+
close(focusTrigger?: boolean): void;
|
|
44
|
+
private onOutside;
|
|
45
|
+
}
|