圖標選擇器

一笛臣、巧用兩次watch監(jiān)聽控制彈窗的顯示

1.在component文件夾下創(chuàng)建文件夾chooseIcon,創(chuàng)建對應文件
2.在views下面注冊組件,然后在router下面配置路由

 {
                path:'/chooseIcon',
                component:() => import ('../views/chooseIcon/index.vue')
            }

3.代碼
(1)component/chooseIcon/src/index.vue

<template>
    <el-button @click="handleClick" type="primary">
        <slot></slot>
    </el-button>
    <el-dialog :title="title" v-model="dialogVisible">哇大美女</el-dialog>
</template>

<script lang="ts" setup>
import { ref, watch } from "@vue/runtime-core"

let props = defineProps<{
    //彈出框的標題
    title:string,
    //控制彈出框的顯示與隱藏
    visible:boolean
}>()
let emits = defineEmits(['update:visible'])

//拷貝一份父組件傳遞過來的visible
let dialogVisible = ref<boolean>(props.visible)
let handleClick = ()=>{
    //需要修改父組件的數(shù)據
    emits('update:visible',!props.visible)

}
//監(jiān)聽visible的變化,只能監(jiān)聽第一次變化尸饺,val為變化之后的數(shù)據
watch(()=>props.visible,val =>{
    dialogVisible.value=val
    //emits('update:visible',val)
})

//監(jiān)聽組件內部dialogVisible的變化
watch(()=>dialogVisible.value,val=>{
    emits('update:visible',val)
})
</script>

<style lang="scss" scoped>

</style>

這里采用了兩次watch監(jiān)聽进统,來控制彈框的顯示與隱藏
拷貝之后,使用dialogVisible所有監(jiān)聽的visible變化只有第一次與父組件有關浪听,后面的變化都有只與自己內部的visible有關螟碎,與父組件無關
(2)views/chooseIcon/index.vue

<template>
    <div>
        <m-choose-icon title="選擇圖標" v-model:visible="visible">
            選擇圖標
        </m-choose-icon>
    </div>
</template>

<script lang="ts" setup>
import { ref } from '@vue/reactivity'
import mChooseIcon from '../../components/chooseIcon/src/index.vue' 

let visible = ref<boolean>(false)
</script>

<style lang="scss" scoped>

</style>

二、巧用component動態(tài)組件顯示所有圖標

component/chooseIcon/src/index.vue

<template>
    <el-button @click="handleClick" type="primary">
        <slot></slot>
    </el-button>
    <el-dialog :title="title" v-model="dialogVisible">
        <div class="container">
            <div 
                class="item"
                v-for="(item,index) in Object.keys(ElIcons)"
                :key="index"
            >
                <div class="text">
                    <component :is="`el-icon-${toLine(item)}`"></component>
                </div>
                <div class="icon">{{item}}</div>
            </div>
        </div>
    </el-dialog>
</template>

<script lang="ts" setup>
import * as  ElIcons from '@element-plus/icons';
import { ref, watch } from "@vue/runtime-core";
import { toLine } from '../../../utils';
let props = defineProps<{
    //彈出框的標題
    title:string,
    //控制彈出框的顯示與隱藏
    visible:boolean
}>()
let emits = defineEmits(['update:visible'])

//拷貝一份父組件傳遞過來的visible
let dialogVisible = ref<boolean>(props.visible)
let handleClick = ()=>{
    //需要修改父組件的數(shù)據
    emits('update:visible',!props.visible)

}
//監(jiān)聽visible的變化,只能監(jiān)聽第一次變化,val為變化之后的數(shù)據
watch(()=>props.visible,val =>{
    dialogVisible.value=val
    //emits('update:visible',val)
})

//監(jiān)聽組件內部dialogVisible的變化
watch(()=>dialogVisible.value,val=>{
    emits('update:visible',val)
})
</script>

<style lang="scss" scoped>
.container{
    display: flex;
    align-items: center;//垂直方向居中
    flex-wrap: wrap;//換行
}
.item{
    width: 25%;
    height: 70px;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;//水平方向居中
    margin-bottom: 20px;
    cursor: pointer;//使得到時候可以點進去復制
}
.text{
    font-size: 14px;
}
.icon{
    flex: 1;
}
svg{
    width: 2em;
    height: 2em;
}
</style>

*不能循環(huán)對象迹栓,所有在取圖標庫的使用要用

v-for="(item,index) in Object.keys(ElIcons)"

三掉分、利用命名空間修改dialog樣式

修改組件庫內部樣式

1.自定義一個類名空間
2.現(xiàn)在瀏覽器里面調試樣式
3.把調試好的類名放在入這個類名里面
4.在App.vue里面引入這個文件
5.在組件內需要改樣式的元素的父元素加上這個類名

代碼

index.vue

<template>
    <el-button @click="handleClick" type="primary">
        <slot></slot>
    </el-button>
    <div class="m-choose-icon-dialog-body-height">
        <el-dialog :title="title" v-model="dialogVisible">
            <div class="container">
                <div 
                    class="item"
                    v-for="(item,index) in Object.keys(ElIcons)"
                    :key="index"
                >
                    <div class="text">
                        <component :is="`el-icon-${toLine(item)}`"></component>
                    </div>
                    <div class="icon">{{item}}</div>
                </div>
            </div>
        </el-dialog>
    </div>
    
</template>


<script lang="ts" setup>
import * as  ElIcons from '@element-plus/icons';
import { ref, watch } from "@vue/runtime-core";
import { toLine } from '../../../utils';
let props = defineProps<{
    //彈出框的標題
    title:string,
    //控制彈出框的顯示與隱藏
    visible:boolean
}>()
let emits = defineEmits(['update:visible'])

//拷貝一份父組件傳遞過來的visible
let dialogVisible = ref<boolean>(props.visible)
let handleClick = ()=>{
    //需要修改父組件的數(shù)據
    emits('update:visible',!props.visible)

}
//監(jiān)聽visible的變化,只能監(jiān)聽第一次變化,val為變化之后的數(shù)據
watch(()=>props.visible,val =>{
    dialogVisible.value=val
    //emits('update:visible',val)
})

//監(jiān)聽組件內部dialogVisible的變化
watch(()=>dialogVisible.value,val=>{
    emits('update:visible',val)
})
</script>

<style lang="scss" scoped>
.container{
    display: flex;
    align-items: center;//垂直方向居中
    flex-wrap: wrap;//換行
}
.item{
    width: 25%;
    height: 70px;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;//水平方向居中
    margin-bottom: 20px;
    cursor: pointer;//使得到時候可以點進去復制
}
.text{
    font-size: 14px;
}
.icon{
    flex: 1;
}
svg{
    width: 2em;
    height: 2em;
}
</style>

styles/ui.scss

.m-choose-icon-dialog-body-height{
    .el-dialog__body{
        height: 500px;
        overflow: scroll;
    }
}

App.vue

<template>
    <router-view></router-view>
</template>

<style>
@import './styles/base.scss';
@import './styles/ui.scss';
</style>

(1)這里記得,一些基本的樣式我們都可以將它們封裝到styles文件夾下面的一個文件下克伊,然后進行引入
(2)我在這里把之前的App.vue中的基本樣式封裝到了styles下面的base.scss

*{
    margin: 0;
    padding: 0;
}

html,body,#app,.el-container,.el-menu{
    height: 100%;

}

svg{
    width: 1em;
    height: 1em;
  }

四酥郭、通過自定義hooks函數(shù)實現(xiàn)復制功能

1.創(chuàng)建hooks文件夾,在下面的文件中定義useCopy函數(shù)
hooks/useCopy/useCopy.ts

import { ElMessage } from "element-plus"

//復制文本
export const useCopy  = (text:string)=>{
    //1.創(chuàng)建一個input框
    let input = document.createElement('input')
    //2.給輸入框value賦值
    input.value=text
    //3.追加到body里面去
    document.body.appendChild(input)
    //4.選擇輸入框的操作
    input.select()
    //5.執(zhí)行復制操作
    document.execCommand('Copy')
    //刪除加入的輸入框
    document.body.removeChild(input)
    //提示用戶
    ElMessage.success('復制成功')
}

component/chooseIcon/src/index.vue

<template>
    <el-button @click="handleClick" type="primary">
        <slot></slot>
    </el-button>
    <div class="m-choose-icon-dialog-body-height">
        <el-dialog :title="title" v-model="dialogVisible">
            <div class="container">
                <div 
                    class="item"
                    v-for="(item,index) in Object.keys(ElIcons)"
                    :key="index"
                    @click="()=>clickItem(item)"
                >
                    <div class="text">
                        <component :is="`el-icon-${toLine(item)}`"></component>
                    </div>
                    <div class="icon">{{item}}</div>
                </div>
            </div>
        </el-dialog>
    </div>
    
</template>


<script lang="ts" setup>
import * as  ElIcons from '@element-plus/icons';
import { ref, watch } from "@vue/runtime-core";
import { toLine } from '../../../utils';
import { useCopy } from '../../../hooks/useCopy/useCopy'
let props = defineProps<{
    //彈出框的標題
    title:string,
    //控制彈出框的顯示與隱藏
    visible:boolean
}>()
let emits = defineEmits(['update:visible'])

//拷貝一份父組件傳遞過來的visible
let dialogVisible = ref<boolean>(props.visible)
//點擊按鈕顯示彈出框
let handleClick = ()=>{
    //需要修改父組件的數(shù)據
    emits('update:visible',!props.visible)

}
//監(jiān)聽visible的變化,只能監(jiān)聽第一次變化,val為變化之后的數(shù)據
watch(()=>props.visible,val =>{
    dialogVisible.value=val
    //emits('update:visible',val)
})

//監(jiān)聽組件內部dialogVisible的變化
watch(()=>dialogVisible.value,val=>{
    emits('update:visible',val)
})

//點擊圖標
let clickItem = (item:string) =>{
    let text = `<el-icon-${toLine(item)} />`
    //復制文本
    useCopy(text)
    //關閉彈框
    dialogVisible.value=false
}
</script>

<style lang="scss" scoped>
.container{
    display: flex;
    align-items: center;//垂直方向居中
    flex-wrap: wrap;//換行
}
.item{
    width: 25%;
    height: 70px;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;//水平方向居中
    margin-bottom: 20px;
    cursor: pointer;//使得到時候可以點進去復制
}
.text{
    font-size: 14px;
}
.icon{
    flex: 1;
}
svg{
    width: 2em;
    height: 2em;
}
</style>

四運行出來的界面

圖標選擇器.png

圖標選擇.png

圖標復制.png

***點擊選擇圖標才會彈出來選擇框愿吹,點擊選擇框右上角的叉叉或者其他地方都可隱藏選擇框,點擊圖標會進行復制不从,然后彈框會隱藏

?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市犁跪,隨后出現(xiàn)的幾起案子椿息,更是在濱河造成了極大的恐慌歹袁,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件寝优,死亡現(xiàn)場離奇詭異宇攻,居然都是意外死亡,警方通過查閱死者的電腦和手機倡勇,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來嘉涌,“玉大人妻熊,你說我怎么就攤上這事÷刈睿” “怎么了扔役?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長警医。 經常有香客問我亿胸,道長,這世上最難降的妖魔是什么预皇? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任侈玄,我火速辦了婚禮,結果婚禮上吟温,老公的妹妹穿的比我還像新娘序仙。我一直安慰自己,他們只是感情好鲁豪,可當我...
    茶點故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布潘悼。 她就那樣靜靜地躺著,像睡著了一般爬橡。 火紅的嫁衣襯著肌膚如雪治唤。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天糙申,我揣著相機與錄音宾添,去河邊找鬼。 笑死郭宝,一個胖子當著我的面吹牛辞槐,可吹牛的內容都是我干的。 我是一名探鬼主播粘室,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼榄檬,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了衔统?” 一聲冷哼從身側響起鹿榜,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤海雪,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后舱殿,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體奥裸,經...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年沪袭,在試婚紗的時候發(fā)現(xiàn)自己被綠了湾宙。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡冈绊,死狀恐怖侠鳄,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情死宣,我是刑警寧澤伟恶,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布,位于F島的核電站毅该,受9級特大地震影響博秫,放射性物質發(fā)生泄漏。R本人自食惡果不足惜眶掌,卻給世界環(huán)境...
    茶點故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一挡育、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧畏线,春花似錦静盅、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至蚣常,卻和暖如春市咽,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背抵蚊。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工施绎, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人贞绳。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓谷醉,卻偏偏與公主長得像,于是被迫代替她去往敵國和親冈闭。 傳聞我的和親對象是個殘疾皇子俱尼,可洞房花燭夜當晚...
    茶點故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內容