58 lines
1.5 KiB
Vue
58 lines
1.5 KiB
Vue
|
<template>
|
||
|
<div>
|
||
|
<label :for="name">{{ label }}{{ required ? "" : " (optional)" }}</label>
|
||
|
<div class="relative flex flex-row items-center gap-2">
|
||
|
<input ref="resultInput" class="!pl-9" :id="name" type="text" v-model="value" :required="required" />
|
||
|
<QrCodeIcon class="absolute h-6 stroke-1 left-2 top-1/2 -translate-y-1/2 cursor-pointer z-10" @click="scanCode" />
|
||
|
</div>
|
||
|
</div>
|
||
|
</template>
|
||
|
|
||
|
<script setup lang="ts">
|
||
|
import { defineComponent, markRaw, defineAsyncComponent } from "vue";
|
||
|
import { QrCodeIcon } from "@heroicons/vue/24/outline";
|
||
|
import { useModalStore } from "../stores/modal";
|
||
|
import { mapActions } from "pinia";
|
||
|
</script>
|
||
|
|
||
|
<script lang="ts">
|
||
|
export default defineComponent({
|
||
|
props: {
|
||
|
label: String,
|
||
|
name: String,
|
||
|
required: {
|
||
|
type: Boolean,
|
||
|
default: true,
|
||
|
},
|
||
|
modelValue: {
|
||
|
type: String,
|
||
|
default: "",
|
||
|
required: false,
|
||
|
},
|
||
|
},
|
||
|
emits: ["update:model-value"],
|
||
|
computed: {
|
||
|
value: {
|
||
|
get() {
|
||
|
return this.modelValue;
|
||
|
},
|
||
|
set(val: String) {
|
||
|
this.$emit("update:model-value", val);
|
||
|
},
|
||
|
},
|
||
|
},
|
||
|
methods: {
|
||
|
...mapActions(useModalStore, ["openModal"]),
|
||
|
scanCode() {
|
||
|
this.openModal(
|
||
|
markRaw(defineAsyncComponent(() => import("@/components/CodeDetector.vue"))),
|
||
|
"codeScanInput",
|
||
|
(result: string) => {
|
||
|
(this.$refs.resultInput as HTMLInputElement).value = result;
|
||
|
}
|
||
|
);
|
||
|
},
|
||
|
},
|
||
|
});
|
||
|
</script>
|