自制空组件

目录

需求

为开发一个空状态通用组件,需要将所有内容水平垂直居中,还需要横向纵向排列,故选择flex布局。

  1. 组件内容分为三部分,图片、文字、其他(插槽)
  2. 默认状态,组件排列方式为纵向,图片307*145,所有内容水平垂直居中。
  3. 容器宽高任一小于330px,假设宽大于高组件排列方式变为横向,图片大小变为70px;否则维持默认。
  4. 容器宽高任一小于120px,组件只显示文字和其他。

一. empty.vue

<template>
  <div class="zoehis_empty_warp">
    <div class="zoehis_empty_inwarp">
      <div
        class="zoehis_empty"
        :class="[
          uiType == 'horizontal' || isChangeSize === 'horizontal'
            ? 'zoehis_empty_horizontal'
            : uiType === 'text' || isChangeSize === 'text'
            ? 'zoehis_empty_text'
            : uiType === 'vertical' || isChangeSize === 'vertical'
            ? 'zoehis_empty_vertical'
            : '',
        ]"
      >
        <!-- 图片 -->
        <div class="zoehis_empty_clear zoehis_empty_noimage">
          <slot name="image">
            <div class="zoehis_empty_image">
              <component v-bind:is="image" :style="{ height: newImageHeight }"></component>
            </div>
          </slot>
        </div>
        <!-- 插槽 -->
        <div class="zoehis_empty_clear">
          <slot name="description">
            <p class="zoehis_empty_description">{{ description }}</p>
          </slot>
        </div>
        <!-- 追加内容 通常是一些操作按钮 -->
        <div class="zoehis_empty_clear">
          <slot></slot>
        </div>
      </div>
    </div>
  </div>
</template>
<script>
// 导入内置图片 img
import defaultEmpty from "../svg/defaultEmpty.vue";
import appendEmpty from "../svg/appendEmpty.vue";
import dataEmpty from "../svg/dataEmpty.vue";
import distributeEmpty from "../svg/distributeEmpty.vue";
import documentEmpty from "../svg/documentEmpty.vue";
import messageEmpty from "../svg/messageEmpty.vue";
const re = /^[0-9]+\.?[0-9]*$/;
export default {
  name: "ZoehisEmpty",
  componentName: "ZoehisEmpty",
  props: {
    image: { // 内置图片类型
      default: () => {
        return defaultEmpty;
      },
    },
    imageHeight: { // 内置图片高度
      type: String,
      default: "",
    },
    description: { // 描述文字
      type: String,
      default: "暂无数据",
    },
    uiType: { // 类型
      type: String,
      default: "",
    },
  },
  components: {
    defaultEmpty,
    appendEmpty,
    dataEmpty,
    distributeEmpty,
    documentEmpty,
    messageEmpty,
  },
  computed: {
    // 图片高度转换
    newImageHeight() {
      if (re.test(this.imageHeight)) {
        return `${this.imageHeight}px`;
      }
      return this.imageHeight;
    },
  },
  data() {
    return {
      isChangeSize: "", // 判断自适应
    };
  },
  mounted() {
    this.resize();
  },
  methods: {
    // 初始化尺寸
    resize() {
      let height = this.$el.offsetHeight || 330;
      let width = this.$el.offsetWidth || 330;
      let num = Math.min(width, height);
      if (!this.uiType) {
        if (num < 330 && num >= 120) {
          if (width > height) {
            this.isChangeSize = "horizontal";
          } else {
            this.isChangeSize = "vertical";
          }
        } else if (num < 120) {
          this.isChangeSize = "text";
        } else {
          this.isChangeSize = "vertical";
        }
      } else {
        this.isChangeSize = "vertical";
      }
    },
  },
};
</script>

二. index.js

import ZoehisEmpty from './src/empty.vue';
import defaultEmpty from './svg/defaultEmpty.vue'; // 默认空状态
import dataEmpty from './svg/dataEmpty.vue'; // 暂无数据
import appendEmpty from './svg/appendEmpty.vue'; // 暂未添加
import documentEmpty from './svg/documentEmpty.vue'; // 暂无相关文档
import messageEmpty from './svg/messageEmpty.vue'; // 暂无相关消息
import distributeEmpty from './svg/distributeEmpty.vue'; // 暂未分发

ZoehisEmpty.install = function(Vue) {
  Vue.component(ZoehisEmpty.name, ZoehisEmpty);
};

ZoehisEmpty.DEFAUL_EMPTY = defaultEmpty
ZoehisEmpty.DATA_EMPTY = dataEmpty
ZoehisEmpty.APPEND_EMPTY = appendEmpty
ZoehisEmpty.DOCUMENT_EMPTY = documentEmpty
ZoehisEmpty.MESSAGE_EMPTY = messageEmpty
ZoehisEmpty.DISTRIBUTE_EMPTY = distributeEmpty

export default ZoehisEmpty

三. empty.scss

.zoehis_empty_warp {
  width: 100%;
  height: 100%;
  overflow: auto;
  .zoehis_empty_inwarp {
    width: 100%;
    height: 100%;
    display: flex;
    align-items: center;
  }
  .zoehis_empty_clear{
    flex-shrink: 0;
  }
}
.zoehis_empty {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  margin: auto;
  flex-shrink: 0;
  .zoehis_empty_description {
    font-size: 16px;
    font-weight: bold;
    margin-top: -24px;
  }
  // 纵向
  &.zoehis_empty_vertical {
    flex-direction: column;
    .zoehis_empty_description{
      margin: 0;
      margin-top: -24px;
      font-weight: bold;
    }
  }
  // 横向
  &.zoehis_empty_horizontal {
    flex-direction: row;
    .zoehis_empty_image{
      img{
        height: 70px;
      }
    }
    .zoehis_empty_description{
      margin: 0;
      font-weight: normal;
      margin-left: -24px;
    }
  }
  // 没图
  &.zoehis_empty_text {
    flex-shrink: 1;
    .zoehis_empty_noimage {
      display: none;
    }
    .zoehis_empty_description {
      margin: 0;
      font-weight: normal;
    }
  }
}

四.flex大坑

https://www.cnblogs.com/DarkCrow/p/15826829.html

上一篇:GJB150军用设备环境(霉菌、淋雨、湿热、盐雾、冲击)试验


下一篇: