基于vue实现文件选择,操作目录返回上一级,进入下一级

48 阅读1分钟

基于vue实现文件选择,操作目录返回上一级,进入下一级

在这里插入图片描述

数据结构 在这里插入图片描述

<template>
  <div>
    <!-- 选择路径组件 -->
    <el-input
      v-model="formData.path"
      placeholder="请输入路径"
      style="width: 400px"
      clearable
    >
      <el-button
        @click="openFileSelect"
        slot="append"
        icon="el-icon-search"
      ></el-button>
    </el-input>

    <el-dialog
      title="select path"
      :visible.sync="dialogVisible"
      width="60%"
      :before-close="handleClose"
    >
      <el-card class="box-card">
        <template #header>
          <div class="card-header">
            <el-breadcrumb separator="\">
              <el-breadcrumb-item v-for="(item, index) in dir" :key="index"
                ><a @click="previousDir(item, index)">{{
                  item
                }}</a></el-breadcrumb-item
              >
            </el-breadcrumb>
          </div>
        </template>
        <div
          v-for="(item, index) in dirList"
          :key="index"
          class="text item"
          @click="nextDir(item)"
        >
          <a class="path-name">{{ item.File_Name }}</a>
        </div>
      </el-card>

      <span slot="footer" class="dialog-footer">
        <el-button @click="dialogVisible = false">取 消</el-button>
        <el-button type="primary" @click="submitPathEvent">确 定</el-button>
      </span>
    </el-dialog>
  </div>
</template>

<script>
import { mapActions, mapState } from "vuex";
export default {
  name: "PathChoose",

  data() {
    return {
      dir: ["/"],
      dirList: [],
      formData: {
        path: "",
      },
      dialogVisible: false,
    };
  },
  computed: {
    ...mapState({
      filePathDocumentData: (state) =>
        state.productForm.filePathDocumentData || {},
    }),
  },
  mounted() {},

  methods: {
    ...mapActions({
      getFilePathDocumentDataAction:
        "productForm/getFilePathDocumentDataAction",
    }),
    openFileSelect() {
      this.dialogVisible = true;
      this.getNewPath();
    },
    submitPathEvent() {
      if (!this.formData.path) {
        return this.$commonMessage.message({
          message: "Please select a path",
          type: "warning",
        });
      }
      this.dialogVisible = false;
    },
    handleClose() {
      this.dialogVisible = false;
    },
    //获取路径数组
    async getNewPath(current, next, Prev) {
      try {
        const { data } = await this.getFilePathDocumentDataAction({
          subordinate_path: next || "",
          current_path: current || "/",
          superior_path: Prev || "",
        });
        this.dirList = data.list;
      } catch (error) {
        console.log("error :>> ", error);
        this.dirList = [];
      }
    },
    //处理数组
    slicePath() {
      let dirRes = "";
      this.dir.forEach((item) => {
        dirRes = dirRes + "/" + item.File_Name;
      });
      return dirRes.slice(1);
    },
    //上一级
    async previousDir(item, index) {
      console.log(item);
      // 如果是最后一个元素则返回,减少网络请求
      if (index + 1 === this.dir.length) {
        return;
      }
      // 删除选中元素后面的所有元素
      this.dir.splice(index + 1, this.dir.length - 1);
      await this.getNewPath("", "", item);
    },
    //下一级
    async nextDir(item) {
      if (item.Subordinate_Path != null) {
        this.dir.push(item.Subordinate_Path);
        await this.getNewPath(
          item.Current_Path,
          item.Subordinate_Path,
          item.Superior_Path
        );
      }
      if (item.File_Type === "文件") {
        const formattedString = this.$_.join(this.dir, "/");
        const resultPath = formattedString + item.File_Name;
        let res = resultPath.replace("/", "");
        console.log(resultPath);
        this.formData.path = res;
        this.dialogVisible = false;
      }
    },
  },
};
</script>
<style lang="scss" scoped>
.card-header {
  width: 100%;
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.text {
  font-size: 14px;
}

.item {
  margin-bottom: 18px;
}
.path-name {
  &:hover {
    color: #409eff;
  }
}

::v-deep .el-dialog__body {
  height: 68vh;
  overflow: auto;
}
</style>