43 lines
1.0 KiB
Vue
43 lines
1.0 KiB
Vue
<script setup lang="ts">
|
|
import { ref, watch } from 'vue'
|
|
|
|
const events = defineEmits<{
|
|
(event: 'submit', message: string): void
|
|
}>()
|
|
|
|
const input = defineModel<string>({
|
|
default: '',
|
|
})
|
|
|
|
const textareaRef = ref<HTMLTextAreaElement>()
|
|
const textareaHeight = ref('auto')
|
|
|
|
function onKeyDown(e: KeyboardEvent) {
|
|
if (e.code === 'Enter' && !e.shiftKey) { // just block Enter is enough, Shift+Enter by default generates a newline
|
|
e.preventDefault()
|
|
events('submit', input.value)
|
|
}
|
|
}
|
|
|
|
// javascript - Creating a textarea with auto-resize - Stack Overflow
|
|
// https://stackoverflow.com/questions/454202/creating-a-textarea-with-auto-resize
|
|
watch(input, () => {
|
|
textareaHeight.value = 'auto'
|
|
requestAnimationFrame(() => {
|
|
if (!textareaRef.value)
|
|
return
|
|
|
|
textareaHeight.value = `${textareaRef.value.scrollHeight}px`
|
|
})
|
|
}, { immediate: true })
|
|
</script>
|
|
|
|
<template>
|
|
<textarea
|
|
ref="textareaRef"
|
|
v-model="input"
|
|
:style="{ height: textareaHeight }"
|
|
@keydown="onKeyDown"
|
|
/>
|
|
</template>
|