@nuralyui/timepicker 0.1.1 → 0.1.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.
@@ -1,890 +0,0 @@
1
- /**
2
- * @license
3
- * Copyright 2023 Nuraly, Laabidi Aymen
4
- * SPDX-License-Identifier: MIT
5
- */
6
- var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
7
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
8
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
9
- else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
10
- return c > 3 && r && Object.defineProperty(target, key, r), r;
11
- };
12
- import { LitElement, html, nothing } from 'lit';
13
- import { customElement, property, query, state } from 'lit/decorators.js';
14
- import { classMap } from 'lit/directives/class-map.js';
15
- import { ifDefined } from 'lit/directives/if-defined.js';
16
- import { NuralyUIBaseMixin } from '../../shared/base-mixin.js';
17
- import { SharedDropdownController } from '../../shared/controllers/dropdown.controller.js';
18
- import { styles } from './timepicker.style.js';
19
- import { TimeFormat, TimePeriod, TimePickerMode, TimePickerSize, TimePickerVariant, TimePickerState, TimePickerPlacement, TIME_PICKER_EVENTS, EMPTY_TIME_VALUE, } from './timepicker.types.js';
20
- import { TIME_INPUT_FIELD_ID, CLOCK_CONTAINER_CLASS, } from './timepicker.constants.js';
21
- import { TimePickerSelectionController, TimePickerValidationController, TimePickerFormattingController, } from './controllers/index.js';
22
- import { TimeUtils } from './utils/time.utils.js';
23
- /**
24
- * NuralyUI Time Picker - A comprehensive time selection component
25
- *
26
- * @element nr-timepicker
27
- *
28
- * @fires nr-time-change - Fired when time is selected
29
- * @fires nr-clock-open - Fired when clock dropdown is opened
30
- * @fires nr-clock-close - Fired when clock dropdown is closed
31
- * @fires nr-focus - Fired when component receives focus
32
- * @fires nr-blur - Fired when component loses focus
33
- * @fires nr-validation - Fired when validation state changes
34
- *
35
- * @slot label - Label content for the input field
36
- * @slot helper-text - Helper text content below the input field
37
- * @slot icon - Icon content for the input field trigger
38
- *
39
- * @csspart input - The input field part
40
- * @csspart dropdown - The clock dropdown container part
41
- * @csspart clock - The clock face part
42
- * @csspart clock-hand - The clock hand part
43
- * @csspart time-input - Individual time input parts (hours, minutes, seconds)
44
- *
45
- * @example Basic usage
46
- * ```html
47
- * <nr-timepicker
48
- * label="Select Time"
49
- * @nr-time-change="${this.handleTimeChange}">
50
- * </nr-timepicker>
51
- * ```
52
- *
53
- * @example 12-hour format with seconds
54
- * ```html
55
- * <nr-timepicker
56
- * format="12h"
57
- * show-seconds
58
- * label="Meeting Time">
59
- * </nr-timepicker>
60
- * ```
61
- *
62
- * @example With time constraints
63
- * ```html
64
- * <nr-timepicker
65
- * min-time="09:00"
66
- * max-time="17:00"
67
- * label="Business Hours">
68
- * </nr-timepicker>
69
- * ```
70
- */
71
- let NrTimePickerElement = class NrTimePickerElement extends NuralyUIBaseMixin(LitElement) {
72
- constructor() {
73
- super(...arguments);
74
- // Controllers following the delegation pattern
75
- this.selectionController = new TimePickerSelectionController(this);
76
- this.validationController = new TimePickerValidationController(this);
77
- this.formattingController = new TimePickerFormattingController(this);
78
- this.dropdownController = new SharedDropdownController(this);
79
- // Core properties
80
- this.name = '';
81
- this.value = '';
82
- this.defaultValue = '';
83
- this.disabled = false;
84
- this.readonly = false;
85
- this.required = false;
86
- this.placeholder = '';
87
- // Time picker specific properties
88
- this.format = TimeFormat.TwentyFourHour;
89
- this.showSeconds = false;
90
- this.showClock = true;
91
- this.minuteInterval = 1;
92
- this.secondInterval = 1;
93
- // UI properties
94
- this.size = TimePickerSize.Medium;
95
- this.variant = TimePickerVariant.Default;
96
- this.state = TimePickerState.Default;
97
- this.placement = TimePickerPlacement.Auto;
98
- this.label = '';
99
- this.helperText = '';
100
- // Clock display state
101
- this.clockOpen = false;
102
- this.clockMode = TimePickerMode.Hours;
103
- // Internal state
104
- this.inputValue = '';
105
- this.currentMode = TimePickerMode.Hours;
106
- this.validationMessage = '';
107
- }
108
- firstUpdated() {
109
- this.initializeTimePicker();
110
- }
111
- updated(changedProperties) {
112
- super.updated(changedProperties);
113
- this.handlePropertyChanges(changedProperties);
114
- }
115
- /**
116
- * Initialize time picker with default values and constraints
117
- */
118
- initializeTimePicker() {
119
- // Set up initial constraints
120
- this.updateConstraints();
121
- // Set initial value
122
- if (this.value) {
123
- this.setTimeFromValue(this.value);
124
- }
125
- else if (this.defaultValue) {
126
- this.setTimeFromValue(this.defaultValue);
127
- }
128
- // Initialize dropdown controller
129
- if (this.clockContainer && this.inputElement) {
130
- this.dropdownController.setElements(this.clockContainer, this.inputElement);
131
- }
132
- }
133
- /**
134
- * Handle property changes
135
- */
136
- handlePropertyChanges(changedProperties) {
137
- if (changedProperties.has('value') && this.value !== this.inputValue) {
138
- this.setTimeFromValue(this.value);
139
- }
140
- if (this.hasConstraintPropertiesChanged(changedProperties)) {
141
- this.updateConstraints();
142
- }
143
- if (changedProperties.has('clockOpen')) {
144
- if (this.clockOpen) {
145
- this.openClock();
146
- }
147
- else {
148
- this.closeClock();
149
- }
150
- }
151
- if (changedProperties.has('clockMode')) {
152
- this.currentMode = this.clockMode;
153
- }
154
- }
155
- /**
156
- * Check if constraint properties changed
157
- */
158
- hasConstraintPropertiesChanged(changedProperties) {
159
- return (changedProperties.has('minTime') ||
160
- changedProperties.has('maxTime') ||
161
- changedProperties.has('disabledTimes') ||
162
- changedProperties.has('enabledTimes'));
163
- }
164
- /**
165
- * Update validation constraints
166
- */
167
- updateConstraints() {
168
- const constraints = {
169
- minTime: this.minTime,
170
- maxTime: this.maxTime,
171
- disabledTimes: this.disabledTimes || [],
172
- enabledTimes: this.enabledTimes,
173
- };
174
- this.validationController.setConstraints(constraints);
175
- }
176
- /**
177
- * Set time from string value
178
- */
179
- setTimeFromValue(value) {
180
- if (this.selectionController.setTimeFromString(value)) {
181
- this.inputValue = value;
182
- this.requestUpdate();
183
- }
184
- }
185
- // TimePickerHost interface implementation
186
- getCurrentTime() {
187
- return this.selectionController.getSelectedTime() || EMPTY_TIME_VALUE;
188
- }
189
- setTime(time) {
190
- this.selectionController.selectTime(time);
191
- this.updateInputValue();
192
- }
193
- formatTime(time) {
194
- return this.formattingController.formatForDisplay(time);
195
- }
196
- parseTime(timeString) {
197
- return this.formattingController.parseInputValue(timeString);
198
- }
199
- getConfig() {
200
- return {
201
- format: this.format,
202
- showSeconds: this.showSeconds,
203
- use12HourClock: this.format === TimeFormat.TwelveHour,
204
- step: {
205
- hours: 1,
206
- minutes: this.minuteInterval,
207
- seconds: this.secondInterval,
208
- },
209
- minuteInterval: this.minuteInterval,
210
- secondInterval: this.secondInterval,
211
- };
212
- }
213
- validateTime(time) {
214
- return this.validationController.validateConstraints(time);
215
- }
216
- // Public API methods
217
- /**
218
- * Open the clock dropdown
219
- */
220
- openClock() {
221
- if (this.disabled || this.readonly)
222
- return;
223
- this.clockOpen = true;
224
- this.dropdownController.open();
225
- this.dispatchEvent(new CustomEvent(TIME_PICKER_EVENTS.CLOCK_OPEN, {
226
- bubbles: true,
227
- composed: true,
228
- }));
229
- }
230
- /**
231
- * Close the clock dropdown
232
- */
233
- closeClock() {
234
- this.clockOpen = false;
235
- this.dropdownController.close();
236
- this.dispatchEvent(new CustomEvent(TIME_PICKER_EVENTS.CLOCK_CLOSE, {
237
- bubbles: true,
238
- composed: true,
239
- }));
240
- }
241
- /**
242
- * Toggle clock dropdown
243
- */
244
- toggleClock() {
245
- if (this.clockOpen) {
246
- this.closeClock();
247
- }
248
- else {
249
- this.openClock();
250
- }
251
- }
252
- /**
253
- * Clear selected time
254
- */
255
- clear() {
256
- this.selectionController.clearSelection();
257
- this.inputValue = '';
258
- this.value = '';
259
- this.requestUpdate();
260
- }
261
- /**
262
- * Set to current time
263
- */
264
- setToNow() {
265
- this.selectionController.setToCurrentTime();
266
- this.updateInputValue();
267
- }
268
- // Event handlers
269
- handleInputChange(event) {
270
- const target = event.target;
271
- const value = target.value;
272
- if (this.selectionController.setTimeFromString(value)) {
273
- this.value = value;
274
- this.inputValue = value;
275
- }
276
- else {
277
- // Reset to previous valid value
278
- target.value = this.inputValue;
279
- }
280
- }
281
- handleInputFocus() {
282
- this.dispatchEvent(new CustomEvent(TIME_PICKER_EVENTS.FOCUS, {
283
- bubbles: true,
284
- composed: true,
285
- }));
286
- }
287
- handleInputBlur() {
288
- this.dispatchEvent(new CustomEvent(TIME_PICKER_EVENTS.BLUR, {
289
- bubbles: true,
290
- composed: true,
291
- }));
292
- }
293
- handleTriggerClick() {
294
- if (!this.disabled && !this.readonly) {
295
- this.toggleClock();
296
- }
297
- }
298
- handleTimeSelection(time) {
299
- this.selectionController.selectTime(time);
300
- this.updateInputValue();
301
- if (!this.showClock || this.currentMode === TimePickerMode.Minutes) {
302
- this.closeClock();
303
- }
304
- }
305
- handleModeChange(mode) {
306
- this.currentMode = mode;
307
- this.clockMode = mode;
308
- }
309
- handleDigitalTimeChange(component, value) {
310
- const selectedTime = this.selectionController.getSelectedTime() || TimeUtils.getCurrentTime();
311
- const updatedTime = Object.assign(Object.assign({}, selectedTime), { [component]: value });
312
- if (this.validateTime(updatedTime)) {
313
- this.selectionController.selectTime(updatedTime);
314
- this.updateInputValue();
315
- }
316
- }
317
- handleHourSelect(hour, format) {
318
- const selectedTime = this.selectionController.getSelectedTime() || TimeUtils.getCurrentTime();
319
- let adjustedHour = hour;
320
- if (format === TimeFormat.TwelveHour) {
321
- const currentPeriod = this.formattingController.getPeriod(selectedTime.hours);
322
- if (hour === 12) {
323
- adjustedHour = currentPeriod === TimePeriod.AM ? 0 : 12;
324
- }
325
- else {
326
- adjustedHour = currentPeriod === TimePeriod.AM ? hour : hour + 12;
327
- }
328
- }
329
- const updatedTime = Object.assign(Object.assign({}, selectedTime), { hours: adjustedHour });
330
- if (this.validateTime(updatedTime)) {
331
- this.selectionController.selectTime(updatedTime);
332
- this.updateInputValue();
333
- }
334
- }
335
- handleMinuteSelect(minute) {
336
- const selectedTime = this.selectionController.getSelectedTime() || TimeUtils.getCurrentTime();
337
- const updatedTime = Object.assign(Object.assign({}, selectedTime), { minutes: minute });
338
- if (this.validateTime(updatedTime)) {
339
- this.selectionController.selectTime(updatedTime);
340
- this.updateInputValue();
341
- }
342
- }
343
- handleSecondSelect(second) {
344
- const selectedTime = this.selectionController.getSelectedTime() || TimeUtils.getCurrentTime();
345
- const updatedTime = Object.assign(Object.assign({}, selectedTime), { seconds: second });
346
- if (this.validateTime(updatedTime)) {
347
- this.selectionController.selectTime(updatedTime);
348
- this.updateInputValue();
349
- }
350
- }
351
- handlePeriodToggle(period) {
352
- const selectedTime = this.selectionController.getSelectedTime();
353
- if (!selectedTime)
354
- return;
355
- let hours = selectedTime.hours;
356
- if (period === TimePeriod.PM && hours < 12) {
357
- hours += 12;
358
- }
359
- else if (period === TimePeriod.AM && hours >= 12) {
360
- hours -= 12;
361
- }
362
- const updatedTime = Object.assign(Object.assign({}, selectedTime), { hours });
363
- this.selectionController.selectTime(updatedTime);
364
- this.updateInputValue();
365
- }
366
- updateInputValue() {
367
- const selectedTime = this.selectionController.getSelectedTime();
368
- if (selectedTime) {
369
- this.inputValue = this.formattingController.formatForInput(selectedTime);
370
- this.value = this.inputValue;
371
- if (this.inputElement) {
372
- this.inputElement.value = this.inputValue;
373
- }
374
- }
375
- }
376
- render() {
377
- return html `
378
- <div class="time-picker" part="time-picker">
379
- ${this.renderLabel()}
380
- ${this.renderInput()}
381
- ${this.renderDropdown()}
382
- ${this.renderHelperText()}
383
- </div>
384
- `;
385
- }
386
- renderLabel() {
387
- if (!this.label)
388
- return nothing;
389
- return html `
390
- <label for="${TIME_INPUT_FIELD_ID}" class="time-picker__label" part="label">
391
- ${this.label}
392
- ${this.required ? html `<span class="time-picker__required">*</span>` : nothing}
393
- </label>
394
- `;
395
- }
396
- renderInput() {
397
- const inputClasses = {
398
- 'time-picker__input': true,
399
- 'time-picker__input--error': this.state === TimePickerState.Error,
400
- 'time-picker__input--readonly': this.readonly,
401
- };
402
- return html `
403
- <div class="time-picker__input-container" part="input-container">
404
- <input
405
- id="${TIME_INPUT_FIELD_ID}"
406
- class="${classMap(inputClasses)}"
407
- part="input"
408
- type="text"
409
- name="${ifDefined(this.name || undefined)}"
410
- .value="${this.inputValue}"
411
- placeholder="${this.placeholder || this.formattingController.getPlaceholder()}"
412
- ?disabled="${this.disabled}"
413
- ?readonly="${this.readonly}"
414
- ?required="${this.required}"
415
- @input="${this.handleInputChange}"
416
- @focus="${this.handleInputFocus}"
417
- @blur="${this.handleInputBlur}"
418
- />
419
- <button
420
- class="time-picker__trigger"
421
- part="trigger"
422
- type="button"
423
- ?disabled="${this.disabled}"
424
- @click="${this.handleTriggerClick}"
425
- aria-label="Open time picker"
426
- >
427
- <slot name="icon">
428
- <svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor">
429
- <path d="M12 2C6.477 2 2 6.477 2 12s4.477 10 10 10 10-4.477 10-10S17.523 2 12 2zm0 18c-4.411 0-8-3.589-8-8s3.589-8 8-8 8 3.589 8 8-3.589 8-8 8z"/>
430
- <path d="M12.5 7H11v6l5.25 3.15.75-1.23-4.5-2.67z"/>
431
- </svg>
432
- </slot>
433
- </button>
434
- </div>
435
- `;
436
- }
437
- renderDropdown() {
438
- if (!this.clockOpen)
439
- return nothing;
440
- const dropdownClasses = {
441
- 'time-picker__dropdown': true,
442
- 'time-picker__dropdown--open': this.clockOpen,
443
- 'time-picker__dropdown--top': this.placement === TimePickerPlacement.Top,
444
- };
445
- return html `
446
- <div class="${classMap(dropdownClasses)}" part="dropdown">
447
- ${this.renderColumnPicker()}
448
- ${this.renderActions()}
449
- </div>
450
- `;
451
- }
452
- renderColumnPicker() {
453
- const selectedTime = this.selectionController.getSelectedTime() || EMPTY_TIME_VALUE;
454
- const config = this.getConfig();
455
- return html `
456
- <div class="time-picker__columns" part="columns">
457
- ${this.renderHourColumn(selectedTime, config)}
458
- ${this.renderMinuteColumn(selectedTime)}
459
- ${this.showSeconds ? this.renderSecondColumn(selectedTime) : nothing}
460
- </div>
461
- `;
462
- }
463
- renderHourColumn(selectedTime, config) {
464
- const hours = config.format === TimeFormat.TwelveHour
465
- ? Array.from({ length: 12 }, (_, i) => i === 0 ? 12 : i)
466
- : Array.from({ length: 24 }, (_, i) => i);
467
- const displayHour = config.format === TimeFormat.TwelveHour
468
- ? this.formattingController.formatHours(selectedTime.hours)
469
- : selectedTime.hours;
470
- return html `
471
- <div class="time-picker__column" part="hour-column">
472
- <div class="time-picker__column-list">
473
- ${hours.map(hour => html `
474
- <div
475
- class="time-picker__column-item ${hour === displayHour ? 'time-picker__column-item--selected' : ''}"
476
- @click="${() => this.handleHourSelect(hour, config.format)}"
477
- >
478
- ${hour.toString().padStart(2, '0')}
479
- </div>
480
- `)}
481
- </div>
482
- </div>
483
- `;
484
- }
485
- renderMinuteColumn(selectedTime) {
486
- const minutes = Array.from({ length: 60 }, (_, i) => i);
487
- return html `
488
- <div class="time-picker__column" part="minute-column">
489
- <div class="time-picker__column-list">
490
- ${minutes.map(minute => html `
491
- <div
492
- class="time-picker__column-item ${minute === selectedTime.minutes ? 'time-picker__column-item--selected' : ''}"
493
- @click="${() => this.handleMinuteSelect(minute)}"
494
- >
495
- ${minute.toString().padStart(2, '0')}
496
- </div>
497
- `)}
498
- </div>
499
- </div>
500
- `;
501
- }
502
- renderSecondColumn(selectedTime) {
503
- const seconds = Array.from({ length: 60 }, (_, i) => i);
504
- return html `
505
- <div class="time-picker__column" part="second-column">
506
- <div class="time-picker__column-list">
507
- ${seconds.map(second => html `
508
- <div
509
- class="time-picker__column-item ${second === selectedTime.seconds ? 'time-picker__column-item--selected' : ''}"
510
- @click="${() => this.handleSecondSelect(second)}"
511
- >
512
- ${second.toString().padStart(2, '0')}
513
- </div>
514
- `)}
515
- </div>
516
- </div>
517
- `;
518
- }
519
- renderActions() {
520
- return html `
521
- <div class="time-picker__actions">
522
- <button
523
- class="time-picker__action-button"
524
- @click="${() => this.setToNow()}"
525
- >
526
- Now
527
- </button>
528
- <button
529
- class="time-picker__action-button time-picker__action-button--primary"
530
- @click="${() => this.closeClock()}"
531
- >
532
- OK
533
- </button>
534
- </div>
535
- `;
536
- }
537
- setToNow() {
538
- const now = TimeUtils.getCurrentTime();
539
- this.selectionController.selectTime(now);
540
- this.updateInputValue();
541
- }
542
- renderClockNumbers() {
543
- const numbers = this.getClockNumbers();
544
- return numbers.map((num, index) => {
545
- const angle = (index * 360) / numbers.length - 90;
546
- const radius = 110;
547
- const x = 50 + radius * Math.cos(angle * Math.PI / 180);
548
- const y = 50 + radius * Math.sin(angle * Math.PI / 180);
549
- const isSelected = this.isNumberSelected(num);
550
- return html `
551
- <div
552
- class="time-picker__clock-number ${isSelected ? 'time-picker__clock-number--selected' : ''}"
553
- style="left: ${x}%; top: ${y}%;"
554
- @click="${() => this.handleNumberClick(num)}"
555
- >
556
- ${num}
557
- </div>
558
- `;
559
- });
560
- }
561
- renderClockHand() {
562
- const selectedValue = this.getSelectedClockValue();
563
- const totalValues = this.getClockNumbers().length;
564
- const angle = (selectedValue * 360 / totalValues) - 90;
565
- return html `
566
- <div
567
- class="time-picker__clock-hand"
568
- part="clock-hand"
569
- style="
570
- width: 2px;
571
- height: 35%;
572
- top: 15%;
573
- left: calc(50% - 1px);
574
- transform: rotate(${angle}deg);
575
- "
576
- ></div>
577
- `;
578
- }
579
- renderModeButtons() {
580
- return html `
581
- <div class="time-picker__mode-buttons">
582
- <button
583
- class="time-picker__mode-button ${this.currentMode === TimePickerMode.Hours ? 'time-picker__mode-button--active' : ''}"
584
- @click="${() => this.handleModeChange(TimePickerMode.Hours)}"
585
- >
586
- Hours
587
- </button>
588
- <button
589
- class="time-picker__mode-button ${this.currentMode === TimePickerMode.Minutes ? 'time-picker__mode-button--active' : ''}"
590
- @click="${() => this.handleModeChange(TimePickerMode.Minutes)}"
591
- >
592
- Minutes
593
- </button>
594
- ${this.showSeconds ? html `
595
- <button
596
- class="time-picker__mode-button ${this.currentMode === TimePickerMode.Seconds ? 'time-picker__mode-button--active' : ''}"
597
- @click="${() => this.handleModeChange(TimePickerMode.Seconds)}"
598
- >
599
- Seconds
600
- </button>
601
- ` : nothing}
602
- </div>
603
- `;
604
- }
605
- renderDigitalInputs() {
606
- const selectedTime = this.selectionController.getSelectedTime() || EMPTY_TIME_VALUE;
607
- const config = this.getConfig();
608
- return html `
609
- <div class="time-picker__digital-inputs">
610
- <input
611
- type="number"
612
- class="time-picker__time-input"
613
- part="time-input"
614
- min="${config.format === TimeFormat.TwelveHour ? 1 : 0}"
615
- max="${config.format === TimeFormat.TwelveHour ? 12 : 23}"
616
- .value="${this.formattingController.formatHours(selectedTime.hours)}"
617
- @change="${(e) => this.handleDigitalTimeChange('hours', parseInt(e.target.value))}"
618
- />
619
- <span class="time-picker__separator">:</span>
620
- <input
621
- type="number"
622
- class="time-picker__time-input"
623
- part="time-input"
624
- min="0"
625
- max="59"
626
- .value="${this.formattingController.formatMinutes(selectedTime.minutes)}"
627
- @change="${(e) => this.handleDigitalTimeChange('minutes', parseInt(e.target.value))}"
628
- />
629
- ${this.showSeconds ? html `
630
- <span class="time-picker__separator">:</span>
631
- <input
632
- type="number"
633
- class="time-picker__time-input"
634
- part="time-input"
635
- min="0"
636
- max="59"
637
- .value="${this.formattingController.formatSeconds(selectedTime.seconds)}"
638
- @change="${(e) => this.handleDigitalTimeChange('seconds', parseInt(e.target.value))}"
639
- />
640
- ` : nothing}
641
- ${config.format === TimeFormat.TwelveHour ? this.renderPeriodToggle() : nothing}
642
- </div>
643
- `;
644
- }
645
- renderPeriodToggle() {
646
- const selectedTime = this.selectionController.getSelectedTime() || EMPTY_TIME_VALUE;
647
- const currentPeriod = this.formattingController.getPeriod(selectedTime.hours);
648
- return html `
649
- <div class="time-picker__period-toggle">
650
- <button
651
- class="time-picker__period-button ${currentPeriod === TimePeriod.AM ? 'time-picker__period-button--active' : ''}"
652
- @click="${() => this.handlePeriodToggle(TimePeriod.AM)}"
653
- >
654
- AM
655
- </button>
656
- <button
657
- class="time-picker__period-button ${currentPeriod === TimePeriod.PM ? 'time-picker__period-button--active' : ''}"
658
- @click="${() => this.handlePeriodToggle(TimePeriod.PM)}"
659
- >
660
- PM
661
- </button>
662
- </div>
663
- `;
664
- }
665
- renderActions() {
666
- return html `
667
- <div class="time-picker__actions">
668
- <button
669
- class="time-picker__action-button"
670
- @click="${() => this.clear()}"
671
- >
672
- Clear
673
- </button>
674
- <button
675
- class="time-picker__action-button"
676
- @click="${() => this.setToNow()}"
677
- >
678
- Now
679
- </button>
680
- >
681
- OK
682
- </button>
683
- </div>
684
- `;
685
- }
686
- renderHelperText() {
687
- const text = this.validationMessage || this.helperText;
688
- if (!text)
689
- return nothing;
690
- const isError = this.state === TimePickerState.Error || !!this.validationMessage;
691
- return html `
692
- <div class="time-picker__helper-text ${isError ? 'time-picker__helper-text--error' : ''}" part="helper-text">
693
- ${text}
694
- </div>
695
- `;
696
- }
697
- };
698
- NrTimePickerElement.styles = styles;
699
- __decorate([
700
- property({ type: String })
701
- ], NrTimePickerElement.prototype, "name", void 0);
702
- __decorate([
703
- property({ type: String })
704
- ], NrTimePickerElement.prototype, "value", void 0);
705
- __decorate([
706
- property({ type: String, attribute: 'default-value' })
707
- ], NrTimePickerElement.prototype, "defaultValue", void 0);
708
- __decorate([
709
- property({ type: Boolean, reflect: true })
710
- ], NrTimePickerElement.prototype, "disabled", void 0);
711
- __decorate([
712
- property({ type: Boolean, reflect: true })
713
- ], NrTimePickerElement.prototype, "readonly", void 0);
714
- __decorate([
715
- property({ type: Boolean })
716
- ], NrTimePickerElement.prototype, "required", void 0);
717
- __decorate([
718
- property({ type: String })
719
- ], NrTimePickerElement.prototype, "placeholder", void 0);
720
- __decorate([
721
- property({ type: String })
722
- ], NrTimePickerElement.prototype, "format", void 0);
723
- __decorate([
724
- property({ type: Boolean, attribute: 'show-seconds' })
725
- ], NrTimePickerElement.prototype, "showSeconds", void 0);
726
- __decorate([
727
- property({ type: Boolean, attribute: 'show-clock' })
728
- ], NrTimePickerElement.prototype, "showClock", void 0);
729
- __decorate([
730
- property({ type: Number, attribute: 'minute-interval' })
731
- ], NrTimePickerElement.prototype, "minuteInterval", void 0);
732
- __decorate([
733
- property({ type: Number, attribute: 'second-interval' })
734
- ], NrTimePickerElement.prototype, "secondInterval", void 0);
735
- __decorate([
736
- property({ type: String, attribute: 'min-time' })
737
- ], NrTimePickerElement.prototype, "minTime", void 0);
738
- __decorate([
739
- property({ type: String, attribute: 'max-time' })
740
- ], NrTimePickerElement.prototype, "maxTime", void 0);
741
- __decorate([
742
- property({ type: Array, attribute: 'disabled-times' })
743
- ], NrTimePickerElement.prototype, "disabledTimes", void 0);
744
- __decorate([
745
- property({ type: Array, attribute: 'enabled-times' })
746
- ], NrTimePickerElement.prototype, "enabledTimes", void 0);
747
- __decorate([
748
- property({ type: String, reflect: true })
749
- ], NrTimePickerElement.prototype, "size", void 0);
750
- __decorate([
751
- property({ type: String, reflect: true })
752
- ], NrTimePickerElement.prototype, "variant", void 0);
753
- __decorate([
754
- property({ type: String })
755
- ], NrTimePickerElement.prototype, "state", void 0);
756
- __decorate([
757
- property({ type: String })
758
- ], NrTimePickerElement.prototype, "placement", void 0);
759
- __decorate([
760
- property({ type: String })
761
- ], NrTimePickerElement.prototype, "label", void 0);
762
- __decorate([
763
- property({ type: String, attribute: 'helper-text' })
764
- ], NrTimePickerElement.prototype, "helperText", void 0);
765
- __decorate([
766
- property({ type: Boolean, reflect: true, attribute: 'clock-open' })
767
- ], NrTimePickerElement.prototype, "clockOpen", void 0);
768
- __decorate([
769
- property({ type: String, attribute: 'clock-mode' })
770
- ], NrTimePickerElement.prototype, "clockMode", void 0);
771
- __decorate([
772
- state()
773
- ], NrTimePickerElement.prototype, "inputValue", void 0);
774
- __decorate([
775
- state()
776
- ], NrTimePickerElement.prototype, "currentMode", void 0);
777
- __decorate([
778
- state()
779
- ], NrTimePickerElement.prototype, "validationMessage", void 0);
780
- __decorate([
781
- query(`#${TIME_INPUT_FIELD_ID}`)
782
- ], NrTimePickerElement.prototype, "inputElement", void 0);
783
- __decorate([
784
- query(`.${CLOCK_CONTAINER_CLASS}`)
785
- ], NrTimePickerElement.prototype, "clockContainer", void 0);
786
- NrTimePickerElement = __decorate([
787
- customElement('nr-timepicker')
788
- ], NrTimePickerElement);
789
- export { NrTimePickerElement };
790
- /div> `;
791
- }
792
-
793
- private renderHelperText(): TemplateResult | typeof nothing {
794
- const text = this.validationMessage || this.helperText;
795
- if (!text) return nothing;
796
-
797
- const isError = this.state === TimePickerState.Error || !!this.validationMessage;
798
-
799
- return html`
800
- < div;
801
- class {
802
- }
803
- "time-picker__helper-text ${isError ? 'time-picker__helper-text--error' : ''}";
804
- part = "helper-text" >
805
- $;
806
- {
807
- text;
808
- }
809
- /div> `;
810
- }
811
-
812
- // Helper methods for clock display
813
- private getClockNumbers(): number[] {
814
- switch (this.currentMode) {
815
- case TimePickerMode.Hours:
816
- return this.format === TimeFormat.TwelveHour
817
- ? Array.from({ length: 12 }, (_, i) => i + 1)
818
- : Array.from({ length: 24 }, (_, i) => i);
819
- case TimePickerMode.Minutes:
820
- case TimePickerMode.Seconds:
821
- return Array.from({ length: 12 }, (_, i) => i * 5);
822
- default:
823
- return [];
824
- }
825
- }
826
-
827
- private getSelectedClockValue(): number {
828
- const selectedTime = this.selectionController.getSelectedTime();
829
- if (!selectedTime) return 0;
830
-
831
- switch (this.currentMode) {
832
- case TimePickerMode.Hours:
833
- return this.format === TimeFormat.TwelveHour
834
- ? (selectedTime.hours % 12) || 12
835
- : selectedTime.hours;
836
- case TimePickerMode.Minutes:
837
- return selectedTime.minutes;
838
- case TimePickerMode.Seconds:
839
- return selectedTime.seconds;
840
- default:
841
- return 0;
842
- }
843
- }
844
-
845
- private isNumberSelected(num: number): boolean {
846
- const selectedValue = this.getSelectedClockValue();
847
-
848
- if (this.currentMode === TimePickerMode.Hours) {
849
- return num === selectedValue;
850
- } else {
851
- return num === Math.floor(selectedValue / 5) * 5;
852
- }
853
- }
854
-
855
- private handleNumberClick(num: number): void {
856
- const selectedTime = this.selectionController.getSelectedTime() || TimeUtils.getCurrentTime();
857
-
858
- let updatedTime: TimeValue;
859
-
860
- switch (this.currentMode) {
861
- case TimePickerMode.Hours:
862
- let hours = num;
863
- if (this.format === TimeFormat.TwelveHour) {
864
- const currentPeriod = this.formattingController.getPeriod(selectedTime.hours);
865
- if (currentPeriod === TimePeriod.PM && num !== 12) {
866
- hours += 12;
867
- } else if (currentPeriod === TimePeriod.AM && num === 12) {
868
- hours = 0;
869
- }
870
- }
871
- updatedTime = { ...selectedTime, hours };
872
- break;
873
- case TimePickerMode.Minutes:
874
- updatedTime = { ...selectedTime, minutes: num };
875
- break;
876
- case TimePickerMode.Seconds:
877
- updatedTime = { ...selectedTime, seconds: num };
878
- break;
879
- default:
880
- return;
881
- }
882
-
883
- if (this.validateTime(updatedTime)) {
884
- this.selectionController.selectTime(updatedTime);
885
- this.updateInputValue();
886
- }
887
- }
888
- }
889
- ;
890
- //# sourceMappingURL=timepicker.component.backup.js.map