index.vue
2.74 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
<template>
<a-trigger trigger="click" :popup-translate="[155, 10]">
<slot>
<a-button>Click Me</a-button>
</slot>
<template #content>
<div class="icon-box">
<div class="icon-header">
<a-input v-model="searchVal" placeholder="选择图标" allow-clear/>
</div>
<div class="icon-list">
<div class="icon-list-item" :class="{'active-icon': activeIconName === name}" v-for="(name,index) in myIcons"
:key="index" @click="handleSelect(name)">
<component v-if="!name.includes('icon-ykite')" :is="name" style="font-size: 24px"></component>
<component v-else is="custom-icon" style="font-size: 24px" :type="name"></component>
</div>
</div>
</div>
</template>
</a-trigger>
</template>
<script setup lang="ts">
import ArcoVueIcon from '@arco-design/web-vue/es/icon';
import iconList from "@/components/select-icon/index";
import {computed, onMounted, ref} from "vue";
const props = defineProps({
name: {
type: String,
default: ''
}
})
const emit = defineEmits(['change'])
// 选中的icon
const activeIconName = ref<string>('')
// 搜索
const searchVal = ref('')
// 获取格式化后的 icon
const formatIcons: any[] = []
// 大驼峰格式为 -
const formatName = (str: string): string => {
return str.replace(/([A-Z])/g, function (match) {
return '-' + match.toLowerCase();
}).slice(1);
}
for (const key in ArcoVueIcon) {
if (key !== 'install') {
formatIcons.push(formatName(ArcoVueIcon[key].name))
}
}
const myIcons = computed(() => {
if (!searchVal.value) return formatIcons.concat(iconList);
const filteredFormatIcons = formatIcons.filter(item => item.indexOf(searchVal.value) !== -1);
const filteredIconFont = iconList.filter(item => item.indexOf(searchVal.value) !== -1);
return [...filteredFormatIcons, ...filteredIconFont];
});
// 传递父组件 icon 名字
const handleSelect = (iconName: string) => {
activeIconName.value = iconName
emit('change', iconName)
}
onMounted(() => {
activeIconName.value = <string>props.name
})
</script>
<style lang="less" scoped>
.icon-box {
border: 1px solid var(--color-border-1);
background-color: var(--color-bg-popup);
.icon-header {
padding: 10px 10px;
}
}
.icon-list {
width: 400px;
height: 400px;
overflow-y: auto;
padding: 0 10px;
.icon-list-item {
display: inline-block;
padding: 5px;
svg {
color: var(--color-text-2);
}
}
.icon-list-item:hover {
svg {
color: white;
}
background: rgb(var(--primary-6));
}
.active-icon {
svg {
color: white;
}
background-color: rgb(var(--primary-6));
}
}
// 隐藏 图标滚动条
.icon-list::-webkit-scrollbar {
display: none;
}
</style>