例如:我们的代码编辑器
终端与代码区,可以纵向拖拽,改变两个容器高度
目录与代码区可以横向拖拽,改变两个容器宽度
本文使用vue3+ts+tailwindcss,把横向纵向整合在一起写了,也可以分开使用
utils目录下新建一个drag.ts文件
import { Ref } from 'vue'
interface ResizeOptions {
rightRef?: Ref<HTMLElement | null>
bottomRef?: Ref<HTMLElement | null>
}
const useResize = ({ rightRef, bottomRef }: ResizeOptions) => {
let startX = 0
let startWidth = 0
let isHorizonResizing = false
let startY = 0
let startHeight = 0
let isVerticalResizing = false
const startHorizonResize = (event: MouseEvent) => {
if (rightRef && rightRef.value) {
startX = event.clientX
startWidth = rightRef.value.offsetWidth
isHorizonResizing = true
window.addEventListener('mousemove', doHorizonResize)
window.addEventListener('mouseup', stopHorizonResize)
}
}
const doHorizonResize = (event: MouseEvent) => {
if (isHorizonResizing && rightRef && rightRef.value) {
const deltaX = event.clientX - startX
rightRef.value.style.width = startWidth - deltaX + 'px'
}
}
const stopHorizonResize = () => {
isHorizonResizing = false
window.removeEventListener('mousemove', doHorizonResize)
window.removeEventListener('mouseup', stopHorizonResize)
}
const startVerticalResize = (event: MouseEvent) => {
if (bottomRef && bottomRef.value) {
startY = event.clientY
startHeight = bottomRef.value.offsetHeight
isVerticalResizing = true
window.addEventListener('mousemove', doVerticalResize)
window.addEventListener('mouseup', stopVerticalResize)
}
}
const doVerticalResize = (event: MouseEvent) => {
if (isVerticalResizing && bottomRef && bottomRef.value) {
const deltaY = event.clientY - startY
bottomRef.value.style.height = startHeight - deltaY + 'px'
}
}
const stopVerticalResize = () => {
isVerticalResizing = false
window.removeEventListener('mousemove', doVerticalResize)
window.removeEventListener('mouseup', stopVerticalResize)
}
return {
startHorizonResize,
startVerticalResize,
}
}
export default useResize
使用
<template>
<div class="h-full w-full flex">
<div class="flex-1 h-full min-w-[100px] w-[300px] bg-[#c1ddfb]"></div>
<div class="cursor-col-resize h-full w-[2px] bg-[#000]" @mousedown.stop.prevent="startHorizonResize"></div>
<div class="h-full w-[calc(100%-300px)] min-w-[500px]" ref="refRight">
<div class="w-full h-full flex flex-col">
<div class="flex-1 bg-[#ebbbdd] h-[400px] min-h-[100px] w-full"></div>
<div class="cursor-row-resize h-[2px] bg-[#333] w-full" @mousedown.stop.prevent="startVerticalResize"></div>
<div class="bg-[#c0eaab] h-[calc(100%-400px)] min-h-[100px] w-full" ref="refBottom"></div>
</div>
</div>
</div>
</template>
<script setup lang="ts">
import { ref } from 'vue'
import useResize from '@/utils/drag'
const refRight = ref<HTMLElement | null>(null)
const refBottom = ref<HTMLElement | null>(null)
const { startHorizonResize, startVerticalResize } = useResize({ rightRef: refRight, bottomRef: refBottom })
</script>
<style scoped></style>