<template>
  <ModuleBase ref="base" :type="data.type">
    <template #content>
      <UploadFile
        key="upload_image"
        :type="data.type"
        :total-size="data.total_size"
        :file-list="data.image_list"
        :file-id-list="data.image_id_list"
        :file-info-list="data.image_info_list"
        :label-text="labelText"
        :accept-file-type="acceptFileType"
        :icon-class="iconClass"
        :limit="1"
        :single-size="500"
        @updateFileList="updateFileList"
      />
      <div class="image-size">
        <span>画板大小</span
        ><el-input-number v-model="data.image_width" :step="100" :min="200" :max="800" /><el-input-number
          v-model="data.image_height"
          :step="100"
          :min="200"
          :max="800"
        />
      </div>
      <div
        class="background-img"
        :style="{
          width: data.image_width + 'px',
          height: data.image_height + 'px',
          border: '1px dotted #DCDFE6',
          background: data.image_list[0] && file_url ? '' : '#DCDFE6',
        }"
      >
        <div
          v-if="data.image_list[0] && file_url"
          class="img-set"
          :style="{ top: `${data.imgData.top - 9}px`, left: `${data.imgData.left}px` }"
        >
          <div class="dot top-left" @mousedown="dragStart($event, 'nwse-resize', 'top-left')"></div>
          <div class="horizontal-line" @mousedown="dragStart($event, 'ns-resize', 'top')"></div>
          <div class="dot top-right" @mousedown="dragStart($event, 'nesw-resize', 'top-right')"></div>
          <div class="vertical-line" @mousedown="dragStart($event, 'ew-resize', 'left')"></div>
          <img
            :src="file_url"
            draggable="false"
            alt="背景图"
            :style="{ width: `${data.imgData.width}px`, height: `${data.imgData.height}px` }"
            @mousedown="dragStart($event, 'move', 'move')"
          />
          <div class="vertical-line" @mousedown="dragStart($event, 'ew-resize', 'right')"></div>
          <div class="dot bottom-left" @mousedown="dragStart($event, 'nesw-resize', 'bottom-left')"></div>
          <div class="horizontal-line" @mousedown="dragStart($event, 'ns-resize', 'bottom')"></div>
          <div class="dot bottom-right" @mousedown="dragStart($event, 'nwse-resize', 'bottom-right')"></div>
        </div>
        <p v-else :style="{ lineHeight: data.image_height + 'px', textAlign: 'center' }">背景图</p>
      </div>
    </template>
  </ModuleBase>
</template>

<script>
import ModuleMixin from '../../common/ModuleMixin';
import UploadFile from '../../base/common/UploadFile.vue';
import { getDrawingData } from '@/views/book/courseware/data/drawing';
import SelectUpload from '@/views/book/courseware/create/components/common/SelectUpload.vue';
import { GetFileURLMap } from '@/api/app';

export default {
  name: 'DrawingPage',
  components: { UploadFile, SelectUpload },
  mixins: [ModuleMixin],
  data() {
    return {
      data: getDrawingData(),
      labelText: '背景图',
      acceptFileType: '.jpg,.png,.jpeg',
      iconClass: 'picture',
      file_url: '',
    };
  },
  watch: {
    'data.image_list': {
      handler(val) {
        if (val.length > 0) {
          this.handleData();
        }
      },
      immediate: true,
    },
  },
  mounted() {
    document.querySelector('.background-img').addEventListener('mousemove', this.mouseMove);
    document.body.addEventListener('mouseup', this.mouseUp);
  },
  beforeDestroy() {
    document.querySelector('.background-img')?.removeEventListener('mousemove', this.mouseMove);
    document.body.removeEventListener('mouseup', this.mouseUp);
  },
  methods: {
    updateFileList({ file_list, file_id_list, file_info_list }) {
      this.data.image_list = file_list;
      this.data.image_id_list = file_id_list;
      this.data.image_info_list = file_info_list;
      this.data.file_id_list = file_id_list;
      if (file_list.length > 0) {
        const img = new Image();
        img.src = file_list[0].file_url;
        this.file_url = file_list[0].file_url;
        img.onload = () => {
          const { width, height } = img;

          if (width > this.data.image_width || height > this.data.image_height) {
            const wScale = width / this.data.image_width;
            const hScale = height / this.data.image_height;
            const scale = wScale > hScale ? this.data.image_width / 2 / width : this.data.image_height / 2 / height;

            this.data.imgData = {
              width: width * scale,
              height: height * scale,
              top: 0,
              left: 0,
            };
          } else {
            this.data.imgData = {
              width,
              height,
              top: 0,
              left: 0,
            };
          }
        };
      }
    },

    handleData() {
      // this.data.image_list.forEach((item) => {
      //   GetFileURLMap({ file_id_list: [item.file_id] }).then(({ url_map }) => {
      //     this.file_url = url_map[item.file_id];
      //     // this.$set(item, 'file_url', url_map[item.file_id]);
      //   });
      // });
      this.handleMindMap();
    },
    handleMindMap() {
      // 思维导图数据
      let node_list = [];
      this.data.image_list.forEach((item) => {
        node_list.push({
          name: item.file_name,
          id: Math.random().toString(36).substring(2, 12),
        });
      });
      this.data.mind_map.node_list = node_list;
    },
    /**
     * 拖拽开始
     * @param {MouseEvent} event
     * @param {string} cursor
     * @param {string} type
     */
    dragStart(event, cursor, type) {
      const { clientX, clientY } = event;
      this.data.drag = {
        dragging: true,
        startX: clientX,
        startY: clientY,
        type,
      };

      document.querySelector('.background-img').style.cursor = cursor;
    },
    /**
     * 鼠标移动
     * @param {MouseEvent} event
     */
    mouseMove(event) {
      if (!this.data.drag.dragging) return;
      const { clientX, clientY } = event;
      const { startX, startY, type } = this.data.drag;

      const widthDiff = clientX - startX;
      const heightDiff = clientY - startY;

      if (type === 'top-left') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(0, this.data.imgData.width - widthDiff));
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(0, this.data.imgData.height - heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top + heightDiff),
        );
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left + widthDiff),
        );
      } else if (type === 'top-right') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(this.data.imgData.width + widthDiff));
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(0, this.data.imgData.height - heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top + heightDiff),
        );
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left),
        );
      } else if (type === 'bottom-left') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(0, this.data.imgData.width - widthDiff));
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(this.data.imgData.height + heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top),
        );
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left + widthDiff),
        );
      } else if (type === 'bottom-right') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(this.data.imgData.width + widthDiff));
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(this.data.imgData.height + heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top),
        );
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left),
        );
      }

      if (type === 'top') {
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(0, this.data.imgData.height - heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top + heightDiff),
        );
      } else if (type === 'bottom') {
        this.data.imgData.height = Math.min(this.data.image_height, Math.max(this.data.imgData.height + heightDiff));
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top),
        );
      } else if (type === 'left') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(this.data.imgData.width - widthDiff));
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left + widthDiff),
        );
      } else if (type === 'right') {
        this.data.imgData.width = Math.min(this.data.image_width, Math.max(this.data.imgData.width + widthDiff));
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left),
        );
      }

      if (type === 'move') {
        this.data.imgData.top = Math.min(
          this.data.image_height - this.data.imgData.height,
          Math.max(0, this.data.imgData.top + heightDiff),
        );
        this.data.imgData.left = Math.min(
          this.data.image_width - this.data.imgData.width,
          Math.max(0, this.data.imgData.left + widthDiff),
        );
      }
      this.data.drag.startX = clientX;
      this.data.drag.startY = clientY;
    },
    /**
     * 鼠标抬起
     */
    mouseUp() {
      this.data.drag.dragging = false;
      document.querySelector('.background-img').style.cursor = 'auto';
    },
  },
};
</script>
<style lang="scss" scoped>
.upload-file {
  // display: flex;
  column-gap: 12px;
  align-items: center;
  margin: 8px 0;

  .file-name {
    display: flex;
    column-gap: 14px;
    align-items: center;
    justify-content: space-between;
    max-width: 360px;
    padding: 8px 12px;
    font-size: 14px;
    color: #1d2129;
    background-color: #f7f8fa;

    span {
      display: flex;
      column-gap: 14px;
      align-items: center;
    }
  }

  .svg-icon {
    cursor: pointer;
  }
}

.image-size {
  display: flex;
  gap: 10px;
  align-items: center;
  padding: 20px 0;
}

.background-img {
  height: 310px;
  border: 1px dashed rgba(0, 0, 0, 8%);

  .img-set {
    position: relative;
    display: inline-grid;
    grid-template:
      ' . . . ' 2px
      ' . img . ' auto
      ' . . . ' 2px
      / 2px auto 2px;

    img {
      object-fit: cover;
    }

    .horizontal-line,
    .vertical-line {
      background-color: $main-color;
    }

    .horizontal-line {
      width: 100%;
      height: 2px;
      cursor: ns-resize;
    }

    .vertical-line {
      width: 2px;
      height: 100%;
      cursor: ew-resize;
    }

    .dot {
      z-index: 1;
      width: 6px;
      height: 6px;
      background-color: $main-color;

      &.top-left {
        top: -2px;
        left: -2px;
      }

      &.top-right {
        top: -2px;
        right: 2px;
      }

      &.bottom-left {
        bottom: 2px;
        left: -2px;
      }

      &.bottom-right {
        right: 2px;
        bottom: 2px;
      }

      &.top-left,
      &.bottom-right {
        position: relative;
        cursor: nwse-resize;
      }

      &.top-right,
      &.bottom-left {
        position: relative;
        cursor: nesw-resize;
      }
    }
  }
}
</style>
