@falcon-ng/tailwind 0.0.2

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.
Files changed (123) hide show
  1. package/README.md +71 -0
  2. package/ng-package.json +7 -0
  3. package/package.json +11 -0
  4. package/src/lib/base-control.ts +142 -0
  5. package/src/lib/base-form-component.ts +363 -0
  6. package/src/lib/component/auto-complete/auto-complete.component.html +39 -0
  7. package/src/lib/component/auto-complete/auto-complete.component.scss +0 -0
  8. package/src/lib/component/auto-complete/auto-complete.component.spec.ts +23 -0
  9. package/src/lib/component/auto-complete/auto-complete.component.ts +31 -0
  10. package/src/lib/component/bottom-sheet/bottom-sheet.component.html +9 -0
  11. package/src/lib/component/bottom-sheet/bottom-sheet.component.scss +0 -0
  12. package/src/lib/component/bottom-sheet/bottom-sheet.component.spec.ts +23 -0
  13. package/src/lib/component/bottom-sheet/bottom-sheet.component.ts +19 -0
  14. package/src/lib/component/button/button.component.css +0 -0
  15. package/src/lib/component/button/button.component.html +54 -0
  16. package/src/lib/component/button/button.component.spec.ts +23 -0
  17. package/src/lib/component/button/button.component.ts +17 -0
  18. package/src/lib/component/button-toggle/button-toggle.component.html +21 -0
  19. package/src/lib/component/button-toggle/button-toggle.component.scss +0 -0
  20. package/src/lib/component/button-toggle/button-toggle.component.spec.ts +23 -0
  21. package/src/lib/component/button-toggle/button-toggle.component.ts +26 -0
  22. package/src/lib/component/checkbox/checkbox.component.html +6 -0
  23. package/src/lib/component/checkbox/checkbox.component.scss +0 -0
  24. package/src/lib/component/checkbox/checkbox.component.spec.ts +23 -0
  25. package/src/lib/component/checkbox/checkbox.component.ts +17 -0
  26. package/src/lib/component/chips/chip.component.html +75 -0
  27. package/src/lib/component/chips/chip.component.scss +3 -0
  28. package/src/lib/component/chips/chip.component.spec.ts +23 -0
  29. package/src/lib/component/chips/chip.component.ts +125 -0
  30. package/src/lib/component/date-picker/date-picker.component.html +18 -0
  31. package/src/lib/component/date-picker/date-picker.component.scss +0 -0
  32. package/src/lib/component/date-picker/date-picker.component.spec.ts +23 -0
  33. package/src/lib/component/date-picker/date-picker.component.ts +13 -0
  34. package/src/lib/component/dialog/dialog.component.html +12 -0
  35. package/src/lib/component/dialog/dialog.component.scss +3 -0
  36. package/src/lib/component/dialog/dialog.component.spec.ts +23 -0
  37. package/src/lib/component/dialog/dialog.component.ts +12 -0
  38. package/src/lib/component/pagination/pagination.component.html +10 -0
  39. package/src/lib/component/pagination/pagination.component.scss +0 -0
  40. package/src/lib/component/pagination/pagination.component.spec.ts +23 -0
  41. package/src/lib/component/pagination/pagination.component.ts +86 -0
  42. package/src/lib/component/progress-bar/progress-bar.component.html +1 -0
  43. package/src/lib/component/progress-bar/progress-bar.component.scss +0 -0
  44. package/src/lib/component/progress-bar/progress-bar.component.spec.ts +23 -0
  45. package/src/lib/component/progress-bar/progress-bar.component.ts +15 -0
  46. package/src/lib/component/progress-spinner/progress-spinner.component.html +7 -0
  47. package/src/lib/component/progress-spinner/progress-spinner.component.scss +0 -0
  48. package/src/lib/component/progress-spinner/progress-spinner.component.spec.ts +23 -0
  49. package/src/lib/component/progress-spinner/progress-spinner.component.ts +16 -0
  50. package/src/lib/component/radio/radio.component.html +13 -0
  51. package/src/lib/component/radio/radio.component.scss +14 -0
  52. package/src/lib/component/radio/radio.component.spec.ts +23 -0
  53. package/src/lib/component/radio/radio.component.ts +29 -0
  54. package/src/lib/component/rich-text-editor/rich-text-editor.component.html +10 -0
  55. package/src/lib/component/rich-text-editor/rich-text-editor.component.scss +0 -0
  56. package/src/lib/component/rich-text-editor/rich-text-editor.component.spec.ts +23 -0
  57. package/src/lib/component/rich-text-editor/rich-text-editor.component.ts +13 -0
  58. package/src/lib/component/select/select.component.html +25 -0
  59. package/src/lib/component/select/select.component.scss +0 -0
  60. package/src/lib/component/select/select.component.spec.ts +23 -0
  61. package/src/lib/component/select/select.component.ts +32 -0
  62. package/src/lib/component/slide-toggle/slide-toggle.component.html +7 -0
  63. package/src/lib/component/slide-toggle/slide-toggle.component.scss +0 -0
  64. package/src/lib/component/slide-toggle/slide-toggle.component.spec.ts +23 -0
  65. package/src/lib/component/slide-toggle/slide-toggle.component.ts +13 -0
  66. package/src/lib/component/slider/slider.component.html +11 -0
  67. package/src/lib/component/slider/slider.component.scss +0 -0
  68. package/src/lib/component/slider/slider.component.spec.ts +23 -0
  69. package/src/lib/component/slider/slider.component.ts +13 -0
  70. package/src/lib/component/snack-bar/snack-bar.component.html +1 -0
  71. package/src/lib/component/snack-bar/snack-bar.component.scss +0 -0
  72. package/src/lib/component/snack-bar/snack-bar.component.spec.ts +23 -0
  73. package/src/lib/component/snack-bar/snack-bar.component.ts +10 -0
  74. package/src/lib/component/table/table.component.html +82 -0
  75. package/src/lib/component/table/table.component.scss +17 -0
  76. package/src/lib/component/table/table.component.spec.ts +23 -0
  77. package/src/lib/component/table/table.component.ts +54 -0
  78. package/src/lib/component/textarea/textarea.component.html +22 -0
  79. package/src/lib/component/textarea/textarea.component.scss +3 -0
  80. package/src/lib/component/textarea/textarea.component.spec.ts +23 -0
  81. package/src/lib/component/textarea/textarea.component.ts +13 -0
  82. package/src/lib/component/textbox/textbox.component.html +27 -0
  83. package/src/lib/component/textbox/textbox.component.scss +3 -0
  84. package/src/lib/component/textbox/textbox.component.spec.ts +23 -0
  85. package/src/lib/component/textbox/textbox.component.ts +13 -0
  86. package/src/lib/control-builder/control-builder.component.html +5 -0
  87. package/src/lib/control-builder/control-builder.component.scss +0 -0
  88. package/src/lib/control-builder/control-builder.component.ts +14 -0
  89. package/src/lib/control-type/AutoComplete.ts +6 -0
  90. package/src/lib/control-type/Button.ts +6 -0
  91. package/src/lib/control-type/ButtonToggle.ts +6 -0
  92. package/src/lib/control-type/CheckBox.ts +6 -0
  93. package/src/lib/control-type/Chip.ts +6 -0
  94. package/src/lib/control-type/DatePicker.ts +6 -0
  95. package/src/lib/control-type/Divider.ts +6 -0
  96. package/src/lib/control-type/Editor.ts +6 -0
  97. package/src/lib/control-type/Radio.ts +6 -0
  98. package/src/lib/control-type/RichTextEditor.ts +6 -0
  99. package/src/lib/control-type/SlideToggle.ts +6 -0
  100. package/src/lib/control-type/Slider.ts +6 -0
  101. package/src/lib/control-type/select.ts +6 -0
  102. package/src/lib/control-type/textarea.ts +6 -0
  103. package/src/lib/control-type/textbox.ts +6 -0
  104. package/src/lib/falcon-core.module.ts +141 -0
  105. package/src/lib/model/constant.ts +32 -0
  106. package/src/lib/model/enum.ts +151 -0
  107. package/src/lib/model/environments.ts +28 -0
  108. package/src/lib/model/interface.ts +310 -0
  109. package/src/lib/model/ivalidator.ts +18 -0
  110. package/src/lib/module/angularmaterial.module.ts +98 -0
  111. package/src/lib/reactive-field.directive.ts +24 -0
  112. package/src/lib/service/appsetting.service.ts +57 -0
  113. package/src/lib/service/http/generic-http-client.ts +205 -0
  114. package/src/lib/service/http/httpInterceptor.ts +36 -0
  115. package/src/lib/service/http/igeneric-http-client.ts +110 -0
  116. package/src/lib/service/logger.service.ts +75 -0
  117. package/src/lib/service/open-id/TokenHelperService.ts +76 -0
  118. package/src/lib/service/open-id/auth-guard.service.ts +25 -0
  119. package/src/lib/service/open-id/auth.service.ts +179 -0
  120. package/src/public-api.ts +35 -0
  121. package/tsconfig.lib.json +15 -0
  122. package/tsconfig.lib.prod.json +10 -0
  123. package/tsconfig.spec.json +14 -0
package/README.md ADDED
@@ -0,0 +1,71 @@
1
+ ## Build
2
+ Run `ng build @falcon-ng/tailwind` to build the project. The build artifacts will be stored in the `dist/` directory.
3
+
4
+ ## In Production
5
+
6
+ - Add the dependencies to the project `npm i @falcon-ng/tailwind`
7
+ ### Publish to NPM
8
+ - `ng build @falcon-ng/tailwind --configuration=production`
9
+ - `npm login`
10
+ - From the project root folder: `cd dist/@falcon-ng/tailwind`
11
+ - `npm publish --access public` access public is for free version
12
+ ### To unplish the package from NPM
13
+ - `npm unpublish @falcon-ng/tailwind@<version>`
14
+ - If publish error or previous version try the below command
15
+ ```
16
+ npm unpublish --force @falcon-ng/tailwind@0.0.1
17
+ npm publish --force --access public
18
+ ```
19
+ - To update the version of the library, cd into the library project
20
+ ```
21
+ npm version <new_Version_No>
22
+ ```
23
+
24
+ ## In Development
25
+
26
+ - During development the best way to consume library is using `npm link`
27
+ ```
28
+ cd dist/@falcon-ng/tailwind
29
+ npm link
30
+ ```
31
+ - We can link an Angular project to this library from anywhere on local machine. From the project root folder:
32
+ ```
33
+ npm link @falcon-ng/tailwind
34
+ ```
35
+ - If we now build the library with the watch flag `ng build @falcon-ng/tailwind --watch`, and at the same time run `ng serve -o` to another project in another terminal window.
36
+ - This will allow us to develop an application and (one or more) linked libraries simultaneously, and see the app recompile with each modification to the library’s source code.
37
+ - add `preserveSymlinks = true` to the `angular.json` located at the other project
38
+ ```
39
+ {
40
+ "architect":
41
+ {
42
+ "build":
43
+ {
44
+ "builder": "@angular-devkit/build-angular:browser",
45
+ "options": {
46
+ "preserveSymlinks": true
47
+ }
48
+ }
49
+ }
50
+ }
51
+ ```
52
+ - Add falcol tailwind module to the project
53
+ ```
54
+ import { FalconCoreModule } from '@falcon-ng/tailwind';
55
+ import {environment} from "../environments/environment";
56
+ @NgModule({
57
+ declarations: [],
58
+ imports:[
59
+ FalconCoreModule.forRoot(environment)
60
+ ],
61
+ bootstrap: [AppComponent]
62
+ })
63
+ ```
64
+
65
+ ## Publish code to GitHub
66
+
67
+ ng build --configuration=production --output-path docs --base-href /<project_name>/
68
+
69
+ Example --> ng build --configuration=production --output-path docs --base-href /Angular-Tailwind-Reusable-Form/
70
+
71
+ - Reference - https://angular.io/guide/deployment
@@ -0,0 +1,7 @@
1
+ {
2
+ "$schema": "../../../node_modules/ng-packagr/ng-package.schema.json",
3
+ "dest": "../../../dist/@falcon-ng/tailwind",
4
+ "lib": {
5
+ "entryFile": "src/public-api.ts"
6
+ }
7
+ }
package/package.json ADDED
@@ -0,0 +1,11 @@
1
+ {
2
+ "name": "@falcon-ng/tailwind",
3
+ "version": "0.0.2",
4
+ "peerDependencies": {
5
+ "@angular/common": "^15.0.0",
6
+ "@angular/core": "^15.0.0"
7
+ },
8
+ "dependencies": {
9
+ "tslib": "^2.3.0"
10
+ }
11
+ }
@@ -0,0 +1,142 @@
1
+ import {ControlType} from './model/enum';
2
+ import {IValidator} from './model/ivalidator';
3
+ import {
4
+ FloatLabelType,
5
+ MatFormFieldAppearance,
6
+ } from '@angular/material/form-field';
7
+ import {
8
+ IComponentEvent,
9
+ IMatHint,
10
+ IOptions,
11
+ ISelectOptions, ISliderProperty,
12
+ ISuffixPrefixConfig,
13
+ ITextAreaProperty,
14
+ } from './model/interface';
15
+
16
+ /**
17
+ * @description
18
+ * Class use for setting the layout.
19
+ * @usageNotes
20
+ * ```ts
21
+ * new Dropdown({
22
+ * key: 'brave',
23
+ * label: 'Bravery Rating',
24
+ * options: [
25
+ * {key: 'solid', value: 'Solid'},
26
+ * {key: 'great', value: 'Great'},
27
+ * {key: 'good', value: 'Good'},
28
+ * {key: 'unproven', value: 'Unproven'}
29
+ * ],
30
+ * order: 3
31
+ * }),
32
+ ** ```
33
+ */
34
+ export interface Layout<T> {
35
+ class?: string;
36
+ baseControls: BaseControl<T>[];
37
+ }
38
+
39
+ /**
40
+ * @description
41
+ * Class use for setting the control properties.
42
+ * @usageNotes
43
+ * ```ts
44
+ * new Dropdown({
45
+ * formControlName: 'brave',
46
+ * label: 'Bravery Rating',
47
+ * options: [
48
+ * {key: 'solid', value: 'Solid'},
49
+ * {key: 'great', value: 'Great'},
50
+ * {key: 'good', value: 'Good'},
51
+ * {key: 'unproven', value: 'Unproven'}
52
+ * ],
53
+ * order: 3
54
+ * }),
55
+ ** ```
56
+ */
57
+ export class BaseControl<T> {
58
+ value: T | undefined;
59
+ formControlName: string;
60
+ label: string;
61
+ labelPosition: any;
62
+ order: number;
63
+ controlType: ControlType;
64
+ type: string;
65
+ disabled: boolean;
66
+ options: IOptions[] | any;
67
+ validations: IValidator[];
68
+ appearance: MatFormFieldAppearance | any;
69
+ class: string;
70
+ style: { [klass: string]: any };
71
+ placeHolder: string;
72
+ floatLabel: FloatLabelType;
73
+ hint: IMatHint;
74
+ suffix: ISuffixPrefixConfig;
75
+ prefix: ISuffixPrefixConfig;
76
+ textAreaProperty: ITextAreaProperty;
77
+ event: IComponentEvent<T>;
78
+ selectProperty: ISelectOptions;
79
+ color: string;
80
+ sliderProperty: ISliderProperty;
81
+ chipSelectedOptions: IOptions[] | any;
82
+ editorProperty: any;
83
+ formArray: BaseControl<T>[] | undefined;
84
+ constructor(
85
+ options: {
86
+ value?: T;
87
+ formControlName?: string;
88
+ label?: string;
89
+ labelPosition?: any;
90
+ order?: number;
91
+ controlType?: ControlType;
92
+ type?: string;
93
+ disabled?: boolean;
94
+ options?: IOptions[] | any;
95
+ validations?: IValidator[];
96
+ appearance?: MatFormFieldAppearance | any;
97
+ class?: string;
98
+ style?: { [klass: string]: any };
99
+ placeHolder?: string;
100
+ floatLabel?: FloatLabelType;
101
+ hint?: IMatHint;
102
+ suffix?: ISuffixPrefixConfig;
103
+ prefix?: ISuffixPrefixConfig;
104
+ textAreaProperty?: ITextAreaProperty;
105
+ event?: IComponentEvent<T>;
106
+ selectProperty?: ISelectOptions;
107
+ color?: string;
108
+ sliderProperty?: ISliderProperty;
109
+ chipSelectedOptions?: IOptions[] | any;
110
+ editorProperty?: any;
111
+ formArray?: BaseControl<T>[];
112
+ } = {}
113
+ ) {
114
+ this.value = options.value;
115
+ this.formControlName = options.formControlName || '';
116
+ this.label = options.label || '';
117
+ this.labelPosition = options.labelPosition || 'before' || 'after';
118
+ this.order = options.order === undefined ? 1 : options.order;
119
+ this.controlType = options.controlType || ControlType.Button;
120
+ this.type = options.type || '';
121
+ this.disabled = options.disabled || false;
122
+ this.options = options.options || [];
123
+ this.validations = options.validations || [];
124
+ this.appearance = options.appearance || 'outline';
125
+ this.class = options.class || '';
126
+ this.style = options.style || {};
127
+ this.placeHolder = options.placeHolder || '';
128
+ this.floatLabel = options.floatLabel || 'auto';
129
+ this.hint = options.hint || ({} as IMatHint);
130
+ this.prefix = options.prefix || ({} as ISuffixPrefixConfig);
131
+ this.suffix = options.suffix || ({} as ISuffixPrefixConfig);
132
+ this.textAreaProperty =
133
+ options.textAreaProperty || ({} as ITextAreaProperty);
134
+ this.event = options.event || {};
135
+ this.selectProperty = options.selectProperty || {};
136
+ this.color = options.color || '';
137
+ this.sliderProperty = options.sliderProperty || {};
138
+ this.chipSelectedOptions = options.chipSelectedOptions || {};
139
+ this.editorProperty = options.editorProperty || {};
140
+ this.formArray = options.formArray || undefined
141
+ }
142
+ }
@@ -0,0 +1,363 @@
1
+ import {Observable} from 'rxjs';
2
+ import {
3
+ FormBuilder,
4
+ FormControl,
5
+ FormGroup,
6
+ ValidatorFn,
7
+ Validators,
8
+ } from '@angular/forms';
9
+ import {BaseControl, Layout} from './base-control';
10
+ import {inject} from '@angular/core';
11
+ import {IValidator} from './model/ivalidator';
12
+ import {ControlType} from './model/enum';
13
+
14
+ /**
15
+ * @description
16
+ * Base form component initialized to create form controls, set validation, submit.
17
+ *
18
+ * @usageNotes
19
+ * The following snippet shows how a component can implement this abstract class to
20
+ * define its own initialization method.
21
+ * ```ts
22
+ * export class InputComponent extends BaseFormComponent<any> implements OnInit {
23
+ * constructor(fb : FormBuilder) {
24
+ * super(fb);
25
+ * this.defineForm();
26
+ * }
27
+ * protected defineForm(): void {
28
+ * }
29
+ * ngOnInit(): void {
30
+ * this.formGroup = this.createControls();
31
+ * }
32
+ * protected submitDatasource(model: any): Observable<any> {
33
+ * return of(model);
34
+ * }
35
+ * ```
36
+ */
37
+ export abstract class BaseFormComponent<T> {
38
+ public formGroup!: FormGroup;
39
+
40
+ protected abstract defineForm(): void;
41
+
42
+ protected abstract submitDataSource(model: T): Observable<T>;
43
+
44
+ public dataSource: T | undefined = undefined;
45
+ public controlsConfig!: Layout<T>;
46
+ public showLoading: boolean = false;
47
+ protected fb = inject(FormBuilder);
48
+
49
+ constructor() {
50
+ }
51
+
52
+ /**
53
+ * @description
54
+ * Method evoke on when the form is submitted.
55
+ * @returns submitDatasource() method with form data if valid otherwise form invalid.
56
+ */
57
+ public onSubmit() {
58
+ if (this.formGroup !== undefined && this.formGroup.valid) {
59
+ this.submitDataSource(this.formGroup.value);
60
+ } else {
61
+ this.validateAllFormFields(this.formGroup);
62
+ }
63
+ }
64
+
65
+ /**
66
+ * @description
67
+ * Private method to validate all form controls before is form submited.
68
+ * @param formGroup Validate form group.
69
+ * @returns Groups of controls added to the form builder.
70
+ */
71
+ private validateAllFormFields(formGroup: FormGroup) {
72
+ if (this.formGroup !== undefined) this.formGroup.markAllAsTouched();
73
+ }
74
+
75
+ /**
76
+ * @description
77
+ * Create the reactive form controls
78
+ * @returns Groups of controls added to the form builder.
79
+ */
80
+ protected createControls() {
81
+ const group = this.fb.group({});
82
+ this.controlsConfig.baseControls.forEach((controls, index) => {
83
+ this.bindControl(controls, group, index);
84
+ });
85
+ return group;
86
+ }
87
+
88
+ /**
89
+ * @description
90
+ * Private method to bind the form control.
91
+ * @param controlConfig field to bind.
92
+ * @param group group to add.
93
+ * @param index index of the layout
94
+ */
95
+ private bindControl(
96
+ controlConfig: BaseControl<T>,
97
+ group: FormGroup,
98
+ index: number
99
+ ) {
100
+ if (controlConfig.controlType === ControlType.Button) return;
101
+ let control = null;
102
+ if (controlConfig.formArray !== undefined) {
103
+ control =
104
+ controlConfig.formArray.length > 0
105
+ ? this.fb.array([
106
+ this.createFormArrayGroup(
107
+ controlConfig.formArray[
108
+ controlConfig.formArray.length - 1
109
+ ].formArray,
110
+ ),
111
+ ])
112
+ : this.fb.array(
113
+ [],
114
+ this.bindValidations(controlConfig.validations || []),
115
+ );
116
+ } else {
117
+ control = this.fb.control(
118
+ {
119
+ value: controlConfig.value,
120
+ disabled: controlConfig.disabled,
121
+ },
122
+ this.bindValidations(controlConfig.validations || [])
123
+ );
124
+ }
125
+ group.addControl(controlConfig.formControlName, control);
126
+ }
127
+
128
+ /**
129
+ * @description
130
+ * Private method to bind the validation to the form controls on form submit.
131
+ * @param validations Push the validation to the controls.
132
+ * @returns Validation.
133
+ */
134
+ private bindValidations(validations: IValidator[]) {
135
+ if (validations.length > 0) {
136
+ const validList: (ValidatorFn | null | undefined)[] = [];
137
+ validations.forEach((valid: IValidator) => {
138
+ validList.push(valid.validator);
139
+ });
140
+ return Validators.compose(validList);
141
+ }
142
+ return null;
143
+ }
144
+
145
+ /**
146
+ * Create an form array element
147
+ * @param layoutConfig layout of form array
148
+ * @returns Form array group
149
+ */
150
+ private createFormArrayGroup(componentConfig: BaseControl<T>[] | undefined): FormGroup {
151
+ var formGroup: FormGroup = this.fb.group({});
152
+ componentConfig?.forEach((item, index) => {
153
+ var control = null;
154
+ if (item.formArray !== undefined) {
155
+ control =
156
+ item.formArray.length > 0
157
+ ? this.fb.array(
158
+ [
159
+ this.createFormArrayGroup(
160
+ item.formArray[item.formArray.length - 1].formArray,
161
+ ),
162
+ ],
163
+ this.bindValidations(item.validations || []),
164
+ )
165
+ : this.fb.array(
166
+ [],
167
+ this.bindValidations(item.validations || []),
168
+ );
169
+ } else {
170
+ control = this.fb.control(
171
+ {
172
+ value: item.value,
173
+ disabled: item.disabled,
174
+ },
175
+ this.bindValidations(item.validations || []),
176
+ );
177
+ }
178
+ formGroup.addControl(item.formControlName, control);
179
+ });
180
+ return formGroup;
181
+ }
182
+
183
+ /**
184
+ * @description
185
+ * Reset fild values to default or specify some value.
186
+ * @param defaultValues Specify the specific value to set to the controls.
187
+ * @returns void.
188
+ */
189
+ public reset(defaultValues?: any): void {
190
+ this.formGroup.reset(defaultValues);
191
+ }
192
+
193
+ /**
194
+ * @description
195
+ * Reset specific fild Errors.
196
+ * @param name Name of the field to reset the error.
197
+ * @returns void.
198
+ */
199
+ resetFieldErrors(name: string): void {
200
+ this.formGroup?.get(name)?.setErrors(null);
201
+ }
202
+
203
+ /**
204
+ * @description
205
+ * Get the controls value from the form.
206
+ * @returns Form controls values.
207
+ */
208
+ get value(): any {
209
+ return this.formGroup.value;
210
+ }
211
+
212
+ /**
213
+ * @description
214
+ * Updating parts of the data model.
215
+ * Use the patchValue() method to replace any properties defined in the object that have changed in the form model.
216
+ * @returns Form controls values.
217
+ * @param value The object that matches the structure of the group.
218
+ * @param options Configuration options that determine how the control propagates changes and
219
+ * emits events after the value is patched.
220
+ * `onlySelf`: When true, each change only affects this control and not its parent. Default is
221
+ * true.
222
+ * `emitEvent`: When true or not supplied (the default), both the `statusChanges` and
223
+ * `valueChanges`
224
+ * @usageNotes
225
+ * The following snippet shows how a component can implement this abstract class to
226
+ * define its own initialization method.
227
+ * ```ts
228
+ * this.formGroup.patchValue({
229
+ * name: 'Todd Motto',
230
+ * event: {
231
+ * title: 'AngularCamp 2016',
232
+ * location: 'Barcelona, Spain'
233
+ * }
234
+ * });
235
+ * ```
236
+ */
237
+ protected patchValue(
238
+ value: { [key: string]: any },
239
+ options?: { onlySelf?: boolean; emitEvent?: boolean }
240
+ ) {
241
+ return this.formGroup.patchValue(value, options);
242
+ }
243
+
244
+ /**
245
+ * @description
246
+ * Updating parts of the data model.
247
+ * Use the setValue() method to set a new value for an individual control. The setValue() method strictly adheres to the structure of the form group and replaces the entire value for the control.
248
+ * @returns Form controls values.
249
+ * @param value The object that matches the structure of the group.
250
+ * @param options Configuration options that determine how the control propagates changes and
251
+ * emits events after the value is patched.
252
+ * `onlySelf`: When true, each change only affects this control and not its parent. Default is
253
+ * true.
254
+ * `emitEvent`: When true or not supplied (the default), both the `statusChanges` and
255
+ * `valueChanges`
256
+ * @usageNotes
257
+ * The following snippet shows how a component can implement this abstract class to
258
+ * define its own initialization method.
259
+ * ```ts
260
+ * this.formGroup.setValue({
261
+ * name: 'Todd Motto',
262
+ * event: {
263
+ * title: 'AngularCamp 2016',
264
+ * location: 'Barcelona, Spain'
265
+ * }
266
+ * });
267
+ * ```
268
+ */
269
+ protected setValue(
270
+ value: { [key: string]: any },
271
+ options?: { onlySelf?: boolean; emitEvent?: boolean }
272
+ ) {
273
+ return this.formGroup.setValue(value, options);
274
+ }
275
+
276
+ /**
277
+ * @description
278
+ * Dynamically remove the form control.
279
+ * @param index Index of item.
280
+ * @usageNotes
281
+ * The following snippet shows how to remove the form control from Froup Group
282
+ * ```ts
283
+ * removeControl(1);
284
+ * ```
285
+ */
286
+ protected removeControl(layoutIndex: number, index: number) {
287
+ this.formGroup.removeControl(
288
+ this.controlsConfig.baseControls[layoutIndex].formControlName
289
+ );
290
+ this.controlsConfig.baseControls.splice(index, 1);
291
+ }
292
+
293
+ /**
294
+ * @description
295
+ * Dynamically add the form control.
296
+ * @param configToAdd Configuration of the form control.
297
+ * @param index Add controls to the specific index.
298
+ * @usageNotes
299
+ * The following snippet shows how a component can implement this abstract class to
300
+ * define its own initialization method.
301
+ * ```ts
302
+ * var configToadd = {
303
+ * componentProperty: {
304
+ * label: "Outline Auto complete",
305
+ * options: [{ value: 'Extra-cheese', viewValue: 'Extra cheese' },
306
+ * { value: 'Bellsprout', viewValue: 'Bellsprout' },
307
+ * { value: 'Mushroom', viewValue: 'Mushroom' },
308
+ * { value: 'Onion', viewValue: 'Onion' },
309
+ * { value: 'Pepperoni', viewValue: 'Pepperoni' },
310
+ * { value: 'Sausage', viewValue: 'Sausage' },
311
+ * { value: 'Tomato', viewValue: 'Tomato' }],
312
+ * appearance: Appearance.Outline,
313
+ * color: 'accent'
314
+ * },
315
+ * componentType: ComponentType.AutoComplete,
316
+ * formControlName: "test"
317
+ * };
318
+ * this.addControl(configToadd); or this.addControl(configToadd,1);
319
+ * ```
320
+ */
321
+ // protected addControl(layoutToAdd?: BaseControl<string>[],index?: number) {
322
+ // layoutToAdd.forEach((layout, layoutIndex) => {
323
+ // layout.componentConfig.forEach(
324
+ // (componentConfig, componentIndex) => {
325
+ // if (componentConfig.formArray !== undefined) {
326
+ // componentConfig.formArray.forEach((control) => {
327
+ // this.formGroup.setControl(
328
+ // 'productOption',
329
+ // this.createFormArrayGroup(control.componentConfig),
330
+ // );
331
+ // this.controlsConfig.container.layoutConfig[1].componentConfig[0].formArray.push(
332
+ // layout,
333
+ // );
334
+ // });
335
+ // } else {
336
+ // this.formGroup.addControl(
337
+ // componentConfig.formControlName,
338
+ // new UntypedFormControl(
339
+ // {
340
+ // value: componentConfig.componentProperty.value,
341
+ // disabled:
342
+ // componentConfig.componentProperty.disabled,
343
+ // },
344
+ // this.bindValidations(
345
+ // componentConfig.validations || [],
346
+ // ),
347
+ // ),
348
+ // );
349
+ // index !== null
350
+ // ? this.controlsConfig.container.layoutConfig.splice(
351
+ // index,
352
+ // 0,
353
+ // layout,
354
+ // )
355
+ // : this.controlsConfig.container.layoutConfig.push(
356
+ // layout,
357
+ // );
358
+ // }
359
+ // },
360
+ // );
361
+ // });
362
+ // }
363
+ }
@@ -0,0 +1,39 @@
1
+ <mat-form-field *ngIf="control.appearance != 'plain'; else plainInput" [appearance]="control.appearance"
2
+ [formGroup]="formGroup" [ngStyle]="control.style" [ngClass]="control.class">
3
+ <mat-label>{{control.label}}</mat-label>
4
+ <input matInput [formControl]="autoCompleteControl" [formControlName]="control.formControlName"
5
+ [placeholder]="control.placeHolder" [type]="control.type" [ngStyle]="control.style" [ngClass]="control.class"
6
+ [matAutocomplete]="auto"
7
+ [required]="formGroup.get(control.formControlName)?.errors !== null && formGroup.get(control.formControlName)?.errors?.['required']">
8
+ <mat-autocomplete #auto="matAutocomplete" (optionSelected)='optionSelected($event.option.viewValue)'>
9
+ <mat-option *ngFor="let item of filteredOptions | async" [value]="item.key">
10
+ {{item.value}}
11
+ </mat-option>
12
+ </mat-autocomplete>
13
+
14
+ <span matPrefix [matTooltip]="control.prefix.toolTipText!"
15
+ [ngClass]="{'material-icons': control.prefix.isIcon}">{{control.prefix.text}} &nbsp;&nbsp;</span>
16
+ <span matSuffix [matTooltip]="control.suffix.toolTipText!"
17
+ [ngClass]="{'material-icons': control.suffix.isIcon}">{{control.suffix.text}} &nbsp;&nbsp;</span>
18
+
19
+ <mat-hint>{{control.hint.text}}</mat-hint>
20
+ <ng-container *ngFor="let validation of control.validations;" ngProjectAs="mat-error">
21
+ <mat-error *ngIf="formGroup.get(control.formControlName)?.hasError(validation.name)">{{validation.message}}
22
+ </mat-error>
23
+ </ng-container>
24
+ </mat-form-field>
25
+
26
+ <ng-template #plainInput>
27
+ <div [formGroup]="formGroup" [ngStyle]="control.style" [ngClass]="control.class">
28
+ <input type="text" [formControl]="autoCompleteControl" [formControlName]="control.formControlName"
29
+ [placeholder]="control.placeHolder" [type]="control.type" [ngStyle]="control.style" [ngClass]="control.class"
30
+ [matAutocomplete]="auto"
31
+ [required]="formGroup.get(control.formControlName)?.errors !== null && formGroup.get(control.formControlName)?.errors?.['required']"
32
+ class="bg-gray-200 appearance-none border-2 border-gray-200 rounded w-full py-2 px-4 text-gray-700 leading-tight focus:outline-none focus:bg-white focus:border-purple-500">
33
+ </div>
34
+ <mat-autocomplete #auto="matAutocomplete" (optionSelected)='optionSelected($event.option.viewValue)'>
35
+ <mat-option *ngFor="let item of filteredOptions | async" [value]="item.key">
36
+ {{item.value}}
37
+ </mat-option>
38
+ </mat-autocomplete>
39
+ </ng-template>
@@ -0,0 +1,23 @@
1
+ import { ComponentFixture, TestBed } from '@angular/core/testing';
2
+
3
+ import { AutoCompleteComponent } from './auto-complete.component';
4
+
5
+ describe('AutoCompleteComponent', () => {
6
+ let component: AutoCompleteComponent;
7
+ let fixture: ComponentFixture<AutoCompleteComponent>;
8
+
9
+ beforeEach(async () => {
10
+ await TestBed.configureTestingModule({
11
+ declarations: [ AutoCompleteComponent ]
12
+ })
13
+ .compileComponents();
14
+
15
+ fixture = TestBed.createComponent(AutoCompleteComponent);
16
+ component = fixture.componentInstance;
17
+ fixture.detectChanges();
18
+ });
19
+
20
+ it('should create', () => {
21
+ expect(component).toBeTruthy();
22
+ });
23
+ });
@@ -0,0 +1,31 @@
1
+ import { Component, OnInit, Input } from '@angular/core';
2
+ import {BaseControl} from "../../base-control";
3
+ import {FormControl, FormGroup} from "@angular/forms";
4
+ import {IOptions} from "../../model/interface";
5
+ import {Observable} from "rxjs";
6
+ import { map, startWith } from 'rxjs/operators';
7
+ @Component({
8
+ selector: 'falcon-auto-complete',
9
+ templateUrl: './auto-complete.component.html',
10
+ styleUrls: ['./auto-complete.component.scss'],
11
+ })
12
+ export class AutoCompleteComponent {
13
+ control!: BaseControl<string>;
14
+ formGroup!: FormGroup;
15
+ autoCompleteControl = new FormControl();
16
+ constructor() { }
17
+ filteredOptions!: Observable<IOptions[]>;
18
+
19
+ ngOnInit() {
20
+ this.filteredOptions = this.autoCompleteControl.valueChanges.pipe(startWith(''),map(value => this._filter(value)));
21
+ }
22
+
23
+ private _filter(value: string): IOptions[] {
24
+ const filterValue = value.toLowerCase();
25
+ return this.control.options.filter((option: IOptions) => option?.key?.toLowerCase().includes(filterValue));
26
+ }
27
+
28
+ optionSelected(value: any) {
29
+ this.formGroup?.get(this.control?.formControlName)?.setValue(value);
30
+ }
31
+ }