wd-tabbar.vue 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. <template>
  2. <view :class="{ 'wd-tabbar__placeholder': fixed && placeholder && safeAreaInsetBottom && shape === 'round' }" :style="{ height: addUnit(height) }">
  3. <view
  4. :class="`wd-tabbar wd-tabbar--${shape} ${customClass} ${fixed ? 'is-fixed' : ''} ${safeAreaInsetBottom ? 'is-safe' : ''} ${
  5. bordered ? 'is-border' : ''
  6. }`"
  7. :style="rootStyle"
  8. >
  9. <slot></slot>
  10. </view>
  11. </view>
  12. </template>
  13. <script lang="ts">
  14. export default {
  15. name: 'wd-tabbar',
  16. options: {
  17. addGlobalClass: true,
  18. virtualHost: true,
  19. styleIsolation: 'shared'
  20. }
  21. }
  22. </script>
  23. <script lang="ts" setup>
  24. import { getCurrentInstance, onMounted, ref, watch, nextTick, computed, type CSSProperties } from 'vue'
  25. import type { TabbarItem } from '../wd-tabbar-item/types'
  26. import { addUnit, getRect, isDef, objToStyle } from '../common/util'
  27. import { useChildren } from '../composables/useChildren'
  28. import { TABBAR_KEY, tabbarProps } from './types'
  29. const props = defineProps(tabbarProps)
  30. const emit = defineEmits(['change', 'update:modelValue'])
  31. const height = ref<number | string>('') // 占位高度
  32. const { proxy } = getCurrentInstance() as any
  33. const { linkChildren } = useChildren(TABBAR_KEY)
  34. linkChildren({
  35. props,
  36. setChange
  37. })
  38. const rootStyle = computed(() => {
  39. const style: CSSProperties = {}
  40. if (isDef(props.zIndex)) {
  41. style['z-index'] = props.zIndex
  42. }
  43. return `${objToStyle(style)}${props.customStyle}`
  44. })
  45. watch(
  46. [() => props.fixed, () => props.placeholder],
  47. () => {
  48. setPlaceholderHeight()
  49. },
  50. { deep: true, immediate: false }
  51. )
  52. onMounted(() => {
  53. if (props.fixed && props.placeholder) {
  54. nextTick(() => {
  55. setPlaceholderHeight()
  56. })
  57. }
  58. })
  59. /**
  60. * 子项状态变更
  61. * @param child 子项
  62. */
  63. function setChange(child: TabbarItem) {
  64. let active = child.name
  65. emit('update:modelValue', active)
  66. emit('change', {
  67. value: active
  68. })
  69. }
  70. function setPlaceholderHeight() {
  71. if (!props.fixed || !props.placeholder) {
  72. return
  73. }
  74. getRect('.wd-tabbar', false, proxy).then((res) => {
  75. height.value = Number(res.height)
  76. })
  77. }
  78. </script>
  79. <style lang="scss" scoped>
  80. @import './index.scss';
  81. </style>