noticeItem.vue 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169
  1. <script setup lang="ts">
  2. import { ListItem } from "./data";
  3. import { ref, PropType, nextTick } from "vue";
  4. const props = defineProps({
  5. noticeItem: {
  6. type: Object as PropType<ListItem>,
  7. default: () => {}
  8. }
  9. });
  10. const titleRef = ref(null);
  11. const descriptionRef = ref(null);
  12. const titleTooltip = ref(false);
  13. const descriptionTooltip = ref(false);
  14. function hoverTitle() {
  15. titleTooltip.value = false;
  16. nextTick(() => {
  17. titleRef.value?.scrollWidth > titleRef.value?.clientWidth
  18. ? (titleTooltip.value = true)
  19. : (titleTooltip.value = false);
  20. });
  21. }
  22. function hoverDescription(event, description) {
  23. // currentWidth 为文本在页面中所占的宽度,创建标签,加入到页面,获取currentWidth ,最后在移除
  24. let tempTag = document.createElement("span");
  25. tempTag.innerText = description;
  26. tempTag.className = "getDescriptionWidth";
  27. document.querySelector("body").appendChild(tempTag);
  28. let currentWidth = (
  29. document.querySelector(".getDescriptionWidth") as HTMLSpanElement
  30. ).offsetWidth;
  31. document.querySelector(".getDescriptionWidth").remove();
  32. // cellWidth为容器的宽度
  33. const cellWidth = event.target.offsetWidth;
  34. // 当文本宽度大于容器宽度两倍时,代表文本显示超过两行
  35. currentWidth > 2 * cellWidth
  36. ? (descriptionTooltip.value = true)
  37. : (descriptionTooltip.value = false);
  38. }
  39. </script>
  40. <template>
  41. <div class="notice-container">
  42. <el-avatar
  43. v-if="props.noticeItem.avatar"
  44. :size="30"
  45. :src="props.noticeItem.avatar"
  46. class="notice-container-avatar"
  47. ></el-avatar>
  48. <div class="notice-container-text">
  49. <div class="notice-text-title">
  50. <el-tooltip
  51. popper-class="notice-title-popper"
  52. :disabled="!titleTooltip"
  53. :content="props.noticeItem.title"
  54. placement="top-start"
  55. >
  56. <div
  57. ref="titleRef"
  58. class="notice-title-content"
  59. @mouseover="hoverTitle"
  60. >
  61. {{ props.noticeItem.title }}
  62. </div>
  63. </el-tooltip>
  64. <el-tag
  65. v-if="props.noticeItem?.extra"
  66. :type="props.noticeItem?.status"
  67. size="small"
  68. class="notice-title-extra"
  69. >{{ props.noticeItem?.extra }}
  70. </el-tag>
  71. </div>
  72. <el-tooltip
  73. popper-class="notice-title-popper"
  74. :disabled="!descriptionTooltip"
  75. :content="props.noticeItem.description"
  76. placement="top-start"
  77. >
  78. <div
  79. ref="descriptionRef"
  80. class="notice-text-description"
  81. @mouseover="hoverDescription($event, props.noticeItem.description)"
  82. >
  83. {{ props.noticeItem.description }}
  84. </div>
  85. </el-tooltip>
  86. <div class="notice-text-datetime">
  87. {{ props.noticeItem.datetime }}
  88. </div>
  89. </div>
  90. </div>
  91. </template>
  92. <style>
  93. .notice-title-popper {
  94. max-width: 238px;
  95. }
  96. </style>
  97. <style scoped lang="scss">
  98. .notice-container {
  99. display: flex;
  100. align-items: flex-start;
  101. justify-content: space-between;
  102. padding: 12px 0;
  103. border-bottom: 1px solid #f0f0f0;
  104. .notice-container-avatar {
  105. margin-right: 16px;
  106. background: #fff;
  107. }
  108. .notice-container-text {
  109. display: flex;
  110. flex-direction: column;
  111. justify-content: space-between;
  112. flex: 1;
  113. .notice-text-title {
  114. display: flex;
  115. margin-bottom: 8px;
  116. font-weight: 400;
  117. font-size: 14px;
  118. line-height: 1.5715;
  119. color: rgba(0, 0, 0, 0.85);
  120. cursor: pointer;
  121. .notice-title-content {
  122. flex: 1;
  123. width: 200px;
  124. overflow: hidden;
  125. white-space: nowrap;
  126. text-overflow: ellipsis;
  127. }
  128. .notice-title-extra {
  129. float: right;
  130. margin-top: -1.5px;
  131. font-weight: 400;
  132. }
  133. }
  134. .notice-text-description,
  135. .notice-text-datetime {
  136. font-size: 12px;
  137. line-height: 1.5715;
  138. color: rgba(0, 0, 0, 0.45);
  139. }
  140. .notice-text-description {
  141. display: -webkit-box;
  142. text-overflow: ellipsis;
  143. overflow: hidden;
  144. -webkit-line-clamp: 2;
  145. -webkit-box-orient: vertical;
  146. }
  147. .notice-text-datetime {
  148. margin-top: 4px;
  149. }
  150. }
  151. }
  152. </style>