bottom-app-bar.vue 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. <script setup lang="ts">
  2. import { getRect, addUnit } from 'wot-design-uni/components/common/util'
  3. const props = defineProps<{
  4. 'safe-area-inset-bottom'?: boolean
  5. fixed?: boolean
  6. placeholder?: boolean
  7. border?: boolean
  8. transparent?: boolean
  9. }>()
  10. const { proxy } = getCurrentInstance() as any
  11. const aRef = ref<HTMLElement>()
  12. const height = ref(0)
  13. const safeAreaInsets = ref()
  14. const setPlaceholderHeight = () => {
  15. if (!props.fixed || !props.placeholder) {
  16. return
  17. }
  18. getRect('.bottom-app-bar', false, proxy).then((res) => {
  19. height.value = res.height as number
  20. })
  21. }
  22. onMounted(async () => {
  23. uni.getSystemInfo({})
  24. const res = await uni.getWindowInfo()
  25. safeAreaInsets.value = res.safeAreaInsets
  26. if (props.fixed && props.placeholder) {
  27. nextTick(() => {
  28. setPlaceholderHeight()
  29. })
  30. }
  31. })
  32. </script>
  33. <template>
  34. <div :style="{ height: addUnit(height) }">
  35. <div
  36. class="bottom-app-bar"
  37. ref="aRef"
  38. :class="[
  39. (fixed ?? true)
  40. ? 'fixed bottom-0 left-0 right-0 after:content-empty after:w-full after:h-full after:relative'
  41. : '',
  42. border ? 'border-t border-t-solid border-[#ececec]' : '',
  43. ]"
  44. >
  45. <div class="px-3.5 py-2.5" :class="[transparent ? '' : 'bg-white']">
  46. <div class=""><slot></slot></div>
  47. </div>
  48. <div
  49. class=""
  50. :class="[transparent ? '' : 'bg-white']"
  51. :style="{ height: `${safeAreaInsets?.bottom}rpx` }"
  52. ></div>
  53. </div>
  54. </div>
  55. </template>