https://github.com/huinalam/mole-virtual-keyboard
GitHub - huinalam/mole-virtual-keyboard: 한글 입력이 가능한 웹 전용 가상 키보드입니다.
한글 입력이 가능한 웹 전용 가상 키보드입니다. Contribute to huinalam/mole-virtual-keyboard development by creating an account on GitHub.
github.com
해당 소스를 참고하여 Vue 버전으로 만들었습니다.
CustomKeyboard.vue (가상키보드 컴포넌트)
<template>
<div ref="keyboardZone" class="keyboard-container">
<div v-for="(rows, index) in form[nowLang]" :key="index" class="keyboard-row">
<button v-for="(key, keyIndex) in rows" :key="keyIndex" class="keyboard-key" @click="handleKeyClick(key)">
{{ key }}
</button>
</div>
</div>
</template>
<script>
import Hangul from 'hangul-js'
export default {
props: {
inputValue: String,
onClick: Function,
onESC: Function,
onEnter: Function
},
data() {
return {
nowLang: 'koNormal',
charlist: [],
form: {
koNormal: [
['뒤로', '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', 'backspace'],
['ㅂ', 'ㅈ', 'ㄷ', 'ㄱ', 'ㅅ', 'ㅛ', 'ㅕ', 'ㅑ', 'ㅐ', 'ㅔ'],
['ㅁ', 'ㄴ', 'ㅇ', 'ㄹ', 'ㅎ', 'ㅗ', 'ㅓ', 'ㅏ', 'ㅣ', 'enter'],
['shift', 'ㅋ', 'ㅌ', 'ㅊ', 'ㅍ', 'ㅠ', 'ㅜ', 'ㅡ', '한/영'],
['space']
],
koShift: [
['뒤로', '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', 'backspace'],
['ㅃ', 'ㅉ', 'ㄸ', 'ㄲ', 'ㅆ', 'ㅛ', 'ㅕ', 'ㅑ', 'ㅒ', 'ㅖ'],
['ㅁ', 'ㄴ', 'ㅇ', 'ㄹ', 'ㅎ', 'ㅗ', 'ㅓ', 'ㅏ', 'ㅣ', 'enter'],
['shift', 'ㅋ', 'ㅌ', 'ㅊ', 'ㅍ', 'ㅠ', 'ㅜ', 'ㅡ', '한/영'],
['space']
],
enNormal: [
['뒤로', '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', 'backspace'],
['q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p'],
['a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', 'enter'],
['shift', 'z', 'x', 'c', 'v', 'b', 'n', 'm', '한/영'],
['space']
],
enShift: [
['뒤로', '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', 'backspace'],
['Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P'],
['A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', 'enter'],
['shift', 'Z', 'X', 'C', 'V', 'B', 'N', 'M', '한/영'],
['space']
]
}
}
},
methods: {
handleKeyClick(key) {
if (key === '뒤로') {
this.onESC && this.onESC()
} else if (key === 'enter') {
this.onEnter && this.onEnter(this.getText())
} else if (key === '한/영') {
this.toggleLanguage()
} else if (key === 'shift') {
this.toggleShift()
} else if (key === 'backspace') {
this.charlist.pop()
} else if (key === 'space') {
this.charlist.push(' ')
} else {
this.charlist.push(key)
}
this.$emit('update:inputValue', this.getText())
this.onClick && this.onClick(this.getText())
},
getText() {
return Hangul.assemble(this.charlist)
},
toggleLanguage() {
if (this.nowLang === 'koNormal') this.nowLang = 'enNormal'
else if (this.nowLang === 'enNormal') this.nowLang = 'koNormal'
else if (this.nowLang === 'koShift') this.nowLang = 'enShift'
else if (this.nowLang === 'enShift') this.nowLang = 'koShift'
},
toggleShift() {
if (this.nowLang === 'koNormal') this.nowLang = 'koShift'
else if (this.nowLang === 'enNormal') this.nowLang = 'enShift'
else if (this.nowLang === 'koShift') this.nowLang = 'koNormal'
else if (this.nowLang === 'enShift') this.nowLang = 'enNormal'
}
}
}
</script>
<style scoped>
.keyboard-container {
position: absolute;
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
align-items: center;
font-size: 25px;
background: #f5f5f5;
padding: 10px;
border-radius: 10px;
}
.keyboard-row {
display: flex;
width: 100%;
justify-content: center;
margin-bottom: 5px;
}
.keyboard-key {
padding: 10px 15px;
font-size: 20px;
margin: 2px;
border: 1px solid #ccc;
background: white;
cursor: pointer;
border-radius: 5px;
}
.keyboard-key:active {
background: #ddd;
}
</style>
부모 컴포넌트
<template>
<div>
<custom-keyboard v-model="name" :onClick="onClick" :onESC="onESC" :onEnter="onEnter" />
</div>
</template>
<script>
import CustomKeyboard from '@/components/CustomKeyboard.vue'
export default {
name: 'keyBoardParent',
components: {
CustomKeyboard,
},
data() {
return {
name: null,
}
},
methods: {
onClick(val) {
this.name = val;
},
onESC() {
console.log("뒤로가기");
},
onEnter(val) {
console.log("엔터 입력됨:", val);
}
},
watch:{
},
mounted() {
}
}
</script>