@sb1/indeks-web 0.16.0 → 0.18.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 +46 -0
- package/dist/npm/index.d.ts +36 -2
- package/dist/npm/index.js +992 -17
- package/dist/npm/lib/components/combobox/IxCombobox.d.ts +1 -0
- package/dist/npm/lib/components/date-field/IxDateField.d.ts +67 -0
- package/dist/npm/lib/components/field/formats.d.ts +55 -7
- package/dist/npm/lib/components/phone-number-field/IxPhoneNumberField.d.ts +33 -0
- package/dist/npm/lib/components/phone-number-field/countries.d.ts +27 -0
- package/dist/npm/lib/components/progress-bar/IxProgressBar.d.ts +1 -0
- package/dist/npm/lib/utils/cn.d.ts +20 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,51 @@
|
|
|
1
1
|
# @sb1/indeks-web
|
|
2
2
|
|
|
3
|
+
## 0.18.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- bb77cc9: Ny intern `cn`-util erstatter den eksterne `clsx`-avhengigheten. `cn` bor i `@sb1/indeks-web` (`lib/utils/cn.ts`), re-eksporteres fra pakken og eksponeres på `globalThis.cn` slik at den er tilgjengelig i web components og for andre konsumenter — også uten import når indeks-web er lastet. `@sb1/indeks-react` får en bevisst duplisert kopi (React runtime-importerer ikke web) som holdes i synk via `cn.sync.test.ts`, re-eksporterer `cn` fra sitt public API, og har fjernet `clsx` som avhengighet. `ProgressBarState` er nå eksportert fra web og synk-testet mot React-kopien.
|
|
8
|
+
- e42af9e: Combobox fungerer nå med React Hook Form `register()`, ikke bare `<Controller>` — og form-innsending blir mer robust for alle rammeverk.
|
|
9
|
+
|
|
10
|
+
- **indeks-web:** `ix-combobox` fyrer nå et native `change`-event på det skjulte, navngitte `<select>`-feltet (i tillegg til host-eventet), slik at lyttere på form-elementet (ren HTML, Vue, Angular, RHF `register`) hører verdiendringer. `focus()` på elementet delegerer nå til det synlige søkefeltet, så «fokusér første felt med feil» fungerer.
|
|
11
|
+
- **indeks-react:** `Combobox` sin `onChange` sender nå et syntetisk change-event på RHF-form (`{ target: { name, value } }`) i stedet for å kalles med verdien direkte, og en ny `onBlur`-prop fyrer når fokus forlater komponenten. Sammen med web-endringene lar dette `{...register('felt')}` binde direkte.
|
|
12
|
+
|
|
13
|
+
**Breaking (React):** `onChange` får nå et event, ikke verdien. Med `<Controller>` binder du `field.onChange` direkte (uendret). Leste du verdien selv, bytt `onChange={(value) => …}` til `onChange={(e) => { const value = e.target.value; … }}`.
|
|
14
|
+
|
|
15
|
+
- 4d69f00: Forbedringer i DateField og live input-formatering.
|
|
16
|
+
|
|
17
|
+
**Separator dukker opp med én gang gruppen er full (live-formatene).** Den delte pattern-formatteren (`data-format` for `phone`, `ssn`, `account`, `orgnr`) setter nå inn separatoren så snart gruppen foran er fylt — `24` → `24.`, `2412` → `24.12.` — i stedet for å vente på neste siffer. Det gjør at brukeren aldri trenger å taste skilletegnet selv (å taste `.` blir en ufarlig no-op), og fjerner den forvirrende «henger ett tegn etter»-følelsen. Separatoren dobles ikke ved innliming av allerede formatert tekst, og dikter seg ikke opp for en halvfylt gruppe. Markøren hopper forbi den auto-innsatte separatoren når en gruppe fylles, så neste tegn havner rett — mens sletting (backspace) fortsatt kommer forbi separatoren som før.
|
|
18
|
+
|
|
19
|
+
**`date` godtar fleksibel inntasting og formaterer på blur.** `data-format="date"` er ikke lenger en live posisjonsmaske, men en skilletegn-bevisst formatter i blur-modus: brukeren kan taste `1.1.2026` like gjerne som `01.01.2026` (eller `01012026` uten skilletegn), teksten står urørt mens man skriver, og feltet normaliserer/nullutfyller til `dd.mm.åååå` når det mister fokus. Det tastede punktumet tolkes som en meningsfull segment-grense — ingen tegn strippes eller omrokeres — så `1.1.2026` blir korrekt `01.01.2026`, ikke `11.20.26`. Året kan tastes med 4 sifre (`2026`) eller 2 sifre som utvides til `20xx` (`1.1.26` → `01.01.2026`); ufullstendige/tvetydige verdier (`1.1.`, `112026`) vises verbatim og gir ingen ISO-verdi. `phone`/`ssn`/`account`/`orgnr`/`amount` er fast-bredde og formaterer fortsatt live.
|
|
20
|
+
|
|
21
|
+
**Kalenderknappen virker nå i Firefox med peker.** På desktop lar den gjennomsiktige native date-inputen pekeren gå gjennom til knappen (`pointer-events: none`), som kaller `showPicker()`. Firefox åpner ikke kalenderen ved klikk i «kroppen» av en `opacity:0` date-input, så knappen var tidligere effektivt utilgjengelig for peker der. Web-komponenten reflekterer nå touch-plattform som `data-touch` på verten; på touch beholdes tap-på-native-overlay som før.
|
|
22
|
+
|
|
23
|
+
**Nytt opt-in-flagg `nativePickerOnMobile` (HTML: `data-native-picker-mobile`).** Lar et tapp hvor som helst i feltet åpne enhetens innebygde datovelger. Kun aktivt på touch-enheter; standard av, så desktop og eksisterende bruk er uendret.
|
|
24
|
+
|
|
25
|
+
**Feltet kappes til innholdsbredde.** Datoen har fast lengde (`dd.mm.åååå`), så `.ix-date-field` har nå et `max-width`-tak i stedet for å flyte ut i full bredde med mye luft. I en smalere beholder krymper feltet fortsatt, og konsumenten kan overstyre med egen `width`/`max-width` (React: `className`).
|
|
26
|
+
|
|
27
|
+
Docs: eksemplene ligger i en stack, og et nytt mobilvelger-eksempel er lagt til.
|
|
28
|
+
|
|
29
|
+
- 4d69f00: Legg til DateField — et datofelt der brukeren taster i norsk format (`dd.mm.åååå`) eller åpner enhetens innebygde kalender via en knapp i feltet. Verdien utad er alltid ISO (`åååå-mm-dd`), både gjennom `onChange`, `value` og ved skjema-innsending, så den amerikanske `mm/dd/åååå`-tvetydigheten unngås samtidig som datoen er maskinlesbar.
|
|
30
|
+
|
|
31
|
+
Ny `<ix-date-field>`-web component er en hybrid: den nøstes inne i `ix-field` (som `ix-combobox`) og lar `ix-field` gjøre ARIA-limet og formateringen (`data-format="date"` → normaliserer til `dd.mm.åååå` på blur; brukeren kan taste `1.1.2026` like gjerne som `01.01.2026`, og teksten står urørt mens man skriver), mens den selv genererer to instrumentelle elementer inn i `.ix-text-field` (idempotent): en kalenderknapp (`.ix-date-field__toggle`) og en overlagt gjennomsiktig native `<input type="date">` (`.ix-date-field__native`) som bærer ISO-verdien, gir `min`/`max`-validering og åpner OS-kalenderen. Komponenten synkroniserer den synlige `dd.mm.åååå`-verdien og den native ISO-verdien begge veier med guard mot event-løkke, speiler `min`/`max`/`disabled`/`readonly` til den native inputen, flytter `name` til den native inputen (så innsending gir ISO), og emitter én `change` per faktisk endring.
|
|
32
|
+
|
|
33
|
+
Kalenderen åpnes robust helt ned til nettleser-baselinen (Safari 15.4 / Firefox 100): der `showPicker()` finnes brukes den, ellers fanger den overlagte native-inputen tap/klikk direkte. På desktop er kalenderknappen et eget tab-stopp, så tastaturbrukere kan tabbe til den og åpne kalenderen med Enter/Mellomrom (i tillegg til å taste datoen direkte). På touch-enheter skjules knappen fra skjermleser og tas ut av tab-rekkefølgen (`IS_TOUCH` → `aria-hidden` + `tabindex="-1"`) så en swipe ikke treffer to mål — der er tasting og tap primærveien. Den overlagte native inputen er alltid `tabindex="-1"`.
|
|
34
|
+
|
|
35
|
+
React via `<DateField label="…" openLabel="…" />` med kontrollert (`value` + `onChange`) eller ukontrollert (`defaultValue`) verdi i ISO. CSS via `ix-date-field`/`.ix-date-field` (dual-target); den synlige inputen gjenbruker `.ix-text-field`-stilen. Ingen hardkodet tekst — `openLabel` (HTML: `data-open-label`) er påkrevd i18n-tekst for kalenderknappens tilgjengelige navn.
|
|
36
|
+
|
|
37
|
+
Kjent begrensning (fase 1): støtter `min`/`max`, men ikke sperring av enkeltdager eller helger, og bruker enhetens innebygde kalender. En egen kalendervelger for desktop er planlagt i en senere fase.
|
|
38
|
+
|
|
39
|
+
- e42af9e: `TextField`-propen `format` er nå typet med navnene på de innebygde variantene (`"phone"`, `"amount"`, `"account"`, `"orgnr"`, `"ssn"`, `"date"`) i stedet for bare `string`. Du får autocomplete på dem, men kan fortsatt sende egne navn registrert via `registerFormat` (typen er `BuiltInFormatName | (string & {})`, så vilkårlige strenger godtas uten runtime-validering).
|
|
40
|
+
|
|
41
|
+
`indeks-web` eksporterer nå `BUILTIN_FORMAT_NAMES` (og typen `BuiltInFormatName`) som registreringene drives fra, slik at React-lagets dupliserte liste holdes i synk via en sync-test.
|
|
42
|
+
|
|
43
|
+
### Patch Changes
|
|
44
|
+
|
|
45
|
+
- 4d69f00: DateField godtar nå 2-sifret år og utvider det til `20xx`: `1.1.26` tolkes som `01.01.2026` (`99` → `2099`, `00` → `2000`). Utvidingen gjelder kun punktum-formen; den tvetydige skilletegnsløse 6-sifrede formen (`112026`) avvises fortsatt. Både den synlige blur-formateringen og den native ISO-verdien går gjennom samme kanoniske `parseDate`, så de holder seg i synk.
|
|
46
|
+
|
|
47
|
+
## 0.17.0
|
|
48
|
+
|
|
3
49
|
## 0.16.0
|
|
4
50
|
|
|
5
51
|
### Minor Changes
|
package/dist/npm/index.d.ts
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import { IxCheckboxGroup } from './lib/components/checkbox-group/IxCheckboxGroup.js';
|
|
2
2
|
import { IxCombobox } from './lib/components/combobox/IxCombobox.js';
|
|
3
|
+
import { IxDateField } from './lib/components/date-field/IxDateField.js';
|
|
3
4
|
import { IxField } from './lib/components/field/IxField.js';
|
|
4
5
|
import { IxIcon, IconName } from './lib/components/icon/IxIcon.js';
|
|
6
|
+
import { IxPhoneNumberField } from './lib/components/phone-number-field/IxPhoneNumberField.js';
|
|
5
7
|
import { IxProgressBar } from './lib/components/progress-bar/IxProgressBar.js';
|
|
6
8
|
import { IxRadioGroup } from './lib/components/radio-group/IxRadioGroup.js';
|
|
7
9
|
import { IxTabs, IxTabList, IxTab, IxTabPanel } from './lib/components/tabs/IxTabs.js';
|
|
@@ -10,19 +12,27 @@ export { IxIcon };
|
|
|
10
12
|
export { IxRadioGroup };
|
|
11
13
|
export { IxCheckboxGroup };
|
|
12
14
|
export { IxCombobox };
|
|
15
|
+
export { IxDateField };
|
|
16
|
+
export { IxPhoneNumberField };
|
|
13
17
|
export { IxProgressBar };
|
|
18
|
+
export type { ProgressBarState } from './lib/components/progress-bar/IxProgressBar.js';
|
|
14
19
|
export { IxTabs, IxTabList, IxTab, IxTabPanel };
|
|
15
20
|
export { COMMON_ICON_NAMES } from './lib/components/icon/IxIcon.js';
|
|
16
21
|
export type { IconName, CommonIconName } from './lib/components/icon/IxIcon.js';
|
|
17
|
-
export { createPatternFormatter, createAmountFormatter, amountFormatterForLocale, registerFormat, resolveFormat } from './lib/components/field/formats.js';
|
|
18
|
-
export type { FieldFormatter } from './lib/components/field/formats.js';
|
|
22
|
+
export { createPatternFormatter, createAmountFormatter, amountFormatterForLocale, registerFormat, resolveFormat, BUILTIN_FORMAT_NAMES } from './lib/components/field/formats.js';
|
|
23
|
+
export type { FieldFormatter, BuiltInFormatName } from './lib/components/field/formats.js';
|
|
24
|
+
export { cn } from './lib/utils/cn.js';
|
|
25
|
+
export type { ClassValue, ClassDictionary } from './lib/utils/cn.js';
|
|
19
26
|
declare global {
|
|
27
|
+
var cn: (...inputs: import('./lib/utils/cn.js').ClassValue[]) => string;
|
|
20
28
|
interface HTMLElementTagNameMap {
|
|
21
29
|
'ix-field': IxField;
|
|
22
30
|
'ix-icon': IxIcon;
|
|
23
31
|
'ix-radio-group': IxRadioGroup;
|
|
24
32
|
'ix-checkbox-group': IxCheckboxGroup;
|
|
25
33
|
'ix-combobox': IxCombobox;
|
|
34
|
+
'ix-date-field': IxDateField;
|
|
35
|
+
'ix-phone-number-field': IxPhoneNumberField;
|
|
26
36
|
'ix-progress-bar': IxProgressBar;
|
|
27
37
|
'ix-tabs': IxTabs;
|
|
28
38
|
'ix-tab-list': IxTabList;
|
|
@@ -54,6 +64,18 @@ declare global {
|
|
|
54
64
|
class?: string;
|
|
55
65
|
children?: unknown;
|
|
56
66
|
};
|
|
67
|
+
'ix-phone-number-field': {
|
|
68
|
+
disabled?: boolean | '';
|
|
69
|
+
readonly?: boolean | '';
|
|
70
|
+
required?: boolean | '';
|
|
71
|
+
'data-state'?: 'error' | 'readonly' | 'disabled';
|
|
72
|
+
'data-locale'?: 'nb' | 'nn' | 'en';
|
|
73
|
+
'data-countries'?: string;
|
|
74
|
+
'data-country-code'?: string;
|
|
75
|
+
'data-default-country-code'?: string;
|
|
76
|
+
class?: string;
|
|
77
|
+
children?: unknown;
|
|
78
|
+
};
|
|
57
79
|
'ix-combobox': {
|
|
58
80
|
name?: string;
|
|
59
81
|
multiple?: boolean | '';
|
|
@@ -67,6 +89,18 @@ declare global {
|
|
|
67
89
|
class?: string;
|
|
68
90
|
children?: unknown;
|
|
69
91
|
};
|
|
92
|
+
'ix-date-field': {
|
|
93
|
+
name?: string;
|
|
94
|
+
min?: string;
|
|
95
|
+
max?: string;
|
|
96
|
+
value?: string;
|
|
97
|
+
disabled?: boolean | '';
|
|
98
|
+
readonly?: boolean | '';
|
|
99
|
+
'data-open-label'?: string;
|
|
100
|
+
'data-native-picker-mobile'?: boolean | '';
|
|
101
|
+
class?: string;
|
|
102
|
+
children?: unknown;
|
|
103
|
+
};
|
|
70
104
|
'ix-icon': {
|
|
71
105
|
name?: IconName;
|
|
72
106
|
'data-size'?: 'sm' | 'md' | 'lg' | 'xl';
|