new feature: drug Loli !

This commit is contained in:
KUN1007 2023-05-15 01:47:25 +08:00
parent c915ddf630
commit 51b03fa939
3 changed files with 136 additions and 108 deletions

View file

@ -45,7 +45,7 @@ const handleClick = () => {}
<Icon
class="moon"
icon="line-md:sunny-outline-to-moon-loop-transition"
/>we
/>
</li>
</div>
</div>
@ -68,7 +68,6 @@ const handleClick = () => {}
</div>
<!-- 看板娘组件 -->
<!-- 此处使用 Teleport如果固定看板娘则将看板娘传送到根组件 -->
<Drug />
<Teleport to="body" :disabled="showFixedLoli">
<Loli class="loli" :isShowFixedLoli="showFixedLoli" />
</Teleport>
@ -83,7 +82,7 @@ const handleClick = () => {}
width: 600px;
top: 65px;
right: 0;
position: fixed;
position: absolute;
background-color: @kungalgame-trans-white-5;
backdrop-filter: blur(5px);
border-radius: 10px;

View file

@ -6,33 +6,42 @@
@wheel.prevent="changeSize"
:style="boxStyle"
>
拖动我
<div
class="box1"
style="
position: relative;
width: 100%;
height: 100%;
background-color: aqua;
"
></div>
</div>
</template>
<script lang="ts">
import { ref, reactive, CSSProperties } from 'vue'
<script setup lang="ts">
import { ref, reactive, CSSProperties, onMounted, onBeforeUnmount } from 'vue'
export default {
setup() {
const box = ref<HTMLElement | null>(null)
const box = ref<HTMLElement | null>(null)
const state = reactive({
const state = reactive({
isDragging: false,
isResizing: false,
origin: { x: 0, y: 0 },
translation: { x: 0, y: 0 },
size: { width: 100, height: 100 },
})
})
const boxStyle: CSSProperties = {
const boxStyle: CSSProperties = {
position: 'absolute',
top: `${state.translation.y}px`,
left: `${state.translation.x}px`,
width: `${state.size.width}px`,
height: `${state.size.height}px`,
backgroundColor: '#ccc',
}
}
const startDrag = (event: MouseEvent) => {
const startDrag = (event: MouseEvent) => {
if (event.ctrlKey) {
state.isResizing = true
} else {
@ -40,14 +49,14 @@ const startDrag = (event: MouseEvent) => {
}
state.origin.x = event.clientX
state.origin.y = event.clientY
}
}
const stopDrag = () => {
const stopDrag = () => {
state.isDragging = false
state.isResizing = false
}
}
const drag = (event: MouseEvent) => {
const drag = (event: MouseEvent) => {
if (state.isDragging && box.value !== null) {
const deltaX = event.clientX - state.origin.x
const deltaY = event.clientY - state.origin.y
@ -58,9 +67,9 @@ const drag = (event: MouseEvent) => {
state.origin.x = event.clientX
state.origin.y = event.clientY
}
}
}
const changeSize = (event: WheelEvent) => {
const changeSize = (event: WheelEvent) => {
if (event.ctrlKey && box.value !== null) {
const delta = Math.sign(event.deltaY) * 3
state.size.width += delta
@ -68,15 +77,24 @@ const changeSize = (event: WheelEvent) => {
box.value.style.width = `${state.size.width}px`
box.value.style.height = `${state.size.height}px`
}
}
onMounted(() => {
window.addEventListener('mouseup', stopDrag)
window.addEventListener('mousemove', drag)
})
onBeforeUnmount(() => {
window.removeEventListener('mouseup', stopDrag)
window.removeEventListener('mousemove', drag)
})
</script>
}
<style scoped></style>
return {
box,
boxStyle,
startDrag,
stopDrag,
drag,
changeSize,
}
},
mounted() {
window.addEventListener('mouseup', this.stopDrag)
window.addEventListener('mousemove', this.drag)
},
beforeUnmount() {
window.removeEventListener('mouseup', this.stopDrag)
window.removeEventListener('mousemove', this.drag)
},
}
</script>

View file

@ -17,58 +17,66 @@ import {
mouth,
face,
} from '@/utils/loli'
import { onMounted, onUnmounted, ref } from 'vue'
interface Position {
x: number
y: number
}
const box = ref<HTMLElement | null>(null)
const isDragging = ref(false)
const mousePosition = ref<Position>({ x: 0, y: 0 })
const elementPosition = ref<Position>({ x: 120, y: -250 })
//
import { ref, reactive, CSSProperties, onMounted, onBeforeUnmount } from 'vue'
const handleMouseDown = (event: MouseEvent) => {
isDragging.value = true
mousePosition.value = { x: event.clientX, y: event.clientY }
const loli = ref<HTMLElement | null>(null)
const state = reactive({
isDragging: false,
isResizing: false,
origin: { x: 0, y: 0 },
translation: { x: 0, y: 0 },
})
const loliStyle: CSSProperties = {
top: `${state.translation.y}px`,
left: `${state.translation.x}px`,
}
const handleMouseMove = (event: MouseEvent) => {
if (isDragging.value) {
const deltaX = event.clientX - mousePosition.value.x
const deltaY = event.clientY - mousePosition.value.y
elementPosition.value = {
x: elementPosition.value.x + deltaX,
y: elementPosition.value.y + deltaY,
}
mousePosition.value = { x: event.clientX, y: event.clientY }
const startDragLoli = (event: MouseEvent) => {
if (event.ctrlKey) {
state.isResizing = true
} else {
state.isDragging = true
}
state.origin.x = event.clientX
state.origin.y = event.clientY
}
const handleMouseUp = () => {
isDragging.value = false
const stopDrag = () => {
state.isDragging = false
state.isResizing = false
}
const drag = (event: MouseEvent) => {
if (state.isDragging && loli.value !== null) {
const deltaX = event.clientX - state.origin.x
const deltaY = event.clientY - state.origin.y
state.translation.x += deltaX
state.translation.y += deltaY
loli.value.style.top = `${state.translation.y}px`
loli.value.style.left = `${state.translation.x}px`
state.origin.x = event.clientX
state.origin.y = event.clientY
}
}
onMounted(() => {
box.value?.addEventListener('mousedown', handleMouseDown)
box.value?.addEventListener('mousemove', handleMouseMove)
box.value?.addEventListener('mouseup', handleMouseUp)
window.addEventListener('mouseup', stopDrag)
window.addEventListener('mousemove', drag)
})
const loliPositionXPixel = elementPosition.value.x + 'px'
const loliPositionYPixel = elementPosition.value.y + 'px'
onUnmounted(() => {
box.value?.removeEventListener('mousedown', handleMouseDown)
box.value?.removeEventListener('mousemove', handleMouseMove)
box.value?.removeEventListener('mouseup', handleMouseUp)
onBeforeUnmount(() => {
window.removeEventListener('mouseup', stopDrag)
window.removeEventListener('mousemove', drag)
})
</script>
<template>
<!-- 看板娘 -->
<!-- 给看板娘整体绑定鼠标移动事件改变看板娘的位置 -->
<div class="loli">
<div class="loli" ref="loli" @mousedown="startDragLoli" :style="loliStyle">
<!-- 身体 -->
<img class="lass" :src="lass" alt="ren" />
<img class="eye" :src="eye" alt="ren" />
@ -82,10 +90,13 @@ onUnmounted(() => {
/* 看板娘 */
.loli {
height: 100%;
width: 300px;
/* 定位看板娘,重要 */
position: fixed;
z-index: 9999;
//
top: v-bind(loliPositionYPixel);
left: v-bind(loliPositionXPixel);
// top: v-bind(loliPositionYPixel);
// left: v-bind(loliPositionXPixel);
}
.lass {
position: absolute;