最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

使用Vue3實現(xiàn)簡單的鼠標跟隨效果

 更新時間:2025年09月08日 16:37:04   作者:Xiecj  
鼠標跟隨效果是一種能顯著提升頁面交互性、增加動態(tài)感與趣味性的常見方式,本文將使用Vue3實現(xiàn)簡單的鼠標跟隨效果,希望對大家有所幫助

1. 創(chuàng)建組件基本結構

首先,創(chuàng)建一個 Vue3 組件,我們把它命名為 PageCursor.vue?;窘Y構如下:

<script setup lang="ts">
import { ref, onMounted, onUnmounted } from 'vue'

const props = withDefaults(defineProps<{
  hideCursorSelector?: string | string[]
}>(), {
  hideCursorSelector: '.hide-page-cursor'
})

const cursor = ref<HTMLElement | null>(null)
const cursorType = ref('auto')
const cursorState = ref('')

onMounted(() => {})

onUnmounted(() => {})
</script>

<template>
  <div
    ref="cursor"
    class="page-cursor"
    :class="[cursorType, cursorState]"
  ></div>
</template>

<style lang="scss" scoped>
.page-cursor {
  --cursor-size: 20px;
  position: fixed;
  z-index: 9999;
  top: calc(-1 * var(--cursor-size) / 2);
  left: calc(-1 * var(--cursor-size) / 2);
  width: var(--cursor-size);
  height: var(--cursor-size);
  border-radius: 50%;
  backdrop-filter: invert(100%);
  pointer-events: none;
  opacity: 0;
}
</style>

在組件中,我們定義了 props 對象、三個響應式對象和一個 page-cursor 樣式類

props 對象用于接收參數(shù)。使用 props 傳參可以在外部引用組件時控制組件的樣式或行為,這里我們只定義了一個 hideCursorSelector 參數(shù)用于設置隱藏光標這個行為。

三個響應式對象分別是:

  • cursor:跟隨鼠標運動的光標元素。
  • cursorType:光標的類型。
  • cursorState:光標的狀態(tài)。

page-cursor 樣式類:

  • --cursor-size:主要是設置光標的大小,后續(xù)有多個地方會用到,所以將其定義為 CSS 變量。
  • top、leftwidth、height:基于 --cursor-size 變量進行位置和大小的設置。
  • backdrop-filter:將其值設置為 invert(100%) 為光標后面區(qū)域添加反色效果。
  • pointer-events:將其值設置為 none 來禁用光標的指針事件,使其不會影響頁面上其他元素的交互。

2. 添加鼠標響應事件

添加鼠標響應事件(移動、按下、彈起)并在組件掛載時注冊事件,在組件卸載時移除事件:

function onMousemove() {}

function onMousedown() {}

function onMouseup() {}

onMounted(() => {
  document.addEventListener('mousemove', onMousemove)
  document.addEventListener('mousedown', onMousedown)
  document.addEventListener('mouseup', onMouseup)
})

onUnmounted(() => {
  document.removeEventListener('mousemove', onMousemove)
  document.removeEventListener('mousedown', onMousedown)
  document.removeEventListener('mouseup', onMouseup)
})

3. 實現(xiàn)具體功能

在 onMousedown 和 onMouseup 中修改光標狀態(tài):

function onMousedown() {
  cursorState.value = 'pressed'
}

function onMouseup() {
  cursorState.value = ''
}

在 onMousemove 事件中獲取鼠標位置,并在 requestAnimationFrame 方法中進行更新位置:

let myReq: number = 0

function onMousemove(event: MouseEvent) {
  if(!cursor.value) return

  cancelAnimationFrame(myReq)

  const { clientX, clientY } = event
  const target = event.target as HTMLElement

  myReq = requestAnimationFrame(() => {
    const style = cursor.value!.style
    style.transform = `translate3d(${clientX}px, ${clientY}px, 0)`
    cursorType.value = getComputedStyle(target)?.cursor || 'auto'

    const hideCursorSelectorList = Array.isArray(props.hideCursorSelector)
      ? props.hideCursorSelector
      : [props.hideCursorSelector]
    const hideCursor = hideCursorSelectorList.some(item => target.closest(item) !== null)
    style.opacity = hideCursor ? '0' : '1'
    style.transition = hideCursor ? '0.2s ease-out' : '0.125s ease-out'
  })
}

在這段代碼中,首先使用 cancelAnimationFrame 方法關閉之前創(chuàng)建的動畫幀任務。然后獲取當前鼠標的坐標和指向的元素。利用 requestAnimationFrame 方法在下一幀渲染前進行樣式設置,以防止在同一幀內執(zhí)行多次樣式設置。并使用 getComputedStyle 方法獲取當前鼠標指向元素的 CSS 屬性,并從中獲取鼠標指針的類型。

最后,將 hideCursorSelector 格式化為 hideCursorSelectorList,通過檢查鼠標指向元素與 hideCursorSelectorList 匹配特定選擇器且離當前元素最近的祖先元素是否存在來判斷是否隱藏光標。

4. 光標的狀態(tài)設置

.page-cursor {
  // 其他 page-cursor 樣式

  // 鼠標光標類型為指針時
  &.pointer {
    --cursor-size: 40px;

    // 指針類型并且按下時
    &.pressed {
      --cursor-size: 20px;
    }
  }

  // 默認類型按下時
  &.pressed {
    --cursor-size: 10px;
  }
}

你還可以在不同的鼠標事件中對 cursorState 和 cursorType 進行賦值,并對 page-cursor 樣式類進行更多的定義,來實現(xiàn)更多光標形態(tài)的展示。

5. 完整代碼

<script setup lang="ts">
import { ref, onMounted, onUnmounted } from 'vue'

const props = withDefaults(defineProps<{
  hideCursorSelector?: string | string[]
}>(), {
  hideCursorSelector: '.hide-page-cursor'
})

const cursor = ref<HTMLElement | null>(null)
const cursorType = ref('auto')
const cursorState = ref('')

let myReq: number = 0

function onMousemove(event: MouseEvent) {
  if(!cursor.value) return

  cancelAnimationFrame(myReq)

  const { clientX, clientY } = event
  const target = event.target as HTMLElement

  myReq = requestAnimationFrame(() => {
    const style = cursor.value!.style
    style.transform = `translate3d(${clientX}px, ${clientY}px, 0)`
    cursorType.value = getComputedStyle(target)?.cursor || 'auto'

    const hideCursorSelectorList = Array.isArray(props.hideCursorSelector)
      ? props.hideCursorSelector
      : [props.hideCursorSelector]
    const hideCursor = hideCursorSelectorList.some(item => target.closest(item) !== null)
    style.opacity = hideCursor ? '0' : '1'
    style.transition = hideCursor ? '0.2s ease-out' : '0.125s ease-out'
  })
}

function onMousedown() {
  cursorState.value = 'pressed'
}

function onMouseup() {
  cursorState.value = ''
}

onMounted(() => {
  globalThis.document.addEventListener('mousemove', onMousemove)
  globalThis.document.addEventListener('mousedown', onMousedown)
  globalThis.document.addEventListener('mouseup', onMouseup)
})

onUnmounted(() => {
  globalThis.document.removeEventListener('mousemove', onMousemove)
  globalThis.document.removeEventListener('mousedown', onMousedown)
  globalThis.document.removeEventListener('mouseup', onMouseup)
})
</script>

<template>
  <div
    ref="cursor"
    class="page-cursor"
    :class="[cursorType, cursorState]"
  ></div>
</template>

<style lang="scss" scoped>
.page-cursor {
  --cursor-size: 20px;
  position: fixed;
  z-index: 9999;
  top: calc(-1 * var(--cursor-size) / 2);
  left: calc(-1 * var(--cursor-size) / 2);
  width: var(--cursor-size);
  height: var(--cursor-size);
  border-radius: 50%;
  backdrop-filter: invert(100%);
  pointer-events: none;
  opacity: 0;

  &.pointer {
    --cursor-size: 40px;

    &.pressed {
      --cursor-size: 20px;
    }
  }

  &.pressed {
    --cursor-size: 10px;
  }
}
</style>

6.效果圖

到此這篇關于使用Vue3實現(xiàn)簡單的鼠標跟隨效果的文章就介紹到這了,更多相關Vue3鼠標跟隨內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • vue-router3.x和vue-router4.x相互影響的問題分析

    vue-router3.x和vue-router4.x相互影響的問題分析

    這篇文章主要介紹了vue-router3.x和vue-router4.x相互影響的問題分析,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2023-04-04
  • vue用addRoutes實現(xiàn)動態(tài)路由的示例

    vue用addRoutes實現(xiàn)動態(tài)路由的示例

    本篇文章主要介紹了vue用addRoutes實現(xiàn)動態(tài)路由的示例,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-09-09
  • BuildAdmin elementPlus自定義表頭添加tooltip方法示例

    BuildAdmin elementPlus自定義表頭添加tooltip方法示例

    這篇文章主要介紹了BuildAdmin elementPlus 自定義表頭,添加tooltip實現(xiàn)方法示例,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-09-09
  • Vue中v-bind原理深入探究

    Vue中v-bind原理深入探究

    這篇文章主要給大家分享了 v-bind的使用和注意需要注意的點,下面文章圍繞 v-bind指令的相關資料展開內容且附上詳細代碼 需要的小伙伴可以參考一下,希望對大家有所幫助
    2022-10-10
  • Vue3中unref的寫法代碼示例

    Vue3中unref的寫法代碼示例

    Vue3中多種響應式實現(xiàn)方式,包括ref、unref、isRef、reactive等,這篇文章主要介紹了Vue3中unref寫法的相關資料,文中通過代碼介紹的非常詳細,需要的朋友可以參考下
    2025-06-06
  • 一文帶你了解Vue數(shù)組的變異方法

    一文帶你了解Vue數(shù)組的變異方法

    Vue框架提供了一些便捷的數(shù)組變異方法,包括push、pop、shift、unshift、splice、sort和reverse等,Vue的數(shù)組變異方法可以自動觸發(fā)DOM更新,本文就詳細帶大家了解一下Vue.js數(shù)組的變異方法
    2023-06-06
  • vue中echarts自動輪播tooltip問題

    vue中echarts自動輪播tooltip問題

    這篇文章主要介紹了vue中echarts自動輪播tooltip問題,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-10-10
  • 聊聊vue集成sweetalert2提示組件的問題

    聊聊vue集成sweetalert2提示組件的問題

    這篇文章主要介紹了vue 集成 sweetalert2 提示組件的問題,本文通過項目案例實例代碼相結合給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友參考下吧
    2021-11-11
  • vue中如何使用ztree

    vue中如何使用ztree

    這篇文章主要介紹了vue中如何使用ztree,包括配置package.json,自動加載jquery的方法,本文給大家介紹的非常詳細,具有參考借鑒價值,需要的朋友可以參考下
    2018-02-02
  • 利用Vite搭建Vue3+ElementUI-Plus項目的全過程

    利用Vite搭建Vue3+ElementUI-Plus項目的全過程

    vue3如今已經成為默認版本了,相信大多數(shù)公司已經全面擁抱vue3了,下面這篇文章主要給大家介紹了關于利用Vite搭建Vue3+ElementUI-Plus項目的相關資料,文中通過實例代碼介紹的非常詳細,需要的朋友可以參考下
    2022-07-07

最新評論

忻城县| 雷山县| 井冈山市| 罗江县| 卓尼县| 若尔盖县| 成都市| 湖口县| 霍城县| 永城市| 鄂伦春自治旗| 名山县| 昌江| 瑞安市| 马边| 兴安盟| 抚州市| 叙永县| 禄丰县| 湟中县| 河北省| 长阳| 肥乡县| 容城县| 泾源县| 华阴市| 谢通门县| 临朐县| 衡阳县| 永丰县| 元朗区| 红原县| 宁波市| 扎囊县| 浮梁县| 长顺县| 多伦县| 庐江县| 六枝特区| 建阳市| 清远市|