@scania-nl/tegel-angular-extensions 0.0.8 → 0.0.9
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 +122 -24
- package/esm2022/index.mjs +3 -1
- package/esm2022/lib/components/tae-date-time-picker/tae-date-time-picker.component.mjs +366 -0
- package/esm2022/lib/components/tae-date-time-picker/tae-date-time-picker.constants.mjs +24 -0
- package/esm2022/lib/components/tae-date-time-picker/tae-date-time-picker.utils.mjs +148 -0
- package/esm2022/lib/directives/typed-template.directive.mjs +38 -0
- package/esm2022/lib/modal/components/modal/modal.component.mjs +10 -3
- package/esm2022/lib/modal/schema/modal.model.mjs +1 -1
- package/index.d.ts +176 -7
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -71,6 +71,7 @@ Provides simple wrappers for toast and modal functionality using Angular 19+ **s
|
|
|
71
71
|
3. [Modal Lifecycle Hooks](#modal-lifecycle-hooks)
|
|
72
72
|
5. [Components & Directives](#components--directives)
|
|
73
73
|
1. [Components](#components)
|
|
74
|
+
1. [DateTime Picker](#datetime-picker-component-tae-date-time-picker)
|
|
74
75
|
1. [Footer](#footer-component-tae-footer)
|
|
75
76
|
2. [Directives](#directives)
|
|
76
77
|
1. [Hard Refresh](#hard-refresh-directive-taehardrefresh)
|
|
@@ -578,15 +579,15 @@ You get a `ModalRef` back from `create()`, which you can use to control that spe
|
|
|
578
579
|
|
|
579
580
|
These options are passed to `modalService.create()` and override defaults from `provideModal()` on a per‑modal basis. For shared defaults like `size`, `actionsPosition`, `prevent`, `closable`, `alertDialog`, `lazy`, `startOpen`, and `removeOnClose`, see [Modal Configuration Options](#modal-configuration-options) above.
|
|
580
581
|
|
|
581
|
-
| Option | Type
|
|
582
|
-
| ------------- |
|
|
583
|
-
| `header` | `string \| TemplateRef<unknown>`
|
|
584
|
-
| `body` | `string \|
|
|
585
|
-
| `buttons` | `ModalButton[]`
|
|
586
|
-
| `selector` | `string`
|
|
587
|
-
| `referenceEl` | `HTMLElement`
|
|
588
|
-
| `onClosed` | `() => void \| Promise<void>`
|
|
589
|
-
| `onRemoved` | `() => void \| Promise<void>`
|
|
582
|
+
| Option | Type | Description |
|
|
583
|
+
| ------------- | ------------------------------------------------------------------- | ----------------------------------------------------------- |
|
|
584
|
+
| `header` | `string \| TemplateRef<unknown>` | Modal header text or template |
|
|
585
|
+
| `body` | `string \| { template, context } \| { component, inputs, outputs }` | Modal body content (string, template+context, or component) |
|
|
586
|
+
| `buttons` | `ModalButton[]` | Action buttons to render in the actions slot |
|
|
587
|
+
| `selector` | `string` | CSS selector for focus return element |
|
|
588
|
+
| `referenceEl` | `HTMLElement` | Element to return focus to (preferred over selector) |
|
|
589
|
+
| `onClosed` | `() => void \| Promise<void>` | Called when the modal is closed |
|
|
590
|
+
| `onRemoved` | `() => void \| Promise<void>` | Called after the modal is removed |
|
|
590
591
|
|
|
591
592
|
> Note: If you want focus to return to the element that opened the modal, pass either `selector` or `referenceEl` when creating the modal. This avoids Tegel's "Missing focus origin" warning.
|
|
592
593
|
|
|
@@ -596,7 +597,7 @@ These options are passed to `modalService.create()` and override defaults from `
|
|
|
596
597
|
|
|
597
598
|
### Body content options
|
|
598
599
|
|
|
599
|
-
The modal body can be provided as a simple string, a
|
|
600
|
+
The modal body can be provided as a simple string, a template body, or a component descriptor.
|
|
600
601
|
|
|
601
602
|
|
|
602
603
|
|
|
@@ -611,26 +612,77 @@ this.modalService.create({
|
|
|
611
612
|
|
|
612
613
|
|
|
613
614
|
|
|
614
|
-
#### 2)
|
|
615
|
+
#### 2) Template body (template + optional context)
|
|
616
|
+
|
|
617
|
+
Signature:
|
|
618
|
+
|
|
619
|
+
```
|
|
620
|
+
body: {
|
|
621
|
+
template: TemplateRef<TContext>;
|
|
622
|
+
context?: TContext;
|
|
623
|
+
}
|
|
624
|
+
```
|
|
625
|
+
|
|
626
|
+
|
|
627
|
+
Example:
|
|
615
628
|
|
|
616
629
|
```html
|
|
617
|
-
<ng-template #bodyTpl>
|
|
618
|
-
<
|
|
630
|
+
<ng-template #bodyTpl let-context>
|
|
631
|
+
<p>
|
|
632
|
+
<b>{{ context.substance }}<b> boils at
|
|
633
|
+
<b>{{ context.value }}</b> degrees {{ context.units }}.
|
|
634
|
+
</p>
|
|
619
635
|
</ng-template>
|
|
620
636
|
```
|
|
621
637
|
|
|
622
638
|
```ts
|
|
623
|
-
|
|
639
|
+
interface SubstanceTemperature {
|
|
640
|
+
substance: string;
|
|
641
|
+
value: number;
|
|
642
|
+
units: string;
|
|
643
|
+
}
|
|
644
|
+
|
|
645
|
+
const bodyTpl =
|
|
646
|
+
viewChild.required<TemplateRef<SubstanceTemperature>>('bodyTpl');
|
|
624
647
|
this.modalService.create({
|
|
625
648
|
header: 'Template',
|
|
626
|
-
body:
|
|
649
|
+
body: {
|
|
650
|
+
template: bodyTpl(),
|
|
651
|
+
context: {
|
|
652
|
+
substance: 'Water',
|
|
653
|
+
value: 100,
|
|
654
|
+
units: 'Celcius',
|
|
655
|
+
},
|
|
656
|
+
},
|
|
627
657
|
});
|
|
628
658
|
```
|
|
629
659
|
|
|
630
660
|
|
|
631
661
|
|
|
662
|
+
For typed templates, you can use `TypedTemplateDirective` to enforce context types in the template:
|
|
663
|
+
|
|
664
|
+
```html
|
|
665
|
+
<ng-template #bodyTpl let-context [typedContext]="this.bodyTpl()">
|
|
666
|
+
...
|
|
667
|
+
</ng-template>
|
|
668
|
+
```
|
|
669
|
+
|
|
670
|
+
|
|
671
|
+
|
|
632
672
|
#### 3) Component body (with inputs/outputs)
|
|
633
673
|
|
|
674
|
+
Signature:
|
|
675
|
+
|
|
676
|
+
```ts
|
|
677
|
+
body: {
|
|
678
|
+
component: Type<TComponent>;
|
|
679
|
+
inputs: ComponentInputs<TComponent>;
|
|
680
|
+
outputs?: ComponentOutputs<TComponent>;
|
|
681
|
+
}
|
|
682
|
+
```
|
|
683
|
+
|
|
684
|
+
|
|
685
|
+
|
|
634
686
|
When you pass a component as the modal body, the `inputs` and `outputs` objects are fully typed. This means you get IntelliSense for signal inputs/outputs, and any `input.required(...)` fields are enforced at compile time (missing required inputs will fail the build).
|
|
635
687
|
|
|
636
688
|
```ts
|
|
@@ -654,7 +706,7 @@ const ref = this.modalService.create({
|
|
|
654
706
|
outputField: (value: string) => {
|
|
655
707
|
console.log('Value:', value);
|
|
656
708
|
ref.close();
|
|
657
|
-
}
|
|
709
|
+
},
|
|
658
710
|
},
|
|
659
711
|
},
|
|
660
712
|
});
|
|
@@ -685,14 +737,14 @@ this.modalService.create({
|
|
|
685
737
|
|
|
686
738
|
Modal action buttons map directly to Tegel's `tds-button` configuration. The following options are supported:
|
|
687
739
|
|
|
688
|
-
| Option | Type
|
|
689
|
-
| ---------- |
|
|
690
|
-
| `text` | `string`
|
|
691
|
-
| `variant` | `'primary' \| 'secondary' \| 'success' \| 'danger'`
|
|
692
|
-
| `size` | `'xs' \| 'sm' \| 'md' \| 'lg'`
|
|
693
|
-
| `disabled` | `boolean`
|
|
694
|
-
| `dismiss` | `boolean`
|
|
695
|
-
| `onClick` | `() => void \| Promise<void>`
|
|
740
|
+
| Option | Type | Description |
|
|
741
|
+
| ---------- | --------------------------------------------------- | ----------------------------------------------------------- |
|
|
742
|
+
| `text` | `string` | Button label text |
|
|
743
|
+
| `variant` | `'primary' \| 'secondary' \| 'success' \| 'danger'` | Visual variant |
|
|
744
|
+
| `size` | `'xs' \| 'sm' \| 'md' \| 'lg'` | Button size |
|
|
745
|
+
| `disabled` | `boolean` | Disable the button |
|
|
746
|
+
| `dismiss` | `boolean` | Adds `data-dismiss-modal` to trigger Tegel's close behavior |
|
|
747
|
+
| `onClick` | `() => void \| Promise<void>` | Optional click handler (sync or async) |
|
|
696
748
|
|
|
697
749
|
---
|
|
698
750
|
|
|
@@ -810,6 +862,52 @@ This library includes a set of standalone UI components and utility directives,
|
|
|
810
862
|
|
|
811
863
|
## Components
|
|
812
864
|
|
|
865
|
+
### DateTime Picker Component (`tae-date-time-picker`) [BETA]
|
|
866
|
+
|
|
867
|
+
`TaeDateTimePickerComponent` is a standalone, form‑compatible picker that supports `date`, `datetime`, and `time` modes. It implements Angular's `ControlValueAccessor`, so it works with both reactive and template‑driven forms.
|
|
868
|
+
|
|
869
|
+
> Beta: This component is still evolving. Improvements are planned and minor bugs may occur.
|
|
870
|
+
|
|
871
|
+
**Inputs:**
|
|
872
|
+
|
|
873
|
+
| Input | Type | Default | Description |
|
|
874
|
+
| --------------- | ------------------------------------- | --------- | ------------------- |
|
|
875
|
+
| `label` | `string` | `''` | Label text |
|
|
876
|
+
| `size` | `'sm' \| 'md' \| 'lg'` | `lg` | Control size |
|
|
877
|
+
| `labelPosition` | `'inside' \| 'outside' \| 'no-label'` | `outside` | Label placement |
|
|
878
|
+
| `state` | `'error' \| undefined` | — | Error state styling |
|
|
879
|
+
| `helper` | `string` | `''` | Helper text |
|
|
880
|
+
| `mode` | `'date' \| 'datetime' \| 'time'` | `date` | Picker mode |
|
|
881
|
+
|
|
882
|
+
> Note: `labelPosition` is currently not implemented; it will be supported in a future update.
|
|
883
|
+
> Note: `state` is currently only used for styling in the template and does not affect behavior.
|
|
884
|
+
|
|
885
|
+
|
|
886
|
+
|
|
887
|
+
**Example (reactive forms):**
|
|
888
|
+
|
|
889
|
+
```ts
|
|
890
|
+
readonly form = this.fb.group({
|
|
891
|
+
date: this.fb.control<string | null>(null),
|
|
892
|
+
time: this.fb.control<string | null>(null),
|
|
893
|
+
dateTime: this.fb.control<string | null>(null),
|
|
894
|
+
});
|
|
895
|
+
```
|
|
896
|
+
|
|
897
|
+
```html
|
|
898
|
+
<form [formGroup]="form">
|
|
899
|
+
<tae-date-time-picker label="Date" formControlName="date" mode="date" />
|
|
900
|
+
<tae-date-time-picker label="Time" formControlName="time" mode="time" />
|
|
901
|
+
<tae-date-time-picker
|
|
902
|
+
label="DateTime"
|
|
903
|
+
formControlName="dateTime"
|
|
904
|
+
mode="datetime"
|
|
905
|
+
/>
|
|
906
|
+
</form>
|
|
907
|
+
```
|
|
908
|
+
|
|
909
|
+
|
|
910
|
+
|
|
813
911
|
### Footer Component (`tae-footer`)
|
|
814
912
|
|
|
815
913
|
`TaeFooterComponent` is an enhanced footer based on the Tegel `TdsFooterComponent`. It preserves the same visual appearance while adding two key improvements:
|
package/esm2022/index.mjs
CHANGED
|
@@ -24,8 +24,10 @@ export { provideStaticConfig } from './lib/env/angular/provide-static-config';
|
|
|
24
24
|
// --------------------------------------------------
|
|
25
25
|
export { BarcodeScannerDirective } from './lib/directives/barcode-scanner.directive';
|
|
26
26
|
export { HardRefreshDirective } from './lib/directives/hard-refresh.directive';
|
|
27
|
+
export { TypedTemplateDirective } from './lib/directives/typed-template.directive';
|
|
27
28
|
// --------------------------------------------------
|
|
28
29
|
// Component Module Exports
|
|
29
30
|
// --------------------------------------------------
|
|
31
|
+
export { TaeDateTimePickerComponent } from './lib/components/tae-date-time-picker/tae-date-time-picker.component';
|
|
30
32
|
export { TaeFooterComponent } from './lib/components/tae-footer/tae-footer.component';
|
|
31
|
-
//# sourceMappingURL=data:application/json;base64,
|
|
33
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9saWJzL3RlZ2VsLWFuZ3VsYXItZXh0ZW5zaW9ucy9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEscURBQXFEO0FBQ3JELHVCQUF1QjtBQUN2QixxREFBcUQ7QUFDckQsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBQ3pELE9BQU8sRUFDTCxvQkFBb0IsRUFDcEIsWUFBWSxHQUViLE1BQU0sMEJBQTBCLENBQUM7QUFDbEMsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLDJCQUEyQixDQUFDO0FBS3pELHFEQUFxRDtBQUNyRCx1QkFBdUI7QUFDdkIscURBQXFEO0FBQ3JELE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSwyQkFBMkIsQ0FBQztBQUN6RCxPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFFekQsT0FBTyxFQUNMLG9CQUFvQixFQUNwQixZQUFZLEdBRWIsTUFBTSxpQ0FBaUMsQ0FBQztBQVN6QyxxREFBcUQ7QUFDckQscUJBQXFCO0FBQ3JCLHFEQUFxRDtBQUNyRCxPQUFPO0FBQ1AsT0FBTyxFQUFFLFlBQVksRUFBRSxNQUFNLCtCQUErQixDQUFDO0FBQzdELE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSwrQkFBK0IsQ0FBQztBQUU3RCxVQUFVO0FBQ1YsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sMENBQTBDLENBQUM7QUFDaEYsT0FBTyxFQUFFLG1CQUFtQixFQUFFLE1BQU0seUNBQXlDLENBQUM7QUFFOUUscURBQXFEO0FBQ3JELDJCQUEyQjtBQUMzQixxREFBcUQ7QUFDckQsT0FBTyxFQUFFLHVCQUF1QixFQUFFLE1BQU0sNENBQTRDLENBQUM7QUFDckYsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0seUNBQXlDLENBQUM7QUFDL0UsT0FBTyxFQUFFLHNCQUFzQixFQUFFLE1BQU0sMkNBQTJDLENBQUM7QUFFbkYscURBQXFEO0FBQ3JELDJCQUEyQjtBQUMzQixxREFBcUQ7QUFDckQsT0FBTyxFQUFFLDBCQUEwQixFQUFFLE1BQU0sc0VBQXNFLENBQUM7QUFDbEgsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sa0RBQWtELENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLVxuLy8gVG9hc3QgTW9kdWxlIEV4cG9ydHNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5leHBvcnQgeyBwcm92aWRlVG9hc3QgfSBmcm9tICcuL2xpYi90b2FzdC9wcm92aWRlLXRvYXN0JztcbmV4cG9ydCB7XG4gIERFRkFVTFRfVE9BU1RfQ09ORklHLFxuICBUT0FTVF9DT05GSUcsXG4gIFRvYXN0Q29uZmlnLFxufSBmcm9tICcuL2xpYi90b2FzdC90b2FzdC5jb25maWcnO1xuZXhwb3J0IHsgVG9hc3RTZXJ2aWNlIH0gZnJvbSAnLi9saWIvdG9hc3QvdG9hc3Quc2VydmljZSc7XG5cbi8vIE1vZGVsc1xuZXhwb3J0IHsgVG9hc3QsIFRvYXN0T3B0aW9ucyB9IGZyb20gJy4vbGliL3RvYXN0L21vZGVscy90b2FzdC5tb2RlbCc7XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBNb2RhbCBNb2R1bGUgRXhwb3J0c1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmV4cG9ydCB7IE1vZGFsU2VydmljZSB9IGZyb20gJy4vbGliL21vZGFsL21vZGFsLnNlcnZpY2UnO1xuZXhwb3J0IHsgcHJvdmlkZU1vZGFsIH0gZnJvbSAnLi9saWIvbW9kYWwvcHJvdmlkZS1tb2RhbCc7XG5leHBvcnQgeyBNb2RhbFJlZiB9IGZyb20gJy4vbGliL21vZGFsL3NjaGVtYS9tb2RhbC1yZWYnO1xuZXhwb3J0IHtcbiAgREVGQVVMVF9NT0RBTF9DT05GSUcsXG4gIE1PREFMX0NPTkZJRyxcbiAgTW9kYWxDb25maWcsXG59IGZyb20gJy4vbGliL21vZGFsL3NjaGVtYS9tb2RhbC5jb25maWcnO1xuZXhwb3J0IHsgTW9kYWwsIE1vZGFsT3B0aW9ucyB9IGZyb20gJy4vbGliL21vZGFsL3NjaGVtYS9tb2RhbC5tb2RlbCc7XG5leHBvcnQge1xuICBNb2RhbEFjdGlvbnNQb3NpdGlvbixcbiAgTW9kYWxBbGVydERpYWxvZ1JvbGUsXG4gIE1vZGFsQnV0dG9uLFxuICBNb2RhbFNpemUsXG59IGZyb20gJy4vbGliL21vZGFsL3NjaGVtYS9tb2RhbC50eXBlcyc7XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBFbnYgTW9kdWxlIEV4cG9ydHNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBDb3JlXG5leHBvcnQgeyBjcmVhdGVFbnZLaXQgfSBmcm9tICcuL2xpYi9lbnYvY29yZS9jcmVhdGUtZW52LWtpdCc7XG5leHBvcnQgeyBwYXJzZUVudkZpbGUgfSBmcm9tICcuL2xpYi9lbnYvY29yZS9wYXJzZS1lbnYtZmlsZSc7XG5cbi8vIEFuZ3VsYXJcbmV4cG9ydCB7IHByb3ZpZGVSdW50aW1lQ29uZmlnIH0gZnJvbSAnLi9saWIvZW52L2FuZ3VsYXIvcHJvdmlkZS1ydW50aW1lLWNvbmZpZyc7XG5leHBvcnQgeyBwcm92aWRlU3RhdGljQ29uZmlnIH0gZnJvbSAnLi9saWIvZW52L2FuZ3VsYXIvcHJvdmlkZS1zdGF0aWMtY29uZmlnJztcblxuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbi8vIERpcmVjdGl2ZSBNb2R1bGUgRXhwb3J0c1xuLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS1cbmV4cG9ydCB7IEJhcmNvZGVTY2FubmVyRGlyZWN0aXZlIH0gZnJvbSAnLi9saWIvZGlyZWN0aXZlcy9iYXJjb2RlLXNjYW5uZXIuZGlyZWN0aXZlJztcbmV4cG9ydCB7IEhhcmRSZWZyZXNoRGlyZWN0aXZlIH0gZnJvbSAnLi9saWIvZGlyZWN0aXZlcy9oYXJkLXJlZnJlc2guZGlyZWN0aXZlJztcbmV4cG9ydCB7IFR5cGVkVGVtcGxhdGVEaXJlY3RpdmUgfSBmcm9tICcuL2xpYi9kaXJlY3RpdmVzL3R5cGVkLXRlbXBsYXRlLmRpcmVjdGl2ZSc7XG5cbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4vLyBDb21wb25lbnQgTW9kdWxlIEV4cG9ydHNcbi8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG5leHBvcnQgeyBUYWVEYXRlVGltZVBpY2tlckNvbXBvbmVudCB9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvdGFlLWRhdGUtdGltZS1waWNrZXIvdGFlLWRhdGUtdGltZS1waWNrZXIuY29tcG9uZW50JztcbmV4cG9ydCB7IFRhZUZvb3RlckNvbXBvbmVudCB9IGZyb20gJy4vbGliL2NvbXBvbmVudHMvdGFlLWZvb3Rlci90YWUtZm9vdGVyLmNvbXBvbmVudCc7XG4iXX0=
|