@syncfusion/ej2-inputs 30.2.4 → 31.1.17

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 (110) hide show
  1. package/dist/ej2-inputs.min.js +2 -2
  2. package/dist/ej2-inputs.umd.min.js +2 -2
  3. package/dist/ej2-inputs.umd.min.js.map +1 -1
  4. package/dist/es6/ej2-inputs.es2015.js +1 -1
  5. package/dist/es6/ej2-inputs.es2015.js.map +1 -1
  6. package/dist/es6/ej2-inputs.es5.js +1 -1
  7. package/dist/es6/ej2-inputs.es5.js.map +1 -1
  8. package/dist/global/ej2-inputs.min.js +2 -2
  9. package/dist/global/ej2-inputs.min.js.map +1 -1
  10. package/dist/global/index.d.ts +1 -1
  11. package/dist/ts/color-picker/color-picker-model.d.ts +186 -0
  12. package/dist/ts/color-picker/color-picker.d.ts +398 -0
  13. package/dist/ts/color-picker/color-picker.ts +2209 -0
  14. package/dist/ts/color-picker/index.d.ts +5 -0
  15. package/dist/ts/color-picker/index.ts +5 -0
  16. package/dist/ts/common/index.d.ts +4 -0
  17. package/dist/ts/common/index.ts +4 -0
  18. package/dist/ts/common/signature-base.d.ts +340 -0
  19. package/dist/ts/common/signature-base.ts +1170 -0
  20. package/dist/ts/form-validator/form-validator-model.d.ts +121 -0
  21. package/dist/ts/form-validator/form-validator.d.ts +312 -0
  22. package/dist/ts/form-validator/form-validator.ts +1068 -0
  23. package/dist/ts/form-validator/index.d.ts +5 -0
  24. package/dist/ts/form-validator/index.ts +5 -0
  25. package/dist/ts/index.d.ts +18 -0
  26. package/dist/ts/index.ts +18 -0
  27. package/dist/ts/input/index.d.ts +4 -0
  28. package/dist/ts/input/index.ts +4 -0
  29. package/dist/ts/input/input.d.ts +345 -0
  30. package/dist/ts/input/input.ts +1277 -0
  31. package/dist/ts/maskedtextbox/base/index.d.ts +4 -0
  32. package/dist/ts/maskedtextbox/base/index.ts +4 -0
  33. package/dist/ts/maskedtextbox/base/mask-base.d.ts +134 -0
  34. package/dist/ts/maskedtextbox/base/mask-base.ts +1207 -0
  35. package/dist/ts/maskedtextbox/index.d.ts +5 -0
  36. package/dist/ts/maskedtextbox/index.ts +5 -0
  37. package/dist/ts/maskedtextbox/maskedtextbox/index.d.ts +5 -0
  38. package/dist/ts/maskedtextbox/maskedtextbox/index.ts +5 -0
  39. package/dist/ts/maskedtextbox/maskedtextbox/maskedtextbox-model.d.ts +167 -0
  40. package/dist/ts/maskedtextbox/maskedtextbox/maskedtextbox.d.ts +307 -0
  41. package/dist/ts/maskedtextbox/maskedtextbox/maskedtextbox.ts +709 -0
  42. package/dist/ts/numerictextbox/index.d.ts +5 -0
  43. package/dist/ts/numerictextbox/index.ts +5 -0
  44. package/dist/ts/numerictextbox/numerictextbox-model.d.ts +228 -0
  45. package/dist/ts/numerictextbox/numerictextbox.d.ts +431 -0
  46. package/dist/ts/numerictextbox/numerictextbox.ts +1672 -0
  47. package/dist/ts/otp-input/index.d.ts +5 -0
  48. package/dist/ts/otp-input/index.ts +5 -0
  49. package/dist/ts/otp-input/otp-input-model.d.ts +165 -0
  50. package/dist/ts/otp-input/otp-input.d.ts +365 -0
  51. package/dist/ts/otp-input/otp-input.ts +924 -0
  52. package/dist/ts/rating/index.d.ts +5 -0
  53. package/dist/ts/rating/index.ts +5 -0
  54. package/dist/ts/rating/rating-model.d.ts +239 -0
  55. package/dist/ts/rating/rating.d.ts +416 -0
  56. package/dist/ts/rating/rating.ts +1101 -0
  57. package/dist/ts/signature/index.d.ts +5 -0
  58. package/dist/ts/signature/index.ts +5 -0
  59. package/dist/ts/signature/signature-model.d.ts +131 -0
  60. package/dist/ts/signature/signature.d.ts +167 -0
  61. package/dist/ts/signature/signature.ts +266 -0
  62. package/dist/ts/slider/index.d.ts +5 -0
  63. package/dist/ts/slider/index.ts +5 -0
  64. package/dist/ts/slider/slider-model.d.ts +401 -0
  65. package/dist/ts/slider/slider.d.ts +721 -0
  66. package/dist/ts/slider/slider.ts +3497 -0
  67. package/dist/ts/smart-textarea/caret-helper.d.ts +17 -0
  68. package/dist/ts/smart-textarea/caret-helper.ts +95 -0
  69. package/dist/ts/smart-textarea/index.d.ts +5 -0
  70. package/dist/ts/smart-textarea/index.ts +5 -0
  71. package/dist/ts/smart-textarea/smart-textarea-model.d.ts +44 -0
  72. package/dist/ts/smart-textarea/smart-textarea.d.ts +80 -0
  73. package/dist/ts/smart-textarea/smart-textarea.ts +518 -0
  74. package/dist/ts/speech-to-text/index.d.ts +5 -0
  75. package/dist/ts/speech-to-text/index.ts +5 -0
  76. package/dist/ts/speech-to-text/speech-to-text-model.d.ts +270 -0
  77. package/dist/ts/speech-to-text/speech-to-text.d.ts +487 -0
  78. package/dist/ts/speech-to-text/speech-to-text.ts +1008 -0
  79. package/dist/ts/textarea/index.d.ts +5 -0
  80. package/dist/ts/textarea/index.ts +5 -0
  81. package/dist/ts/textarea/textarea-model.d.ts +161 -0
  82. package/dist/ts/textarea/textarea.d.ts +237 -0
  83. package/dist/ts/textarea/textarea.ts +812 -0
  84. package/dist/ts/textbox/index.d.ts +5 -0
  85. package/dist/ts/textbox/index.ts +5 -0
  86. package/dist/ts/textbox/textbox-model.d.ts +155 -0
  87. package/dist/ts/textbox/textbox.d.ts +288 -0
  88. package/dist/ts/textbox/textbox.ts +872 -0
  89. package/dist/ts/uploader/index.d.ts +5 -0
  90. package/dist/ts/uploader/index.ts +5 -0
  91. package/dist/ts/uploader/uploader-model.d.ts +555 -0
  92. package/dist/ts/uploader/uploader.d.ts +1216 -0
  93. package/dist/ts/uploader/uploader.ts +4391 -0
  94. package/package.json +62 -12
  95. package/src/input/input.js +1 -1
  96. package/styles/bootstrap5.3-lite.css +3 -3
  97. package/styles/bootstrap5.3.css +5 -5
  98. package/styles/input/_layout.scss +0 -1
  99. package/styles/input/tailwind3.css +0 -1
  100. package/styles/tailwind-dark-lite.css +3 -3
  101. package/styles/tailwind-dark.css +5 -5
  102. package/styles/tailwind-lite.css +3 -3
  103. package/styles/tailwind.css +5 -5
  104. package/styles/tailwind3-lite.css +0 -1
  105. package/styles/tailwind3.css +0 -1
  106. package/styles/uploader/_bootstrap5.3-definition.scss +1 -1
  107. package/styles/uploader/_tailwind-definition.scss +1 -1
  108. package/styles/uploader/bootstrap5.3.css +5 -5
  109. package/styles/uploader/tailwind-dark.css +5 -5
  110. package/styles/uploader/tailwind.css +5 -5
@@ -0,0 +1,1101 @@
1
+ import { addClass, Event, attributes, BaseEventArgs, compile, Component, EmitType, EventHandler, getUniqueID, INotifyPropertyChanged, select, Browser, append } from '@syncfusion/ej2-base';
2
+ import { isNullOrUndefined, KeyboardEventArgs, KeyboardEvents, MouseEventArgs, NotifyPropertyChanges, Property, remove, removeClass, initializeCSPTemplate, closest } from '@syncfusion/ej2-base';
3
+ import { Tooltip } from '@syncfusion/ej2-popups';
4
+ import { RatingModel } from './rating-model';
5
+
6
+ const ICONCSS: string = 'e-rating-icon e-icons e-star-filled';
7
+ const ITEMLIST: string = 'e-rating-item-list';
8
+ const ITEMCONTAINER: string = 'e-rating-item-container';
9
+ const SELECTED: string = 'e-rating-selected';
10
+ const INTERMEDIATE: string = 'e-rating-intermediate';
11
+ const LABEL: string = 'e-rating-label';
12
+ const RESET: string = 'e-icons e-reset';
13
+ const HIDDEN: string = 'e-rating-hidden';
14
+ const DISABLED: string = 'e-disabled';
15
+ const READONLY: string = 'e-rating-readonly';
16
+ const RTL: string = 'e-rtl';
17
+ const ANIMATION: string = 'e-rating-animation';
18
+ const FULLTEMPLATE: string = 'e-rating-full';
19
+ const EMPTYTEMPLATE: string = 'e-rating-empty';
20
+ const SELECTEDVALUE: string = 'e-selected-value';
21
+
22
+ const RATINGVALUE: string = '--rating-value';
23
+
24
+ /**
25
+ * Defines where to position the label in rating
26
+ */
27
+ export enum LabelPosition {
28
+ /**
29
+ * The label is positioned at the top center of the rating component.
30
+ */
31
+ Top = 'Top',
32
+ /**
33
+ * The label is positioned at the bottom center of the rating component.
34
+ */
35
+ Bottom = 'Bottom',
36
+ /**
37
+ * The label is positioned at the left side of the rating component.
38
+ */
39
+ Left = 'Left',
40
+ /**
41
+ * The label is positioned at the right side of the rating component.
42
+ */
43
+ Right = 'Right'
44
+ }
45
+
46
+ /**
47
+ * Defines the precision type of the rating.
48
+ * It is used to component the granularity of the rating, allowing users to provide ratings with varying levels of precision.
49
+ */
50
+ export enum PrecisionType {
51
+ /**
52
+ * The rating is increased in whole number increments.
53
+ */
54
+ Full = 'Full',
55
+ /**
56
+ * The rating is increased in increments of 0.5 (half).
57
+ */
58
+ Half = 'Half',
59
+ /**
60
+ * The rating is increased in increments of 0.25 (quarter).
61
+ */
62
+ Quarter = 'Quarter',
63
+ /**
64
+ * The rating is increased in increments of 0.1.
65
+ */
66
+ Exact = 'Exact'
67
+ }
68
+
69
+ /**
70
+ * Provides information about valueChanged event callback
71
+ */
72
+ export interface RatingChangedEventArgs extends BaseEventArgs {
73
+ /**
74
+ * Provides the original event
75
+ */
76
+ event: Event;
77
+
78
+ /**
79
+ * Provides whether the change is triggered by user interaction.
80
+ */
81
+ isInteracted: boolean;
82
+
83
+ /**
84
+ * Provides the previous value.
85
+ */
86
+ previousValue: number;
87
+
88
+ /**
89
+ * Provides the current value.
90
+ */
91
+ value: number;
92
+ }
93
+
94
+ /**
95
+ * Provides information about onItemHover event callback.
96
+ */
97
+ export interface RatingHoverEventArgs extends BaseEventArgs {
98
+ /**
99
+ * Provides the rating item element reference.
100
+ */
101
+ element: HTMLElement;
102
+
103
+ /**
104
+ * Provides the original event.
105
+ */
106
+ event: Event;
107
+
108
+ /**
109
+ * Provides the hover value at hovered point of rating.
110
+ */
111
+ value: number;
112
+ }
113
+
114
+ /**
115
+ * Provides information about beforeItemRender event callback.
116
+ */
117
+ export interface RatingItemEventArgs extends BaseEventArgs {
118
+ /**
119
+ * Provides the rating item element reference.
120
+ */
121
+ element: HTMLElement;
122
+
123
+ /**
124
+ * Provides the place value of the item.
125
+ */
126
+ value: number;
127
+ }
128
+
129
+ /**
130
+ * The Rating component allows the user to rate something by clicking on a set of symbols on a numeric scale.
131
+ * This allows users to provide feedback or ratings for products, services, or content.
132
+ *
133
+ * ```html
134
+ * <input id="rating">
135
+ * ```
136
+ * ```typescript
137
+ * <script>
138
+ * let ratingObj: Rating = new Rating();
139
+ * ratingObj.appendTo('#rating');
140
+ * </script>
141
+ * ```
142
+ */
143
+ @NotifyPropertyChanges
144
+ export class Rating extends Component<HTMLElement> implements INotifyPropertyChanged {
145
+
146
+ /**
147
+ * Defines whether to show or hide the reset button in a rating component.
148
+ * When set to "true", the reset button will be visible to the user, and they will be able to click it to reset the rating value to its default value.
149
+ *
150
+ * {% codeBlock src='rating/allowReset/index.md' %}{% endcodeBlock %}
151
+ *
152
+ * @default false
153
+ */
154
+ @Property(false)
155
+ public allowReset: boolean;
156
+
157
+ /**
158
+ * Defines one or more CSS classes that can be used to customize the appearance of a rating component.
159
+ * One or more CSS classes to customize the appearance of the rating component, such as by changing its colors, fonts, sizes, or other visual aspects.
160
+ *
161
+ * @default ''
162
+ */
163
+ @Property('')
164
+ public cssClass: string;
165
+
166
+ /**
167
+ * Defines whether a rating component is enabled or disabled.
168
+ * A disabled rating component may have a different visual appearance than an enabled one.
169
+ * When set to "true", the rating component will be disabled, and the user will not be able to interact with it.
170
+ *
171
+ * @default false
172
+ */
173
+ @Property(false)
174
+ public disabled: boolean;
175
+
176
+ /**
177
+ * Defines the template that defines the appearance of each un-rated item in a rating component.
178
+ *
179
+ * @default ''
180
+ * @angularType string | object
181
+ * @reactType string | function | JSX.Element
182
+ * @vueType string | function
183
+ * @aspType string
184
+ */
185
+ @Property('')
186
+ public emptyTemplate: string | Function;
187
+
188
+ /**
189
+ * Defines whether to add animation (to provide visual feedback to the user) when an item in a rating component is hovered.
190
+ * When set to "true", an animation will be added when the user hovers their cursor over an item in the rating component.
191
+ *
192
+ * @default true
193
+ */
194
+ @Property(true)
195
+ public enableAnimation: boolean;
196
+
197
+ /**
198
+ * Defines whether to select all the items before the selected item should be in selected state in a rating component.
199
+ * When set to "true", only the selected item will be in the selected state, and all other items will be un-selected.
200
+ * When set to "false", all items before the selected one will be in the selected state.
201
+ *
202
+ * @default false
203
+ */
204
+ @Property(false)
205
+ public enableSingleSelection: boolean;
206
+
207
+ /**
208
+ * Defines the template that defines the appearance of each rated item in a rating component.
209
+ *
210
+ * {% codeBlock src='rating/fullTemplate/index.md' %}{% endcodeBlock %}
211
+ *
212
+ * @default ''
213
+ * @angularType string | object
214
+ * @reactType string | function | JSX.Element
215
+ * @vueType string | function
216
+ * @aspType string
217
+ */
218
+ @Property('')
219
+ public fullTemplate: string | Function;
220
+
221
+ /**
222
+ * Defines the specific number of items (symbols) in rating component.
223
+ * The rating component typically consists of a number of items, such as stars or other symbols, that represent the rating value.
224
+ *
225
+ * @default 5
226
+ * @aspType int
227
+ */
228
+ @Property(5)
229
+ public itemsCount: number;
230
+
231
+ /**
232
+ * Defines the position of the label in rating component.
233
+ *
234
+ * The possible values are:
235
+ * * Top
236
+ * * Bottom
237
+ * * Left
238
+ * * Right
239
+ *
240
+ * {% codeBlock src='rating/labelPosition/index.md' %}{% endcodeBlock %}
241
+ *
242
+ * @isenumeration true
243
+ * @default LabelPosition.Right
244
+ * @asptype LabelPosition
245
+ */
246
+ @Property(LabelPosition.Right)
247
+ public labelPosition: string | LabelPosition;
248
+
249
+ /**
250
+ * Defines the template that used as label over default label of the rating. The current value of rating passed as context to build the content.
251
+ *
252
+ * {% codeBlock src='rating/labelTemplate/index.md' %}{% endcodeBlock %}
253
+ *
254
+ * @default ''
255
+ * @angularType string | object
256
+ * @reactType string | function | JSX.Element
257
+ * @vueType string | function
258
+ * @aspType string
259
+ */
260
+ @Property('')
261
+ public labelTemplate: string | Function;
262
+
263
+ /**
264
+ * Defines the value that specifies minimum rating that a user can select.
265
+ * The value is set to 0, which means that the minimum possible rating is 0.
266
+ *
267
+ * @default 0.0
268
+ * @aspType double
269
+ */
270
+ @Property(0.0)
271
+ public min: number;
272
+
273
+ /**
274
+ * Defines the precision type of the rating which used to component the granularity of the rating,
275
+ * allowing users to provide ratings with varying levels of precision.
276
+ *
277
+ * The possible values are:
278
+ * * Full
279
+ * * Half
280
+ * * Quarter
281
+ * * Exact
282
+ *
283
+ * {% codeBlock src='rating/precision/index.md' %}{% endcodeBlock %}
284
+ *
285
+ * @isenumeration true
286
+ * @default PrecisionType.Full
287
+ * @asptype PrecisionType
288
+ */
289
+ @Property(PrecisionType.Full)
290
+ public precision: string | PrecisionType;
291
+
292
+ /**
293
+ * Defines a boolean value that specifies whether the read-only mode is enabled for a rating component,
294
+ * which prevents the user from modifying or interacting with the rating value but allows them to read it.
295
+ *
296
+ * @default false
297
+ */
298
+ @Property(false)
299
+ public readOnly: boolean;
300
+
301
+ /**
302
+ * Defines a value that specifies whether to display a label that shows the current value of a rating.
303
+ * When set to "true", a label will be displayed that shows the current value of the rating; otherwise false.
304
+ *
305
+ * {% codeBlock src='rating/showLabel/index.md' %}{% endcodeBlock %}
306
+ *
307
+ * @default false
308
+ */
309
+ @Property(false)
310
+ public showLabel: boolean;
311
+
312
+ /**
313
+ * Defines a value that defines whether to show tooltip for the items.
314
+ * When set to "true", show tooltip for the items.
315
+ *
316
+ * @default true
317
+ */
318
+ @Property(true)
319
+ public showTooltip: boolean;
320
+
321
+ /**
322
+ * Defines the template that used as tooltip content over default tooltip content of the rating.
323
+ * The current value of rating passed as context to build the content.
324
+ *
325
+ * {% codeBlock src='rating/tooltipTemplate/index.md' %}{% endcodeBlock %}
326
+ *
327
+ * @default ''
328
+ * @angularType string | object
329
+ * @reactType string | function | JSX.Element
330
+ * @vueType string | function
331
+ * @aspType string
332
+ */
333
+ @Property('')
334
+ public tooltipTemplate: string | Function;
335
+
336
+ /**
337
+ * Defines the current rating value which used to display and update the rating selected by the user.
338
+ * Based on "PrecisionType", users can select ratings with varying levels of precision.
339
+ * The "value" is a decimal value that ranges from the minimum value to the items count,
340
+ * as specified by the "min" and "itemsCount" properties of the rating.
341
+ *
342
+ * {% codeBlock src='rating/value/index.md' %}{% endcodeBlock %}
343
+ *
344
+ * @default 0.0
345
+ * @aspType double
346
+ */
347
+ @Property(0.0)
348
+ public value: number;
349
+
350
+ /**
351
+ * Defines a value that indicates whether the rating component is visible or hidden.
352
+ * When set to "true", if the rating component is visible.
353
+ *
354
+ * @default true
355
+ */
356
+ @Property(true)
357
+ public visible: boolean;
358
+
359
+ /**
360
+ * Event callback that is raised before rendering each item.
361
+ *
362
+ * {% codeBlock src='rating/beforeItemRenderEvent/index.md' %}{% endcodeBlock %}
363
+ *
364
+ * @event beforeItemRender
365
+ */
366
+ @Event()
367
+ public beforeItemRender: EmitType<RatingItemEventArgs>;
368
+
369
+ /**
370
+ * Event callback that is raised after rendering the rating.
371
+ *
372
+ * @event created
373
+ */
374
+ @Event()
375
+ public created: EmitType<Event>;
376
+
377
+ /**
378
+ * Event callback that is raised when a user hovers over an item.
379
+ *
380
+ * {% codeBlock src='rating/onItemHoverEvent/index.md' %}{% endcodeBlock %}
381
+ *
382
+ * @event onItemHover
383
+ */
384
+ @Event()
385
+ public onItemHover: EmitType<RatingHoverEventArgs>;
386
+
387
+ /**
388
+ * Event callback that is raised when the value is changed.
389
+ *
390
+ * {% codeBlock src='rating/valueChangedEvent/index.md' %}{% endcodeBlock %}
391
+ *
392
+ * @event valueChanged
393
+ */
394
+ @Event()
395
+ public valueChanged: EmitType<RatingChangedEventArgs>;
396
+
397
+ /* Private variables */
398
+ private wrapper: HTMLElement;
399
+ private ratingItemList: HTMLElement;
400
+ private spanLabel: HTMLElement;
401
+ private itemElements: HTMLElement[] = [];
402
+ private resetElement: HTMLSpanElement;
403
+ private keyboardModuleRating: KeyboardEvents;
404
+ private keyConfigs: { [key: string]: string };
405
+ private tooltipObj: Tooltip;
406
+ private currentValue: number;
407
+ private emptyTemplateFunction: Function;
408
+ private fullTemplateFunction: Function;
409
+ private tooltipOpen: boolean;
410
+ private isTouchSelected: boolean;
411
+
412
+ /**
413
+ * Constructor for creating the widget
414
+ *
415
+ * @param {RatingModel} options - Specifies the rating model
416
+ * @param {string|HTMLButtonElement} element - Specifies the target element
417
+ */
418
+ constructor(options?: RatingModel, element?: string | HTMLInputElement) {
419
+ super(options, <string | HTMLInputElement>element);
420
+ }
421
+
422
+ protected preRender(): void {
423
+ if (!this.element.id) {
424
+ this.element.id = getUniqueID('e-' + this.getModuleName());
425
+ }
426
+ this.keyConfigs = {
427
+ downarrow: 'downarrow',
428
+ leftarrow: 'leftarrow',
429
+ rightarrow: 'rightarrow',
430
+ uparrow: 'uparrow',
431
+ space: 'space'
432
+ };
433
+ this.tooltipOpen = false;
434
+ this.isTouchSelected = false;
435
+ if (closest(this.element, 'form') && this.element.getAttribute('value')) {
436
+ this.setProperties({ value: this.element.getAttribute('value') }, true);
437
+ }
438
+ }
439
+
440
+ public render(): void {
441
+ this.initialize();
442
+ this.updateMinValue();
443
+ this.updateTemplateFunction();
444
+ this.triggerChange(null, this.value, false, true);
445
+ this.renderItems();
446
+ this.displayLabel();
447
+ }
448
+
449
+ private initialize(): void {
450
+ this.wrapper = this.createElement('div', { className: 'e-' + this.getModuleName() + '-container ' });
451
+ this.element.parentNode.insertBefore(this.wrapper, this.element);
452
+ this.wrapper.appendChild(this.element);
453
+ if ((this.element.getAttribute('name') == null)) {
454
+ this.element.setAttribute('name', this.element.id);
455
+ }
456
+ attributes(this.element, { 'aria-label': 'rating' });
457
+ this.renderItemList();
458
+ this.updateReset();
459
+ if (this.readOnly) {
460
+ this.wrapper.classList.add(READONLY);
461
+ }
462
+ if (!this.visible) {
463
+ this.wrapper.classList.add(HIDDEN);
464
+ }
465
+ if (this.enableRtl) {
466
+ this.wrapper.classList.add(RTL);
467
+ }
468
+ if (this.enableAnimation) {
469
+ this.wrapper.classList.add(ANIMATION);
470
+ }
471
+ if (this.cssClass) {
472
+ addClass([this.wrapper], this.cssClass.split(' '));
473
+ }
474
+ this.updateTooltip();
475
+ this.wireKeyboardEvent();
476
+ this.updateDisabled();
477
+ }
478
+
479
+ private updateDisabled(): void {
480
+ this.wrapper.classList[this.disabled ? 'add' : 'remove'](DISABLED);
481
+ attributes(this.ratingItemList, { 'tabindex': (this.disabled) ? '-1' : '0' });
482
+ this.updateResetButton();
483
+ }
484
+
485
+ private updateResetButton(): void {
486
+ if (this.allowReset) {
487
+ if (this.resetElement) {
488
+ this.resetElement.blur();
489
+ }
490
+ const isDisabled: boolean = (this.value <= this.min) || this.disabled;
491
+ this.resetElement.classList[isDisabled ? 'add' : 'remove'](DISABLED);
492
+ attributes(this.resetElement, { 'tabindex': (isDisabled ? '-1' : '0'), 'aria-hidden': isDisabled.toString() });
493
+ }
494
+ }
495
+
496
+ private renderItemList(): void {
497
+ this.ratingItemList = this.createElement('div', {
498
+ className: ITEMLIST,
499
+ id: this.element.id + '_item-list'
500
+ });
501
+ attributes(this.ratingItemList, { 'aria-label': 'rating', 'role': 'slider' });
502
+ this.wrapper.appendChild(this.ratingItemList);
503
+ EventHandler.add(this.ratingItemList, 'touchmove', (e: Event) => this.touchMoveHandler(e), this);
504
+ EventHandler.add(this.ratingItemList, Browser.touchEndEvent, this.touchEndHandler, this);
505
+ }
506
+
507
+ private touchMoveHandler(e: Event): void {
508
+ if (!this.isTouchSelected) {
509
+ this.wrapper.classList.add('e-rating-touch');
510
+ this.isTouchSelected = true;
511
+ }
512
+ this.wrapper.classList.add('e-touch-select');
513
+ const rect: DOMRect = this.ratingItemList.getBoundingClientRect() as DOMRect;
514
+ const x: number = (e as TouchEvent).touches[0].clientX - rect.x;
515
+ let currValue: number = (x / rect.width) * this.itemsCount;
516
+ currValue = (this.enableRtl) ? (this.itemsCount - currValue) : currValue;
517
+ currValue = currValue < this.min ? this.min : currValue > this.itemsCount ? this.itemsCount : currValue;
518
+ currValue = this.validateValue(currValue);
519
+ const element: HTMLElement = currValue === 0 ? null : this.itemElements[parseInt((Math.ceil(currValue) - 1).toString(), 10)];
520
+ if (currValue === this.currentValue) {
521
+ if (this.showTooltip && element) {
522
+ this.openRatingTooltip(element, false);
523
+ }
524
+ return;
525
+ }
526
+ const previousValue: number = this.currentValue;
527
+ this.triggerChange(e, currValue);
528
+ this.updateCurrentValue(currValue);
529
+ if (this.showTooltip) {
530
+ if (element) {
531
+ if (Math.ceil(currValue) !== Math.ceil(previousValue)) { this.closeRatingTooltip(); }
532
+ this.openRatingTooltip(element, true);
533
+ } else {
534
+ this.closeRatingTooltip();
535
+ }
536
+ }
537
+ }
538
+
539
+ private touchEndHandler(): void {
540
+ this.closeRatingTooltip();
541
+ this.wrapper.classList.remove('e-touch-select');
542
+ }
543
+
544
+ private updateTemplateFunction(): void {
545
+ this.emptyTemplateFunction = this.emptyTemplate ? this.getTemplateString(this.emptyTemplate) : null;
546
+ this.fullTemplateFunction = this.fullTemplate ? this.getTemplateString(this.fullTemplate) : null;
547
+ }
548
+
549
+ private renderItems(): void {
550
+ for (let i: number = 0; i < this.itemsCount; i++) {
551
+ const ratingItemContainer: HTMLElement = this.createElement('span', { className: ITEMCONTAINER });
552
+ const spanItem: HTMLElement = this.createElement('span', { className: 'e-rating-item' });
553
+ const ratingValue: number = this.getRatingValue(this.value, i);
554
+ this.renderItemContent(spanItem, ratingValue, i , false);
555
+ ratingItemContainer.appendChild(spanItem);
556
+ this.wireItemsEvents(ratingItemContainer, i + 1);
557
+ this.itemElements.push(ratingItemContainer);
558
+ const eventArgs: RatingItemEventArgs = { element: ratingItemContainer, value: i + 1 };
559
+ this.trigger('beforeItemRender', eventArgs, (args: RatingItemEventArgs) => {
560
+ this.ratingItemList.appendChild(args.element);
561
+ });
562
+ }
563
+ attributes(this.ratingItemList, { 'aria-valuemax': this.itemsCount.toString() });
564
+ this.updateItemValue(false);
565
+ }
566
+
567
+ private renderItemContent(spanEle: HTMLElement, val: number, index: number, isrerender: boolean): void {
568
+ if (isrerender) {
569
+ this.removeItemContent(spanEle);
570
+ }
571
+ if (this.fullTemplate && val === 1) {
572
+ spanEle.classList.add(FULLTEMPLATE);
573
+ append(this.fullTemplateFunction({ index: index, ratingValue: val }, this, 'ratingFullTemplate', (this.element.id + 'fullTemplate'), this.isStringTemplate), spanEle);
574
+ }
575
+ else if (this.emptyTemplate) {
576
+ spanEle.classList.add(EMPTYTEMPLATE);
577
+ append(this.emptyTemplateFunction({ index: index, ratingValue: val }, this, 'ratingEmptyTemplate', (this.element.id + 'emptyTemplate'), this.isStringTemplate), spanEle);
578
+ }
579
+ else {
580
+ addClass([spanEle], ICONCSS.split(' '));
581
+ }
582
+ }
583
+
584
+ private removeItemContent(spanEle: HTMLElement): void {
585
+ spanEle.classList.remove(FULLTEMPLATE, EMPTYTEMPLATE);
586
+ removeClass([spanEle], ICONCSS.split(' '));
587
+ if (spanEle.firstChild) {
588
+ spanEle.innerHTML = '';
589
+ }
590
+ }
591
+
592
+ private updateTooltip(): void {
593
+ if (this.showTooltip) {
594
+ this.tooltipObj = new Tooltip({
595
+ target: '.e-rating-item-container', windowCollision: true,
596
+ opensOn: 'Custom', cssClass: this.cssClass ? ('e-rating-tooltip ' + this.cssClass) : 'e-rating-tooltip'
597
+ });
598
+ this.tooltipObj.appendTo(this.ratingItemList);
599
+ }
600
+ else {
601
+ if (!isNullOrUndefined(this.tooltipObj)) {
602
+ this.tooltipObj.destroy();
603
+ this.tooltipObj = null;
604
+ }
605
+ }
606
+ }
607
+
608
+ private updateMinValue(): void {
609
+ this.setProperties({min: this.validateValue(this.min)}, true);
610
+ if (this.min > 0 && this.value < this.min) {
611
+ this.triggerChange(null, this.min, false);
612
+ }
613
+ attributes(this.ratingItemList, { 'aria-valuemin': this.min.toString() });
614
+ }
615
+
616
+ private validateValue(currentValue: number): number {
617
+ if (currentValue > this.itemsCount) {
618
+ currentValue = this.itemsCount;
619
+ }
620
+ else if (currentValue < 0) {
621
+ currentValue = 0;
622
+ }
623
+ else {
624
+ currentValue = ((this.precision === PrecisionType.Full) || this.enableSingleSelection) ? Math.round(currentValue) :
625
+ (this.precision === PrecisionType.Half) ? (Math.round(currentValue * 2) / 2) :
626
+ (this.precision === PrecisionType.Quarter) ? (Math.round(currentValue * 4) / 4) : (Math.round(currentValue * 10) / 10);
627
+ }
628
+ return currentValue;
629
+ }
630
+
631
+ private getRatingValue(value: number, i: number): number {
632
+ return (this.enableSingleSelection) ? (((value > i) && (value <= i + 1)) ? 1 : 0) :
633
+ (value >= i + 1) ? 1 : ((value < i) ? 0 : (value - i));
634
+ }
635
+
636
+ private updateItemValue(isUpdate: boolean = true): void {
637
+ for (let i: number = 0; i < this.itemsCount; i++) {
638
+ const itemElement: HTMLElement = this.itemElements[parseInt(i.toString(), 10)];
639
+ itemElement.classList.remove(SELECTED, INTERMEDIATE, SELECTEDVALUE);
640
+ const ratingValue: number = this.getRatingValue(this.currentValue, i);
641
+ if (ratingValue === 1) { itemElement.classList.add(SELECTED); }
642
+ else if (ratingValue > 0) { itemElement.classList.add(INTERMEDIATE); }
643
+ else if ((this.precision === PrecisionType.Full) && (i + 1 <= this.value) && (!this.enableSingleSelection)) {
644
+ itemElement.classList.add(SELECTEDVALUE);
645
+ }
646
+ if (isUpdate) { this.updateItemContent(ratingValue, i); }
647
+ itemElement.style.setProperty(RATINGVALUE, (ratingValue * 100) + '%');
648
+ itemElement.classList[((this.value === 0) && (i === 0)) || (this.value === i + 1) || ((ratingValue > 0) && (ratingValue < 1)) ? 'add' : 'remove']('e-rating-focus');
649
+ }
650
+ if (isUpdate) { this.renderReactTemplates(); }
651
+ this.updateResetButton();
652
+ attributes(this.ratingItemList, { 'aria-valuenow': this.currentValue.toString() });
653
+ attributes(this.element, { 'value': this.value.toString() });
654
+ }
655
+
656
+ private updateItemContent(ratingValue: number, index: number): void {
657
+ if (!this.fullTemplate && !this.emptyTemplate) { return; }
658
+ const spanEle: HTMLElement = this.itemElements[parseInt(index.toString(), 10)].querySelector('.e-rating-item');
659
+ if (this.fullTemplate && ratingValue === 1) {
660
+ if (spanEle.classList.contains(FULLTEMPLATE)) { return; }
661
+ this.removeItemContent(spanEle as HTMLElement);
662
+ spanEle.classList.add(FULLTEMPLATE);
663
+ append(this.fullTemplateFunction({ ratingValue: ratingValue, index: index }, this, 'ratingFullTemplate', (this.element.id + 'fullTemplate' + index), this.isStringTemplate), spanEle);
664
+ }
665
+ else if (this.emptyTemplate) {
666
+ if (spanEle.classList.contains(EMPTYTEMPLATE)) { return; }
667
+ this.removeItemContent(spanEle as HTMLElement);
668
+ spanEle.classList.add(EMPTYTEMPLATE);
669
+ append(this.emptyTemplateFunction({ ratingValue: ratingValue, index: index }, this, 'ratingEmptyTemplate', (this.element.id + 'emptyTemplate' + index), this.isStringTemplate), spanEle);
670
+ }
671
+ else {
672
+ this.removeItemContent(spanEle as HTMLElement);
673
+ addClass([spanEle], ICONCSS.split(' '));
674
+ }
675
+ }
676
+
677
+ private updateTooltipContent(isChange: boolean): void {
678
+ if (this.showTooltip) {
679
+ if (this.isReact) { this.clearTemplate(['ratingTooltipTemplate']); }
680
+ let content: string | HTMLElement;
681
+ if (this.tooltipTemplate) {
682
+ content = this.createElement('span', { className: 'e-rating-tooltip-content' });
683
+ const templateFunction: Function = this.getTemplateString(this.tooltipTemplate);
684
+ append(templateFunction({ value: this.currentValue }, this, 'ratingTooltipTemplate', (this.element.id + 'tooltipTemplate'), this.isStringTemplate), (content as HTMLElement));
685
+ this.tooltipObj.setProperties({ content: content }, isChange);
686
+ if (this.isAngular) {
687
+ setTimeout(() => {
688
+ const ratingSpan: NodeListOf<HTMLElement> = this.ratingItemList.querySelectorAll('.' + ITEMCONTAINER + '.' + SELECTED);
689
+ this.tooltipObj.refresh(ratingSpan[ratingSpan.length - 1]);
690
+ });
691
+ }
692
+ }
693
+ else {
694
+ content = this.currentValue.toString();
695
+ this.tooltipObj.setProperties({ content: initializeCSPTemplate( () => { return content; }) }, isChange);
696
+ }
697
+ this.renderReactTemplates();
698
+ }
699
+ }
700
+
701
+ private getTemplateString(template: string | Function): Function {
702
+ let stringContent: string | Function = '';
703
+ try {
704
+ if (typeof template !== 'function') {
705
+ const tempEle: HTMLElement = select(template);
706
+ if (tempEle) {
707
+ //Return innerHTML incase of jsrenderer script else outerHTML
708
+ stringContent = tempEle.tagName === 'SCRIPT' ? tempEle.innerHTML : tempEle.outerHTML;
709
+ } else {
710
+ stringContent = template;
711
+ }
712
+ } else {
713
+ stringContent = template;
714
+ }
715
+ } catch (e) {
716
+ stringContent = template;
717
+ }
718
+ return compile(stringContent);
719
+ }
720
+
721
+ private displayLabel(): void {
722
+ if (this.showLabel) {
723
+ this.spanLabel = this.createElement('span', { className: LABEL });
724
+ this.updateLabel();
725
+ this.updateLabelPosition();
726
+ }
727
+ else {
728
+ if (this.wrapper.contains(this.spanLabel)) {
729
+ remove(this.spanLabel);
730
+ this.spanLabel = null;
731
+ }
732
+ }
733
+ }
734
+
735
+ private updateLabel(): void {
736
+ if (this.showLabel) {
737
+ if (this.labelTemplate) {
738
+ if (this.isReact) { this.clearTemplate(['ratingLabelTemplate']); }
739
+ if (this.spanLabel.firstChild) {
740
+ this.spanLabel.innerHTML = '';
741
+ }
742
+ const templateFunction: Function = this.getTemplateString(this.labelTemplate);
743
+ append(templateFunction({ value: this.currentValue }, this, 'ratingLabelTemplate', (this.element.id + 'labelTemplate'), this.isStringTemplate), this.spanLabel);
744
+ this.renderReactTemplates();
745
+ }
746
+ else {
747
+ this.spanLabel.textContent = this.currentValue + ' / ' + this.itemsCount;
748
+ }
749
+ }
750
+ }
751
+
752
+ private updateReset(): void {
753
+ if (this.allowReset) {
754
+ this.resetElement = this.createElement('span', {
755
+ className: RESET,
756
+ attrs: {'aria-label': 'resetbutton', 'role': 'button'}
757
+ });
758
+ this.updateResetButton();
759
+ EventHandler.add(this.resetElement, 'click', this.resetClicked, this);
760
+ this.wrapper.insertBefore(this.resetElement, this.ratingItemList);
761
+ }
762
+ else {
763
+ if (this.wrapper.contains(this.resetElement)) {
764
+ remove(this.resetElement);
765
+ this.resetElement = null;
766
+ }
767
+ }
768
+ }
769
+
770
+ private updateLabelPosition(): void {
771
+ this.clearLabelPosition();
772
+ this.spanLabel.classList.add('e-label-' + this.labelPosition.toLowerCase());
773
+ if (this.labelPosition === 'Left' || this.labelPosition === 'Top') {
774
+ this.wrapper.firstChild.after(this.spanLabel);
775
+ }
776
+ else {
777
+ this.wrapper.appendChild(this.spanLabel);
778
+ }
779
+ }
780
+
781
+ private clearLabelPosition(): void {
782
+ const removeCss: string[] = this.spanLabel.classList.value.match(/(e-label-[top|bottom|right|left]+)/g);
783
+ if (removeCss) {
784
+ removeClass([this.spanLabel], removeCss);
785
+ }
786
+ }
787
+
788
+ private wireItemsEvents(itemElement: HTMLElement, index: number): void {
789
+ EventHandler.add(itemElement, 'click', (e: Event) => this.clickHandler(e), this);
790
+ EventHandler.add(itemElement, 'mousemove', (e: Event) => this.mouseMoveHandler(index, e), this);
791
+ EventHandler.add(itemElement, 'mouseleave', this.mouseLeaveHandler, this);
792
+ }
793
+
794
+ private clickHandler(e: Event): void {
795
+ this.currentValue = (this.min > 0 && this.currentValue < this.min) ? this.min : this.currentValue;
796
+ this.triggerChange(e, this.currentValue);
797
+ this.updateItemValue();
798
+ this.updateLabel();
799
+ this.updateResetButton();
800
+ }
801
+
802
+ private updateValueChange(e: Event, val: number, isInteracted: boolean = true): void{
803
+ this.triggerChange(e, val, isInteracted);
804
+ this.updateItemValue();
805
+ this.updateLabel();
806
+ }
807
+
808
+ private triggerChange(e: Event, val: number, isInteracted: boolean = true, isInitial: boolean = false): void {
809
+ const ratingObj: any = null || this;
810
+ val = this.validateValue(val);
811
+ this.currentValue = val;
812
+ if (this.currentValue === this.value) { return; }
813
+ const eventArgs: RatingChangedEventArgs = { event: e, isInteracted: isInteracted, value: val, previousValue: this.value };
814
+ this.setProperties({ value: val }, true);
815
+ if (this.isAngular && !isInitial) {
816
+ ratingObj.localChange({ value: val });
817
+ }
818
+ if (!isInitial) {
819
+ this.trigger('valueChanged', eventArgs);
820
+ }
821
+ }
822
+
823
+ private mouseMoveHandler(index: number, e: Event): void {
824
+ if (this.isTouchSelected) {
825
+ this.wrapper.classList.remove('e-rating-touch');
826
+ this.isTouchSelected = false;
827
+ }
828
+ let currValue: number = this.calculateCurrentValue(index, e as MouseEventArgs);
829
+ currValue = this.validateValue(currValue);
830
+ const element: HTMLElement = this.itemElements[parseInt((index - 1).toString(), 10)];
831
+ if (currValue === this.currentValue) {
832
+ this.openRatingTooltip(element, false);
833
+ return;
834
+ }
835
+ this.updateCurrentValue(currValue);
836
+ this.openRatingTooltip(element, true);
837
+ const eventArgs: RatingHoverEventArgs = { element: element, event: e, value: currValue };
838
+ this.trigger('onItemHover', eventArgs);
839
+ }
840
+
841
+ private openRatingTooltip(element: HTMLElement, isChange: boolean): void {
842
+ if (this.showTooltip) {
843
+ if (!this.tooltipOpen) {
844
+ this.updateTooltipContent(false);
845
+ this.tooltipObj.open(element);
846
+ this.tooltipOpen = true;
847
+ } else if (isChange) {
848
+ this.updateTooltipContent(true);
849
+ this.tooltipObj.refresh(element);
850
+ }
851
+ }
852
+ }
853
+
854
+ private closeRatingTooltip(): void {
855
+ if (this.tooltipOpen) {
856
+ this.tooltipObj.close();
857
+ this.tooltipOpen = false;
858
+ }
859
+ }
860
+
861
+ private updateCurrentValue(currValue: number): void {
862
+ this.currentValue = currValue;
863
+ this.updateItemValue();
864
+ this.updateLabel();
865
+ }
866
+
867
+ private mouseLeaveHandler(): void {
868
+ this.closeRatingTooltip();
869
+ this.updateCurrentValue(this.value);
870
+ }
871
+
872
+ private calculateCurrentValue(index: number, args: MouseEventArgs): number {
873
+ let currentValue: number = index;
874
+ if (!(this.enableSingleSelection || (this.precision === PrecisionType.Full))) {
875
+ currentValue = args.offsetX / this.itemElements[index - 1].clientWidth;
876
+ currentValue = (this.enableRtl) ? (1 - currentValue) : currentValue;
877
+ if (this.precision === PrecisionType.Quarter) {
878
+ currentValue = currentValue <= 0.25 ? 0.25 : currentValue <= 0.5 ? 0.5 : currentValue < 0.75 ? 0.75 : 1.0;
879
+ }
880
+ else if (this.precision === PrecisionType.Half) {
881
+ currentValue = currentValue <= 0.5 ? 0.5 : 1;
882
+ }
883
+ currentValue = currentValue + index - 1;
884
+ }
885
+ return currentValue;
886
+ }
887
+
888
+ /**
889
+ * Reset’s the value to minimum.
890
+ *
891
+ * {% codeBlock src='rating/reset/index.md' %}{% endcodeBlock %}
892
+ *
893
+ * @returns {void}
894
+ */
895
+ public reset(): void {
896
+ this.resetClicked(null, false);
897
+ }
898
+
899
+ private resetClicked(e: Event, isInteracted: boolean = true): void {
900
+ this.updateValueChange(e, this.min, isInteracted);
901
+ this.updateResetButton();
902
+ }
903
+
904
+ private wireKeyboardEvent(): void {
905
+ this.keyboardModuleRating = new KeyboardEvents(this.wrapper, {
906
+ keyAction: this.keyActionHandler.bind(this),
907
+ keyConfigs: this.keyConfigs,
908
+ eventName: 'keydown'
909
+ });
910
+ }
911
+
912
+ private keyActionHandler(e: KeyboardEventArgs): void {
913
+ e.preventDefault();
914
+ if (this.disabled || this.readOnly) { return; }
915
+ if ((e.target as HTMLElement).classList.contains(ITEMLIST)) {
916
+ switch (e.action) {
917
+ case 'uparrow':
918
+ this.handleNavigation(e, true);
919
+ break;
920
+ case 'downarrow':
921
+ this.handleNavigation(e, false);
922
+ break;
923
+ case 'leftarrow':
924
+ this.handleNavigation(e, this.enableRtl);
925
+ break;
926
+ case 'rightarrow':
927
+ this.handleNavigation(e, !this.enableRtl);
928
+ break;
929
+ }
930
+ }
931
+ if (this.allowReset && (e.target as HTMLElement).classList.contains('e-reset')) {
932
+ switch (e.action) {
933
+ case 'space':
934
+ this.resetClicked(e);
935
+ break;
936
+ }
937
+ }
938
+ }
939
+
940
+ private handleNavigation(e: Event, isIncrease: boolean): void {
941
+ if ((!isIncrease && (this.value > this.min)) || (isIncrease && (this.value < this.itemsCount))) {
942
+ let currentValue: number = (this.precision === PrecisionType.Full || this.enableSingleSelection) ? 1 :
943
+ (this.precision === PrecisionType.Half) ? 0.5 : (this.precision === PrecisionType.Quarter) ? 0.25 :
944
+ Math.round(0.1 * 10) / 10;
945
+ currentValue = isIncrease ? this.value + currentValue : this.value - currentValue;
946
+ this.updateValueChange(e, (currentValue));
947
+ this.updateResetButton();
948
+ }
949
+ }
950
+
951
+ private updateContent(): void {
952
+ for (let i: number = 0; i < this.itemsCount; i++) {
953
+ const itemElement: HTMLElement = this.itemElements[parseInt(i.toString(), 10)].firstElementChild as HTMLElement;
954
+ this.renderItemContent(itemElement, this.getRatingValue(this.value, i), i, true);
955
+ }
956
+ }
957
+
958
+ /**
959
+ * To get component name.
960
+ *
961
+ * @returns {string} - Module Name
962
+ * @private
963
+ */
964
+ public getModuleName(): string {
965
+ return 'rating';
966
+ }
967
+
968
+ /**
969
+ * To get the properties to be maintained in the persisted state.
970
+ *
971
+ * @returns {string} - Persist data
972
+ */
973
+ protected getPersistData(): string {
974
+ return this.addOnPersist([]);
975
+ }
976
+
977
+ private removeItemElements(): void {
978
+ for (let i: number = 0; i < this.itemElements.length; i++) {
979
+ remove(this.itemElements[parseInt(i.toString(), 10)]);
980
+ }
981
+ this.itemElements = [];
982
+ }
983
+
984
+ /**
985
+ * Destroys the Rating instance.
986
+ *
987
+ * @returns {void}
988
+ */
989
+ public destroy(): void {
990
+ super.destroy();
991
+ // unwires the events and detach the li elements
992
+ this.removeItemElements();
993
+ this.clearTemplate();
994
+ if (this.spanLabel) {
995
+ remove(this.spanLabel);
996
+ this.spanLabel = null;
997
+ }
998
+ if (this.resetElement) {
999
+ remove(this.resetElement);
1000
+ this.resetElement = null;
1001
+ }
1002
+ if (this.showTooltip) {
1003
+ this.tooltipObj.destroy();
1004
+ this.tooltipObj = null;
1005
+ }
1006
+ remove(this.ratingItemList);
1007
+ this.ratingItemList = null;
1008
+ this.wrapper.parentNode.insertBefore(this.element, this.wrapper);
1009
+ remove(this.wrapper);
1010
+ this.wrapper = null;
1011
+ this.keyboardModuleRating.destroy();
1012
+ this.keyboardModuleRating = null;
1013
+ ['value', 'aria-label', 'name'].forEach((attr: string) => {
1014
+ this.element.removeAttribute(attr);
1015
+ });
1016
+ }
1017
+
1018
+ /**
1019
+ * Called internally if any of the property value changed.
1020
+ *
1021
+ * @param {RatingModel} newProp - Specifies new properties
1022
+ * @param {RatingModel} oldProp - Specifies old properties
1023
+ * @returns {void}
1024
+ * @private
1025
+ */
1026
+ public onPropertyChanged(newProp: RatingModel, oldProp?: RatingModel): void {
1027
+ for (const prop of Object.keys(newProp)) {
1028
+ switch (prop) {
1029
+ case 'value':
1030
+ this.updateValueChange(null, (this.value > this.min) ? this.value : this.min, false);
1031
+ break;
1032
+ case 'min':
1033
+ this.updateMinValue();
1034
+ this.updateItemValue();
1035
+ this.updateLabel();
1036
+ break;
1037
+ case 'showLabel':
1038
+ this.displayLabel();
1039
+ break;
1040
+ case 'visible':
1041
+ this.wrapper.classList[!this.visible ? 'add' : 'remove'](HIDDEN);
1042
+ break;
1043
+ case 'disabled':
1044
+ this.updateDisabled();
1045
+ break;
1046
+ case 'readOnly':
1047
+ this.wrapper.classList[this.readOnly ? 'add' : 'remove'](READONLY);
1048
+ break;
1049
+ case 'allowReset':
1050
+ this.updateReset();
1051
+ break;
1052
+ case 'enableRtl':
1053
+ this.wrapper.classList[this.enableRtl ? 'add' : 'remove'](RTL);
1054
+ break;
1055
+ case 'cssClass':
1056
+ if (oldProp.cssClass) {
1057
+ removeClass([this.wrapper], oldProp.cssClass.split(' '));
1058
+ }
1059
+ if (newProp.cssClass) {
1060
+ addClass([this.wrapper], newProp.cssClass.split(' '));
1061
+ }
1062
+ if (this.tooltipObj) {
1063
+ this.tooltipObj.setProperties({ cssClass: this.cssClass ? ('e-rating-tooltip ' + this.cssClass) : 'e-rating-tooltip'});
1064
+ }
1065
+ break;
1066
+ case 'labelPosition':
1067
+ this.updateLabelPosition();
1068
+ break;
1069
+ case 'showTooltip':
1070
+ this.updateTooltip();
1071
+ break;
1072
+ case 'precision':
1073
+ this.updateMinValue();
1074
+ this.triggerChange(null, this.value, false);
1075
+ this.updateItemValue();
1076
+ this.updateLabel();
1077
+ break;
1078
+ case 'enableSingleSelection':
1079
+ //To validate the value against single selection and update the items, label + trigger change event if value changed
1080
+ this.updateValueChange(null, this.currentValue, false);
1081
+ break;
1082
+ case 'enableAnimation':
1083
+ this.wrapper.classList[this.enableAnimation ? 'add' : 'remove'](ANIMATION);
1084
+ break;
1085
+ case 'emptyTemplate':
1086
+ case 'fullTemplate':
1087
+ this.updateTemplateFunction();
1088
+ this.updateContent();
1089
+ break;
1090
+ case 'labelTemplate':
1091
+ this.updateLabel();
1092
+ break;
1093
+ case 'itemsCount':
1094
+ this.removeItemElements();
1095
+ this.renderItems();
1096
+ this.updateLabel();
1097
+ break;
1098
+ }
1099
+ }
1100
+ }
1101
+ }