亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Vue3?實(shí)現(xiàn)一個(gè)自定義toast?小彈窗功能

 更新時(shí)間:2022年09月15日 16:16:47   作者:韓振方  
這篇文章主要介紹了Vue3?實(shí)現(xiàn)一個(gè)自定義toast?小彈窗,本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下

前言:

前兩天在項(xiàng)目中很多場(chǎng)景下都需要用到一個(gè)toast彈窗,項(xiàng)目使用的是ionic+tialwind_Css,ionic也有自帶的toast彈窗,雖然大部分場(chǎng)景下直接調(diào)用它提供的api已經(jīng)能滿足需求了,但是它彈窗的高度,(也就是彈窗出現(xiàn)的位置)并不是高度自定義的,并且彈窗的z-index在我們項(xiàng)目中會(huì)和一些組件沖突,但是這個(gè)之前一直沒(méi)有辦法解決,所以干脆自己手寫了一個(gè)使用方法高度類似ionic_Toast的組件。

這個(gè)組件也是我第一次在vue3下實(shí)現(xiàn)的,也查閱了很多網(wǎng)上相關(guān)的文章,也受到很多啟發(fā)靈感,所以自己吸取精華去其糟粕來(lái)完成了一版?zhèn)€人感覺(jué)使用起來(lái)很方便的一個(gè)版本,特來(lái)記錄一下實(shí)現(xiàn)的過(guò)程,希望可以幫助到遇到同樣迷惑的人。

tips:(本篇文章不會(huì)上手就教你樣式怎么寫,代碼怎么寫,而是會(huì)幫你逐漸一步步理解相關(guān)額外的知識(shí)。會(huì)以“假如我是一個(gè)初學(xué)者,如果當(dāng)時(shí)有人這樣告訴我的話,我就大概能聽(tīng)明白”的角度去解釋。所以篇幅較長(zhǎng),如果想直接看組件的實(shí)現(xiàn),可直接跳轉(zhuǎn)到標(biāo)題三)

下面是正文:

一. 前置任務(wù):JSX和渲染函數(shù)的概念

想要完成這個(gè)需求,你需要了解一下標(biāo)題的那兩個(gè)概念。官方文檔在這里,里面的話語(yǔ)太過(guò)于“專業(yè)和官方”,導(dǎo)致我剛開(kāi)始看的時(shí)候非常迷惑,所以在這里我會(huì)幫你去理解里面的一些很官方的言語(yǔ),讓你快速有個(gè)認(rèn)知。

原地址在這里:vue官方文檔JSX和渲染函數(shù)。

我們暫且還不需要去深入理解渲染機(jī)制的整個(gè)流程。所以官方下面?zhèn)€鏈接暫且不要去查閱,會(huì)讓你越來(lái)越頭暈。 但在這里我要說(shuō)明一點(diǎn),接下來(lái)講的內(nèi)容都是建立在我默認(rèn)你對(duì)虛擬DOM的概念有一定的了解。

緊接就寫到了Vue為我們提供了一個(gè)函數(shù),來(lái)創(chuàng)建vnodes。在閱讀這個(gè)頁(yè)面的時(shí)候,一定注意官方在每個(gè)代碼右上角的文件類型。

這里需要插個(gè)必須要了解的題外話,了解React的同學(xué)一定知道JSX這種寫法

Vue里JSX的概念和React的JSX的概念是極其相似的。Vue也是借鑒了React的這個(gè)思想,這里我們重點(diǎn)看畫線的這句話。(不熟悉react的小伙伴也不要擔(dān)心,本文實(shí)現(xiàn)的Toast并沒(méi)有使用到JSX和babel。)

是不是覺(jué)得和剛剛Vue官方寫的很相似?

官方在上文也提到了h是什么。如果我們把h換成createVnode(),是不是就和React.createElement的用法及其相似了呢?

其實(shí)不管是Vue的h(),還是React.createElement() 它們最終要達(dá)到的目的只有一個(gè):創(chuàng)建虛擬DOM。而這也對(duì)應(yīng)了Vue中createVnode的Vnode其實(shí)就是virtual node的意思。函數(shù)名的直接翻譯其實(shí)也就是創(chuàng)建虛擬節(jié)點(diǎn)。而JSX只是創(chuàng)建虛擬dom的語(yǔ)法題而已,僅此而已,并沒(méi)有什么特別之處。

二. createVnode函數(shù)的意義

現(xiàn)在我們?cè)?.Vue文件寫如下代碼。

非常簡(jiǎn)單的結(jié)構(gòu),一個(gè)id是"hanzhenfang"的div標(biāo)簽,標(biāo)簽內(nèi)容是我的名字。ok,這樣寫的話,vue就會(huì)幫我們將這個(gè)結(jié)構(gòu)轉(zhuǎn)換為虛擬dom。 本質(zhì)上是使用了

h("div",{id:"hanzhenfang"},"韓振方")

h()可以有多個(gè)參數(shù),

這段代碼是在<template>標(biāo)簽內(nèi)寫的,它底層其實(shí)還是使用了h() 函數(shù)去實(shí)現(xiàn)的。說(shuō)白了就是,React選用JSX來(lái)作為渲染虛擬dom函數(shù)的語(yǔ)法糖。而<template>標(biāo)簽是Vue采用的渲染虛擬dom的語(yǔ)法糖。

從而可以引出官方的標(biāo)準(zhǔn)解釋:

你可能會(huì)疑問(wèn)了,既然模板可以實(shí)現(xiàn)這樣的功能,那我直接寫模版不就完事了嗎?還需要寫什么h() 函數(shù)呢?因?yàn)橛械膱?chǎng)景確實(shí)是模板做不到的。這也就是我為什么會(huì)寫這篇文章的原因,因?yàn)檫@個(gè)toast需求使用的場(chǎng)景很多很多,我總不能在每個(gè)地方都引入一個(gè)組件通過(guò)v-if來(lái)控制它的顯示和關(guān)閉吧?非常繁瑣和麻煩。

三. 編寫Toast組件(不使用tsx)

1.首先創(chuàng)建一個(gè)toast.vue文件寫出大致樣式。由于是使用tailwindCss,所以樣式書寫的方式可能和傳統(tǒng)的在style標(biāo)簽寫樣式不太一樣,但是原理是一樣的,不用擔(dān)心。實(shí)現(xiàn)如下:

2.toast在絕大場(chǎng)景下都是居中的,并且脫離文檔流,位于整個(gè)頁(yè)面的最頂部,所以我這里采用了傳統(tǒng)的絕對(duì)定位的方案。

3.絕對(duì)定位最簡(jiǎn)單居中方案不過(guò)與設(shè)置top和left各50%。但是我們不要忽略了一點(diǎn),偏移的時(shí)候,我們還要減去自身寬度和高度的一半,才可以做到完全居中。但是處于復(fù)用性考慮,我們的toast的寬度是不能設(shè)置固定寬度的,具體的寬度是由當(dāng)時(shí)文字的大小決定的。

4.這時(shí)候我們需要用到offsetWidth

1.額外技能補(bǔ)充 offsetWidth

1.先讓我們看看MDN如何解釋的。

2.具體什么意思呢?我們隨手寫一個(gè)很簡(jiǎn)單的template。

我們現(xiàn)在不加任何Css屬性,來(lái)查看一下offsetWidth是什么值。

不要把調(diào)試工具只當(dāng)成console.log的地方,一定利用好這個(gè)工具。我們選擇剛剛寫的元素,點(diǎn)擊調(diào)試工具選項(xiàng)欄的Properties標(biāo)簽。

可以看到offsetWidth目前是20(注意,這是一個(gè)十進(jìn)制的number類型,并不帶單位,并且是一個(gè)只讀屬性,無(wú)法直接更改。) 20是怎么來(lái)的呢?其實(shí)它就是我們?cè)O(shè)置的字體大小。

來(lái)驗(yàn)證一下猜想,我們?cè)O(shè)置一下字體大小為15px

3.現(xiàn)在給這個(gè)div加上10px寬度的border。

別著急看offsetWidth的值,我們根據(jù)它的定義猜想一下。

應(yīng)該等于15px的字體大小+10px?

確定嗎,別忘了border是上下左右都為10px,所以根據(jù)猜想 `offsetWidht=15px + 10px + 10px

4.如果這個(gè)div我們自己設(shè)定寬度呢?我們來(lái)給它設(shè)定100px的寬度。

我們會(huì)發(fā)現(xiàn)offsetWidth的值變成了100

但是我明明有還有10px的border??!哪里去了?

你是否忘了我們現(xiàn)在大部分情況下使用的都是box-size:border-box呢?設(shè)置的寬度是包含border的。

驗(yàn)證一下,我們改變一下box-size的類型。

可以看出來(lái),offsetWidth就變成了100px+10px+10px

Tips:不過(guò)在本文中不會(huì)設(shè)置定寬去限制

四. Toast居中的思路

1.現(xiàn)在我們可以不設(shè)置Toast的寬度,并且拿到根據(jù)文字?jǐn)?shù)量不同所變化的寬度。由于這個(gè)屬性是組件掛載完畢以后才有的屬性,那么我們可以在onMounted里拿到。首先需要拿到元素本身,這里采用打ref的方式。

具體變量和代碼如下:不過(guò)多贅述

然后我們需要通過(guò)一個(gè)計(jì)算屬性動(dòng)態(tài)的計(jì)算出該組件的樣式;

ok,這樣就實(shí)現(xiàn)了居中的效果。并且不管我們?nèi)绾胃淖儍?nèi)容都沒(méi)關(guān)系。居中效果是動(dòng)態(tài)計(jì)算獲得的,并不是一開(kāi)始就寫死的。

五. Toast三個(gè)出現(xiàn)位置的思路

有些場(chǎng)景下Toast出現(xiàn)在底部并不是特別合適,所以我們還要考慮出現(xiàn)位置的問(wèn)題。這里簡(jiǎn)單設(shè)計(jì)另外兩個(gè),一個(gè)中間,一個(gè)偏頂部。實(shí)現(xiàn)起來(lái)也比較簡(jiǎn)單。我們讓它toastWrapperStyle計(jì)算top的偏移量也是一個(gè)動(dòng)態(tài)計(jì)算的就可以了。

我們就可以在后面給這個(gè)組件傳遞參數(shù)來(lái)控制具體的位置在哪里。 這個(gè)目前的代碼還動(dòng)態(tài)的展示效果,我們慢慢在后面體現(xiàn)。

tips:下面的章節(jié)是本文全篇重點(diǎn)

六*. h()函數(shù)的使用

我們創(chuàng)建一個(gè)toastCreator.ts的文件,便于函數(shù)式調(diào)用展示Toast組件。

準(zhǔn)備如下內(nèi)容,這里需要用到前面所提到的h(),還有render(),render你暫且可以理解為給你返回一個(gè)真實(shí)的DOM。因?yàn)閔() 是生成虛擬dom的,但是我們最終展示到頁(yè)面的是真實(shí)dom,我們之前不用在<template>標(biāo)簽內(nèi)不用執(zhí)行render是因?yàn)閂ue幫你調(diào)用了render()。但是我們?cè)谶@里相當(dāng)于手動(dòng)實(shí)現(xiàn)一個(gè)Vue的渲染過(guò)程,所以我們也同時(shí)需要用到這個(gè)函數(shù)。

同時(shí)把同文件夾下剛剛寫好的Toast.vue引入。class相關(guān)的知識(shí)不是本文的重點(diǎn),不了解的需要自行去查閱相關(guān)知識(shí),這點(diǎn)很重要。

增加了一個(gè)duration選項(xiàng),也就是持續(xù)時(shí)間,效果為Toast,在頁(yè)面出現(xiàn)多少秒后自動(dòng)消失。

然后我們需要編寫一個(gè)這個(gè)類本身的方法,名為present()(這里借鑒了ionic的Toast組件的調(diào)用名稱。) 這一步是重點(diǎn),也是比較難理解的一個(gè)點(diǎn)。 1.首先我們需要自己創(chuàng)建一個(gè)Vnode,經(jīng)過(guò)翻閱官網(wǎng)。(注意我們著重看JS的文件)。

2.我們得知,原來(lái)h() 函數(shù)可以直接接收一個(gè)組件模板作為參數(shù)。那么我們可以這樣寫:

這樣變量myToast就是一個(gè)Vnode了。

3.然后再調(diào)用引入的render() 函數(shù),我們自然而言的會(huì)想到這樣寫。

但是好像不太對(duì)勁啊,怎么報(bào)錯(cuò)了呢?看一下報(bào)錯(cuò)信息,原來(lái)render() 函數(shù)需要接收兩個(gè)參數(shù)。第一個(gè)參數(shù)是Vnode,第二個(gè)參數(shù)是套在Vnode的真實(shí)dom。

讓我們創(chuàng)建并且加上一層外殼containner。其實(shí)就是一個(gè)普通的div標(biāo)簽。如下:

在這里要強(qiáng)調(diào)一下,你創(chuàng)建的虛擬節(jié)點(diǎn)必須包裹一層真實(shí)的DOM作為容器。

這樣正好對(duì)應(yīng),為什么Vue或者React組項(xiàng)目的根目錄都會(huì)有一個(gè).html文件,并且還有一個(gè)根div標(biāo)簽的原因。 因?yàn)閞ender() 函數(shù)需要。(想更深入了解原理的可以翻看源碼,不再過(guò)多贅述。)

七. 如何傳遞props?

Vnode和真實(shí)DOM都有了,那我們?nèi)绾蝹鬟fprops呢?

2.這里不賣官子,先給結(jié)果,我們需要改造一下我們剛剛寫的h() 函數(shù)。

這樣即可將調(diào)用構(gòu)造函數(shù)時(shí)傳遞的參數(shù)轉(zhuǎn)換為該組件的props。 由于篇幅限制,具體細(xì)節(jié)大家仔細(xì)閱讀為上面貼出來(lái)的Vue官方文檔。

八. 掛載真實(shí)DOM到頁(yè)面上

都是基礎(chǔ)的知識(shí),不過(guò)多解釋了,代碼如下:

九. 持續(xù)時(shí)間的控制

編寫dismiss() 方法。非常簡(jiǎn)單,直接移除這個(gè)節(jié)點(diǎn)即可。

持續(xù)時(shí)間如何控制呢? 和時(shí)間掛鉤,自然而然可以想到setTimout()。實(shí)現(xiàn)原理其實(shí)也是非常簡(jiǎn)單。在特定的時(shí)間,調(diào)用dismiss() 方法即可

十. Toast自定義組件的使用方法

忘了寫message屬性了,我們補(bǔ)充一下

然后在App.vue文件引入

隨手寫一個(gè)<button>標(biāo)簽。

效果如下:

3.測(cè)試一下 position:top。

十一. 增加淡出的效果

我們項(xiàng)目不需要淡入,所以我就沒(méi)做,不過(guò)和淡出是如出一轍,在這里我講一下大致思路。 只需在dismiss() 函數(shù)執(zhí)行前,增加一個(gè)透明效果,這里使用的是增加類名,只不過(guò)這個(gè)動(dòng)畫名稱是搭配tailWind來(lái)完成的,你也可以使用別的方法,我的方法并不是最好的,原理思路是一致的

在tailwind.config.js下設(shè)置全局動(dòng)畫樣式。

這里需要注意??!你的動(dòng)畫持續(xù)時(shí)間要和dismiss()函數(shù)的setTimeout參數(shù)一致,不然會(huì)出現(xiàn)意想不到的效果。動(dòng)畫結(jié)束了,結(jié)果組件又出現(xiàn)啦。

2.再調(diào)用document.doby.removeChild方法之前,讓我們的組件在0.5s內(nèi)透明度變?yōu)?,然后再移除組件,就完美實(shí)現(xiàn)了淡出的效果。

?最終效果如下:

到此這篇關(guān)于Vue3 實(shí)現(xiàn)一個(gè)自定義toast 小彈窗的文章就介紹到這了,更多相關(guān)Vue3 toast小彈窗內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • vue使用echarts實(shí)現(xiàn)柱狀圖動(dòng)態(tài)排序效果

    vue使用echarts實(shí)現(xiàn)柱狀圖動(dòng)態(tài)排序效果

    echarts在前端開(kāi)發(fā)中實(shí)屬必不可缺的大數(shù)據(jù)可視化工具,這篇文章主要為大家詳細(xì)介紹了vue如何使用echarts實(shí)現(xiàn)柱狀圖動(dòng)態(tài)排序效果,感興趣的可以了解下
    2023-10-10
  • vue踩坑日記之params傳遞參數(shù)問(wèn)題

    vue踩坑日記之params傳遞參數(shù)問(wèn)題

    這篇文章主要介紹了vue踩坑日記之params傳遞參數(shù)問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-05-05
  • vue嵌入第三方頁(yè)面幾種常見(jiàn)方法

    vue嵌入第三方頁(yè)面幾種常見(jiàn)方法

    在Vue中嵌入第三方頁(yè)面可以采用多種方法,例如使用<iframe>、Vue插件、動(dòng)態(tài)加載第三方腳本或WebComponents,不同方法適用于不同類型的內(nèi)容和項(xiàng)目需求,如<iframe>適用于整個(gè)網(wǎng)頁(yè),而動(dòng)態(tài)腳本和WebComponents適合特定功能,選擇合適的方法可以有效整合外部資源
    2024-09-09
  • 詳解IOS微信上Vue單頁(yè)面應(yīng)用JSSDK簽名失敗解決方案

    詳解IOS微信上Vue單頁(yè)面應(yīng)用JSSDK簽名失敗解決方案

    這篇文章主要介紹了詳解IOS微信上Vue單頁(yè)面應(yīng)用JSSDK簽名失敗解決方案,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-11-11
  • 一篇文章帶你了解Vue組件的創(chuàng)建和使用

    一篇文章帶你了解Vue組件的創(chuàng)建和使用

    這篇文章主要為大家介紹了Vue組件的創(chuàng)建和使用,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下,希望能夠給你帶來(lái)幫助
    2021-12-12
  • vue el-table實(shí)現(xiàn)多選框回填的示例代碼

    vue el-table實(shí)現(xiàn)多選框回填的示例代碼

    摘要:Vue多選框回填是實(shí)現(xiàn)表單數(shù)據(jù)高效處理的常見(jiàn)需求,本文主要介紹了vue el-table實(shí)現(xiàn)多選框回填的示例代碼,具有一定的參考價(jià)值,感興趣的可以了解一下
    2024-01-01
  • vue項(xiàng)目打包清除console.log的四種方法總結(jié)

    vue項(xiàng)目打包清除console.log的四種方法總結(jié)

    大家在項(xiàng)目開(kāi)發(fā)的時(shí)候,需要看看一些后端接口返回的結(jié)果,會(huì)多次使用console.log項(xiàng)目開(kāi)發(fā)完成打包的時(shí)候,發(fā)現(xiàn)控制臺(tái)一堆的console.log,非常頭疼,下面這篇文章主要給大家介紹了關(guān)于vue項(xiàng)目打包清除console.log的四種方法,需要的朋友可以參考下
    2023-04-04
  • Vue中sync修飾符分析原理及用法示例

    Vue中sync修飾符分析原理及用法示例

    在vue中,子組件如果想修改父組件的變量,一般做法是通過(guò)綁定事件的方法,父組件向子組件傳遞修改變量的方法,子組件觸發(fā)修改變量的方法執(zhí)行,這種方式中規(guī)中矩;另一種方法是使用sync修飾符,此方法可以減少很多代碼量
    2022-08-08
  • vue2 webpack proxy與nginx配置方式

    vue2 webpack proxy與nginx配置方式

    這篇文章主要介紹了vue2 webpack proxy與nginx配置方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-10-10
  • Vue實(shí)現(xiàn)模糊查詢的簡(jiǎn)單示例

    Vue實(shí)現(xiàn)模糊查詢的簡(jiǎn)單示例

    在Vue中實(shí)現(xiàn)模糊查詢,你可以使用JavaScript的filter和includes方法,結(jié)合Vue的v-for指令,本文給大家舉了一個(gè)簡(jiǎn)單的示例,并通過(guò)代碼示例給大家介紹的非常詳細(xì),需要的朋友可以參考下
    2024-01-01

最新評(píng)論