Skip to content

Commit

Permalink
.
Browse files Browse the repository at this point in the history
  • Loading branch information
brc-dd committed Sep 25, 2024
1 parent 34c2529 commit 7375377
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 18 deletions.
11 changes: 9 additions & 2 deletions lib/components/SDatePicker.vue
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,14 @@ import { computed, nextTick, reactive, ref } from 'vue'
import { useLang } from '../composables/Lang'
import { type SDate, now } from '../support/Now'
const model = defineModel<SDate>({ required: true })
const selected = reactive(model.value)
const { selected } = defineProps<{
selected: SDate
}>()
const emit = defineEmits<{
'selected': [value: SDate]
}>()
const curr = reactive({ ...selected })
const mode = ref<'days' | 'months' | 'years'>('days')
Expand Down Expand Up @@ -117,6 +123,7 @@ function onSelected(/** 1-indexed */ i: number): void {
selected.year = getYearForIndex(i)
}
onZoomIn()
emit('selected', { ...selected })
}
function onFocused(/** 1-indexed */ i: number): void {
Expand Down
70 changes: 54 additions & 16 deletions lib/components/SInputDate.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
<script setup lang="ts">
import { type Component, computed } from 'vue'
import { type MaskInputOptions } from 'maska'
import { vMaska } from 'maska/vue'
import { type Component, computed, reactive, ref, watch } from 'vue'
import { type Validatable } from '../composables/Validation'
import { type Day, day } from '../support/Day'
import { type SDate, now } from '../support/Now'
import SDatePicker from './SDatePicker.vue'
import SInputBase from './SInputBase.vue'
export type Size = 'mini' | 'small' | 'medium'
Expand All @@ -19,30 +23,51 @@ const props = defineProps<{
checkColor?: Color
block?: boolean
disabled?: boolean
modelValue: Day | null
validation?: Validatable
hideError?: boolean
}>()
const emit = defineEmits<{
(e: 'update:model-value', value: Day | null): void
}>()
const modelValue = defineModel<Day | null>({ required: true })
const classes = computed(() => [
props.size ?? 'small'
])
const inputValue = ref('')
const dateValue = reactive({ ...now })
const value = computed(() => {
return props.modelValue
? props.modelValue.format('YYYY-MM-DD')
: null
watch(inputValue, () => {
const [year, month, day] = inputValue.value.split('-')
if (year && year.length === 4) {
const yearValue = Number.parseInt(year)
if (dateValue.year !== yearValue && yearValue >= 1900 && yearValue <= 2099) {
dateValue.year = yearValue
}
}
if (month && month.length === 2) {
const monthValue = Number.parseInt(month)
if (dateValue.month !== monthValue && monthValue >= 1 && monthValue <= 12) {
dateValue.month = monthValue
}
}
if (day && day.length === 2) {
const dayValue = Number.parseInt(day)
const daysInMonth = new Date(dateValue.year, dateValue.month, 0).getDate()
if (dateValue.day !== dayValue && dayValue >= 1 && dayValue <= daysInMonth) {
dateValue.day = dayValue
}
}
})
function emitInput(date?: string) {
emit('update:model-value', date ? day(date) : null)
const maskOptions: MaskInputOptions = {
mask: '####-##-##',
eager: true
}
const classes = computed(() => [props.size ?? 'small'])
function onSelected(date: SDate) {
inputValue.value = [date.year, date.month, date.day]
.map((value) => value.toString().padStart(2, '0')).join('-')
}
function emitBlur() {
function onBlur() {
setTimeout(() => {
props.validation && props.validation.$touch()
}, 100)
Expand All @@ -65,7 +90,20 @@ function emitBlur() {
:validation="validation"
>
<div class="container">
TODO
<input
:id="name"
:class="{ block, disabled }"
:disabled="disabled"
@blur="onBlur"
autocomplete="off"
class="input"
inputmode="numeric"
placeholder="YYYY-MM-DD"
type="text"
v-maska="maskOptions"
v-model="inputValue"
>
<SDatePicker :selected="dateValue" @selected="onSelected" />
</div>
<template v-if="$slots.info" #info><slot name="info" /></template>
</SInputBase>
Expand Down

0 comments on commit 7375377

Please sign in to comment.