TextLeftRightBlock.vue 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. <script lang="ts">
  2. /**
  3. * 组件说明: 文本块。
  4. *
  5. * 可设置左右文字,左侧文字支持双行。
  6. *
  7. * 此组件适用于需要展示多行文本信息并具备一定交互性和布局灵活性的场景,如列表项、信息展示框等。
  8. */
  9. export default {}
  10. </script>
  11. <script setup lang="ts">
  12. import Text, { type TextProps } from '../../basic/Text.vue';
  13. import type { PropType } from 'vue';
  14. import Touchable from '@/components/feedback/Touchable.vue';
  15. defineEmits([ 'click' ])
  16. defineProps({
  17. /**
  18. * 主文本内容
  19. * @type {string}
  20. * @default ''
  21. */
  22. text : {
  23. type: String,
  24. default: '',
  25. },
  26. /**
  27. * 主文本的样式类名
  28. * @type {string}
  29. * @default 'contentLight'
  30. */
  31. textProps : {
  32. type: Object as PropType<TextProps>,
  33. default: () => ({
  34. color: 'text.content',
  35. }),
  36. },
  37. /**
  38. * 副文本内容
  39. * @type {string}
  40. * @default ''
  41. */
  42. text2 : {
  43. type: String,
  44. default: '',
  45. },
  46. text2Empty : {
  47. type: String,
  48. default: '暂无',
  49. },
  50. /**
  51. * 副文本的样式类名
  52. * @type {string}
  53. * @default 'contentSecond'
  54. */
  55. text2Props : {
  56. type: Object as PropType<TextProps>,
  57. default: () => ({
  58. color: 'text.second',
  59. }),
  60. },
  61. /**
  62. * 副文本的最大行数
  63. */
  64. text2Lines : {
  65. type: Number,
  66. default: undefined,
  67. },
  68. /**
  69. * 传递给根容器的额外属性对象
  70. * @type {Object}
  71. * @default undefined
  72. */
  73. viewProps: {
  74. type: Object,
  75. default: undefined
  76. },
  77. /**
  78. * 标识文本块是否可点击
  79. * @type {boolean}
  80. * @default false
  81. */
  82. touchable: {
  83. type: Boolean,
  84. default: false,
  85. },
  86. /**
  87. * 标识文本是否换行显示
  88. * @type {boolean}
  89. * @default false
  90. */
  91. wrap: {
  92. type: Boolean,
  93. default: false,
  94. },
  95. })
  96. </script>
  97. <template>
  98. <Touchable
  99. :touchable="touchable"
  100. :setCursor="false"
  101. justify="space-between"
  102. align="flex-start"
  103. width="fill"
  104. direction="row"
  105. v-bind="viewProps"
  106. @click="$emit('click')"
  107. >
  108. <Text
  109. :class="[
  110. 'nana-text first',
  111. wrap ? 'wrap' : '',
  112. ]"
  113. v-bind="textProps"
  114. :text="text"
  115. />
  116. <slot>
  117. <Text
  118. :class="[
  119. 'nana-text second',
  120. wrap ? 'wrap' : '',
  121. ]"
  122. v-bind="text2Props"
  123. :lines="text2Lines"
  124. :text="text2 || text2Empty"
  125. />
  126. </slot>
  127. </Touchable>
  128. </template>
  129. <style lang="scss">
  130. .nana-text {
  131. white-space: nowrap;
  132. overflow: hidden;
  133. text-overflow: ellipsis;
  134. flex: 1 1 100%;
  135. max-width: 100%;
  136. &.wrap {
  137. white-space: normal;
  138. }
  139. &.first {
  140. flex-shrink: 1;
  141. flex-grow: 0;
  142. flex-basis: 30%;
  143. }
  144. }
  145. .nana-text-prefix {
  146. flex-shrink: 0;
  147. overflow: hidden;
  148. text-overflow: ellipsis;
  149. margin-right: 20rpx;
  150. }
  151. .nana-text-suffix {
  152. flex-shrink: 0;
  153. overflow: hidden;
  154. text-overflow: ellipsis;
  155. }
  156. </style>