TimeInput: add confirmation text

This commit is contained in:
Elijah Duffy
2025-05-20 10:49:44 -07:00
parent 9a820794a2
commit 72bc7e23b4
5 changed files with 25 additions and 48 deletions

View File

@@ -1,10 +0,0 @@
import type { Snippet } from 'svelte';
type $$ComponentProps = {
for: string;
error?: boolean;
bigError?: boolean;
children: Snippet;
};
declare const Label: import("svelte").Component<$$ComponentProps, {}, "">;
type Label = ReturnType<typeof Label>;
export default Label;

View File

@@ -1,12 +0,0 @@
import type { HTMLInputAttributes } from 'svelte/elements';
import { type InputValidatorEvent, type ValidatorOptions } from '@repo/validate';
type $Props = Omit<HTMLInputAttributes, 'name' | 'value'> & {
name: string;
value?: string;
validate?: ValidatorOptions;
ref?: HTMLInputElement | null;
onvalidate?: (e: InputValidatorEvent) => void;
};
declare const StyledRawInput: import("svelte").Component<$Props, {}, "value" | "ref">;
type StyledRawInput = ReturnType<typeof StyledRawInput>;
export default StyledRawInput;

View File

@@ -1,5 +1,5 @@
<script lang="ts">
import { inputValidator, keydownValidator, liveValidator, validate } from '@repo/validate';
import { liveValidator, validate } from '@repo/validate';
import Label from './Label.svelte';
import StyledRawInput from './StyledRawInput.svelte';
import { onMount } from 'svelte';
@@ -12,7 +12,7 @@
formattedValue = $bindable(''),
required,
invalidMessage = 'Please select a time',
showText = false
showConfirm = false
}: {
name: string;
label?: string;
@@ -20,7 +20,7 @@
formattedValue?: string;
required?: boolean;
invalidMessage?: string;
showText?: boolean;
showConfirm?: boolean;
} = $props();
let ampm: 'AM' | 'PM' = $state('AM');
@@ -145,6 +145,7 @@
if (isNaN(hourValue)) {
value = '';
formattedValue = '';
updateHiddenInput();
return;
}
@@ -162,6 +163,8 @@
updateHiddenInput();
// update formatted value
const date = moment(value, 'HH:mm');
formattedValue = date.format('h:mm A');
};
/**
@@ -214,6 +217,11 @@
onkeydown={(e) => {
if (!hourInput) return;
if (e.key === ':' && hourInput.value.length !== 0) {
minuteInput?.focus();
e.preventDefault();
}
if (e.key === 'ArrowRight' && hourInput.selectionEnd === hourInput.value.length) {
minuteInput?.focus();
}
@@ -230,7 +238,6 @@
}
if (e.key === 'ArrowUp' || e.key === 'ArrowDown') {
e.preventDefault();
return;
}
}}
oninput={() => {
@@ -305,7 +312,7 @@
<div class="flex flex-col">
<!-- AM Button -->
<button
class={['ampm rounded-t-sm border', ampm === 'AM' && 'selected ring-1 ring-blue-300']}
class={['ampm rounded-t-sm border', ampm === 'AM' && 'selected']}
onclick={() => {
ampm = 'AM';
updateValue();
@@ -321,10 +328,7 @@
<!-- PM Button -->
<button
class={[
'ampm rounded-b-sm border-r border-b border-l',
ampm === 'PM' && 'selected ring-1 ring-blue-300'
]}
class={['ampm rounded-b-sm border-r border-b border-l', ampm === 'PM' && 'selected']}
onclick={() => {
ampm = 'PM';
updateValue();
@@ -339,9 +343,13 @@
</div>
</div>
<div class={['opacity-0 transition-opacity', !valid && 'opacity-100']}>
<Label for={name} error>
{invalidMessage}
<div class={['opacity-0 transition-opacity', (!valid || showConfirm) && 'opacity-100']}>
<Label for={name} error={!valid}>
{#if !valid}
{invalidMessage}
{:else if showConfirm}
{formattedValue !== '' ? `See you at ${formattedValue}!` : ''}
{/if}
</Label>
</div>
</div>
@@ -367,7 +375,7 @@
@apply border-accent dark:border-accent/50 cursor-pointer px-3 py-1 font-medium;
&.selected {
@apply bg-accent text-background dark:bg-accent/30 dark:text-background/90 ring-1 ring-blue-600 dark:ring-blue-300;
@apply bg-accent text-background dark:bg-accent/30 dark:text-background/90 ring-1 ring-black dark:ring-blue-300;
}
}
</style>

View File

@@ -1,10 +0,0 @@
type $$ComponentProps = {
name: string;
label?: string;
value?: string;
required?: boolean;
invalidMessage?: string;
};
declare const TimeInput: import("svelte").Component<$$ComponentProps, {}, "value">;
type TimeInput = ReturnType<typeof TimeInput>;
export default TimeInput;