前書き: このコンポーネントは現在、大きなビジュアライゼーション画面で数値を表示するために使用されており、複雑なコンテンツのシーン表示には当面使用できません。
実現目標: ElementPlusライブラリのツールチップコンポーネントをベースとした二次カプセル化により、コンポーネント内へのコンテンツの書き込みを実現 コンテンツがコンポーネントの親ボックスの幅を超える場合、コンポーネントコンテンツの超過部分を非表示にし、省略記号を表示ツールチップを通じてコンテンツ全体をプロンプト表示します。
結果を示す:
手順:
<!-- template部分 -->
<template>
<div class="box">
<Tip>
<b class="gray">{
{ 123456 }}</b>
</Tip>
</div>
</template>
// script部分
<script setup lang="ts">
import Tip from "@/components/..书写自己的文件夹路径../Tip.vue"
</script>
// css部分
<style scoped lang="scss">
.box {
width: 100px;
background-color: red;
}
</style>
コードのバグ: Tip コンポーネントに書かれた内容は、コメントも含めてすべてバブルに表示されます。したがって、コンポーネント内にコメントを書かないでください。!
コンポーネントコード:
<!-- 技术栈: Vue3 + ElementPlus -->
<!-- 利用el-tooltip实现文字超出时显示省略号并气泡提示,否则不气泡提示 -->
<!-- 使用: Tip组件"内"必须包裹仅且一个html标签,外层div标签需要具有宽度
<div>
<Tip><templat>...</templat></Tip>
</div>
-->
<template>
<div v-if="flag">
<el-tooltip placement="top">
<template #content>{
{ content.join("") }}</template>
<div
class="ellipsis"
ref="slotRef">
<slot></slot>
</div>
</el-tooltip>
</div>
<div
v-else
class="ellipsis"
ref="slotRef">
<slot></slot>
</div>
</template>
<script setup lang="ts">
import { useSlots, ref, onMounted, onUpdated } from "vue";
const slots = useSlots() as any;
let slotDom = slots.default();
const slotRef = ref();
const flag = ref(false);
const content = ref([]);
const isArray = (arr: any) => {
return Object.prototype.toString.call(arr) === "[object Array]";
};
const childrenIsArray = (arr: any, content: Array<string>) => {
arr.forEach((v: any) => {
if (isArray(v.children)) {
childrenIsArray(v.children, content);
} else {
content.push(v.children);
}
});
};
const slotDomIsSingleElArray = (slotDom: any) => {
if (isArray(slotDom.children)) {
childrenIsArray(slotDom.children, content.value);
} else {
content.value = slotDom.children;
}
};
const getContent = () => {
if (slotDom.length > 1) {
slotDom.forEach((v: any, i: number) => {
slotDomIsSingleElArray(v);
});
} else {
slotDomIsSingleElArray(slotDom[0]);
}
};
const compareWidth = () => {
content.value = [];
const parentW = slotRef.value.offsetWidth;
const childW = slotRef.value.firstElementChild.offsetWidth;
childW > parentW ? (flag.value = true) : (flag.value = false);
if (flag.value) {
getContent();
}
};
onMounted(() => {
compareWidth();
});
onUpdated(() => {
slotDom = slots.default();
compareWidth();
});
</script>
<style lang="scss" scoped>
.ellipsis {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
</style>
以前のツールチップスタイル変更の CSS コードを添付します。
// tooltips 自定义样式
.el-popper.is-customized {
max-width: 400px !important;
padding: 6px 12px !important;
background: linear-gradient(180deg, #4574AB, #4574AB) !important;
}
.el-popper.is-customized .el-popper__arrow::before {
background: linear-gradient(45deg, #4574AB, #4574AB) !important;
right: 0;
}
// tooltips 默认样式
.el-popper.is-dark {
max-width: 400px !important;
padding: 6px 12px !important;
color: #fff;
border: 0px;
background: linear-gradient(180deg, #4574AB, #4574AB) !important;
}
.el-popper.is-dark .el-popper__arrow::before {
border: 0px;
background: linear-gradient(45deg, #4574AB, #4574AB) !important;
right: 0;
}