@nextcloud/vue
Version:
Nextcloud vue components
366 lines (365 loc) • 14.9 kB
JavaScript
import '../assets/NcDateTimePicker-D6xbEbaC.css';
import { defineComponent, mergeModels, useModel, useTemplateRef, computed, createElementBlock, openBlock, createVNode, createBlock, unref, mergeProps, createSlots, withCtx, createTextVNode, toDisplayString, Teleport, createElementVNode } from "vue";
import { v as mdiChevronUp, w as mdiChevronDown, c as mdiChevronRight, x as mdiChevronLeft, y as mdiClock, z as mdiCalendarBlank, b as mdiClose } from "./mdi-XFJRiRqJ.mjs";
import { getCanonicalLocale, getFirstDay, getDayNamesMin, getDayNames } from "@nextcloud/l10n";
import VueDatePicker from "@vuepic/vue-datepicker";
import { N as NcIconSvgWrapper } from "./NcIconSvgWrapper-BvLanNaW.mjs";
import { _ as _sfc_main$1 } from "./NcTimezonePicker.vue_vue_type_script_setup_true_lang-CGFRZR-3.mjs";
import { r as register, a as t } from "./_l10n-DrTiip5c.mjs";
import { N as NcButton } from "./NcButton-Dc8V4Urj.mjs";
import { _ as _export_sfc } from "./_plugin-vue_export-helper-1tPrXgE0.mjs";
register();
const _hoisted_1 = { class: "vue-date-time-picker__wrapper" };
const _hoisted_2 = {
ref: "target",
class: "vue-date-time-picker__wrapper vue-date-time-picker__wrapper--teleport"
};
const _sfc_main = /* @__PURE__ */ defineComponent({
__name: "NcDateTimePicker",
props: /* @__PURE__ */ mergeModels({
appendToBody: { type: Boolean },
ariaLabel: { default: t("Datepicker input") },
ariaLabelMenu: { default: t("Datepicker menu") },
clearable: { type: Boolean },
confirm: { type: Boolean },
format: { type: [String, Function], default: void 0 },
locale: { default: getCanonicalLocale() },
minuteStep: { default: 10 },
modelValue: { default: null },
placeholder: { default: void 0 },
showTimezoneSelect: { type: Boolean },
showWeekNumber: { type: Boolean },
type: { default: "date" }
}, {
"timezoneId": { default: "UTC" },
"timezoneIdModifiers": {}
}),
emits: /* @__PURE__ */ mergeModels(["update:modelValue", "update:timezoneId"], ["update:timezoneId"]),
setup(__props, { emit: __emit }) {
const timezoneId = useModel(__props, "timezoneId");
const props = __props;
const emit = __emit;
const targetElement = useTemplateRef("target");
const pickerInstance = useTemplateRef("picker");
const value = computed(() => {
if (props.modelValue === null && props.clearable) {
return null;
}
if (props.type === "week") {
const date = props.modelValue instanceof Date ? props.modelValue : /* @__PURE__ */ new Date();
const end = new Date(date);
end.setUTCDate(date.getUTCDate() + 6);
return [date, end];
} else if (props.type === "year") {
const date = props.modelValue instanceof Date ? props.modelValue : /* @__PURE__ */ new Date();
return date.getUTCFullYear();
} else if (props.type === "month") {
const date = props.modelValue instanceof Date ? props.modelValue : /* @__PURE__ */ new Date();
return { year: date.getUTCFullYear(), month: date.getUTCMonth() };
} else if (props.type === "time") {
const time = props.modelValue instanceof Date ? props.modelValue : /* @__PURE__ */ new Date();
return {
hours: time.getHours(),
minutes: time.getMinutes(),
seconds: time.getSeconds()
};
} else if (props.type === "time-range") {
const time = [props.modelValue].flat();
if (time.length !== 2) {
const start = /* @__PURE__ */ new Date();
const end = new Date(start);
end.setHours(end.getHours() + 1);
time.splice(0, 2, start, end);
}
return time.map((date) => ({
hours: date.getHours(),
minutes: date.getMinutes(),
seconds: date.getSeconds()
}));
} else if (props.type.endsWith("-range")) {
if (props.modelValue === void 0) {
const start = /* @__PURE__ */ new Date();
const end = new Date(start);
end.setUTCDate(start.getUTCDate() + 7);
return [start, end];
}
return props.modelValue;
}
return props.modelValue ?? /* @__PURE__ */ new Date();
});
const placeholderFallback = computed(() => {
if (props.type === "date") {
return t("Select date");
} else if (props.type === "time") {
return t("Select time");
} else if (props.type === "datetime") {
return t("Select date and time");
} else if (props.type === "week") {
return t("Select week");
} else if (props.type === "month") {
return t("Select month");
} else if (props.type === "year") {
return t("Select year");
} else if (props.type.endsWith("-range")) {
return t("Select time range");
}
return t("Select date and time");
});
const realFormat = computed(() => {
if (props.format) {
return props.format;
} else if (props.type === "week") {
return "RR-II";
}
let formatter;
if (props.type === "date" || props.type === "date-range") {
formatter = new Intl.DateTimeFormat(getCanonicalLocale(), { dateStyle: "medium" });
} else if (props.type === "time" || props.type === "time-range") {
formatter = new Intl.DateTimeFormat(getCanonicalLocale(), { timeStyle: "short" });
} else if (props.type === "datetime" || props.type === "datetime-range") {
formatter = new Intl.DateTimeFormat(getCanonicalLocale(), { dateStyle: "medium", timeStyle: "short" });
} else if (props.type === "month") {
formatter = new Intl.DateTimeFormat(getCanonicalLocale(), { year: "numeric", month: "2-digit" });
} else if (props.type === "year") {
formatter = new Intl.DateTimeFormat(getCanonicalLocale(), { year: "numeric" });
}
if (formatter) {
return (input) => Array.isArray(input) ? formatter.formatRange(input[0], input[1]) : formatter.format(input);
}
return void 0;
});
const pickerType = computed(() => ({
timePicker: props.type === "time" || props.type === "time-range",
yearPicker: props.type === "year",
monthPicker: props.type === "month",
weekPicker: props.type === "week",
range: props.type.endsWith("-range") && {
// do not use partial ranges (meaning after selecting the start [Date, null] will be emitted)
// if this is needed someday we can enable it,
// but its not covered by our component interface (props / events) documentation so just disabled for now.
partialRange: false
},
enableTimePicker: !(props.type === "date" || props.type === "date-range"),
flow: props.type === "datetime" ? ["calendar", "time"] : void 0
}));
function onUpdateModelValue(value2) {
if (value2 === null) {
return emit("update:modelValue", null);
}
if (props.type === "time") {
emit("update:modelValue", formatLibraryTime(value2));
} else if (props.type === "time-range") {
const start = formatLibraryTime(value2[0]);
const end = formatLibraryTime(value2[1]);
if (end.getTime() < start.getTime()) {
end.setDate(end.getDate() + 1);
}
emit("update:modelValue", [start, end]);
} else if (props.type === "month") {
const data = value2;
emit("update:modelValue", new Date(data.year, data.month, 1));
} else if (props.type === "year") {
emit("update:modelValue", new Date(value2, 0));
} else if (props.type === "week") {
emit("update:modelValue", value2[0]);
} else {
emit("update:modelValue", value2);
}
}
function formatLibraryTime(time) {
const date = /* @__PURE__ */ new Date();
date.setHours(time.hours);
date.setMinutes(time.minutes);
date.setSeconds(time.seconds);
return date;
}
const weekStart = getFirstDay();
const dayNames = [...getDayNamesMin()];
for (let i = 0; i < weekStart; i++) {
dayNames.push(dayNames.shift());
}
const weekNumName = t("W");
const ariaLabels = computed(() => ({
toggleOverlay: t("Toggle overlay"),
menu: props.ariaLabelMenu,
input: props.ariaLabel,
openTimePicker: t("Open time picker"),
closeTimePicker: t("Close time Picker"),
incrementValue: (type) => {
if (type === "hours") {
return t("Increment hours");
} else if (type === "minutes") {
return t("Increment minutes");
}
return t("Increment seconds");
},
decrementValue: (type) => {
if (type === "hours") {
return t("Decrement hours");
} else if (type === "minutes") {
return t("Decrement minutes");
}
return t("Decrement seconds");
},
openTpOverlay: (type) => {
if (type === "hours") {
return t("Open hours overlay");
} else if (type === "minutes") {
return t("Open minutes overlay");
}
return t("Open seconds overlay");
},
amPmButton: t("Switch AM/PM mode"),
openYearsOverlay: t("Open years overlay"),
openMonthsOverlay: t("Open months overlay"),
nextMonth: t("Next month"),
prevMonth: t("Previous month"),
nextYear: t("Next year"),
prevYear: t("Previous year"),
weekDay: (day) => getDayNames()[day],
clearInput: t("Clear value"),
calendarIcon: t("Calendar icon"),
timePicker: t("Time picker"),
monthPicker: (overlay) => overlay ? t("Month picker overlay") : t("Month picker"),
yearPicker: (overlay) => overlay ? t("Year picker overlay") : t("Year picker")
}));
function selectDate() {
pickerInstance.value.selectDate();
}
function cancelSelection() {
pickerInstance.value.closeMenu();
}
return (_ctx, _cache) => {
return openBlock(), createElementBlock("div", _hoisted_1, [
createVNode(unref(VueDatePicker), mergeProps({
ref: "picker",
"aria-labels": ariaLabels.value,
"auto-apply": !_ctx.confirm,
class: ["vue-date-time-picker", { "vue-date-time-picker--clearable": _ctx.clearable }],
"cancel-text": unref(t)("Cancel"),
clearable: _ctx.clearable,
"day-names": dayNames,
placeholder: _ctx.placeholder ?? placeholderFallback.value,
format: realFormat.value,
locale: _ctx.locale,
"minutes-increment": _ctx.minuteStep,
"model-value": value.value,
"now-button-label": unref(t)("Now"),
"select-text": unref(t)("Pick"),
"six-weeks": "fair",
teleport: _ctx.appendToBody ? targetElement.value || void 0 : false,
"text-input": "",
"week-num-name": unref(weekNumName),
"week-numbers": _ctx.showWeekNumber ? { type: "iso" } : void 0,
"week-start": unref(weekStart)
}, pickerType.value, { "onUpdate:modelValue": onUpdateModelValue }), createSlots({
"action-buttons": withCtx(() => [
createVNode(unref(NcButton), {
size: "small",
variant: "tertiary",
onClick: cancelSelection
}, {
default: withCtx(() => [
createTextVNode(toDisplayString(unref(t)("Cancel")), 1)
]),
_: 1
}),
createVNode(unref(NcButton), {
size: "small",
variant: "primary",
onClick: selectDate
}, {
default: withCtx(() => [
createTextVNode(toDisplayString(unref(t)("Pick")), 1)
]),
_: 1
})
]),
"clear-icon": withCtx(({ clear }) => [
createVNode(unref(NcButton), {
"aria-label": unref(t)("Clear value"),
variant: "tertiary-no-background",
onClick: clear
}, {
icon: withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiClose),
size: 20
}, null, 8, ["path"])
]),
_: 2
}, 1032, ["aria-label", "onClick"])
]),
"input-icon": withCtx(() => [
createVNode(NcIconSvgWrapper, {
path: unref(mdiCalendarBlank),
size: 20
}, null, 8, ["path"])
]),
"clock-icon": withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiClock),
size: 20
}, null, 8, ["path"])
]),
"arrow-left": withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiChevronLeft),
size: 20
}, null, 8, ["path"])
]),
"arrow-right": withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiChevronRight),
size: 20
}, null, 8, ["path"])
]),
"arrow-down": withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiChevronDown),
size: 20
}, null, 8, ["path"])
]),
"arrow-up": withCtx(() => [
createVNode(NcIconSvgWrapper, {
inline: "",
path: unref(mdiChevronUp),
size: 20
}, null, 8, ["path"])
]),
_: 2
}, [
_ctx.showTimezoneSelect ? {
name: "action-extra",
fn: withCtx(() => [
createVNode(_sfc_main$1, {
modelValue: timezoneId.value,
"onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => timezoneId.value = $event),
class: "vue-date-time-picker__timezone",
"append-to-body": false,
"input-label": unref(t)("Time zone")
}, null, 8, ["modelValue", "input-label"])
]),
key: "0"
} : void 0
]), 1040, ["aria-labels", "auto-apply", "class", "cancel-text", "clearable", "placeholder", "format", "locale", "minutes-increment", "model-value", "now-button-label", "select-text", "teleport", "week-num-name", "week-numbers", "week-start"]),
(openBlock(), createBlock(Teleport, {
to: "body",
disabled: !_ctx.appendToBody
}, [
createElementVNode("div", _hoisted_2, null, 512)
], 8, ["disabled"]))
]);
};
}
});
const NcDateTimePicker = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-c436522a"]]);
export {
NcDateTimePicker as N
};
//# sourceMappingURL=NcDateTimePicker-DTf51PD8.mjs.map