<template>
  <div>
    <el-row :gutter="20">
      <el-col :span="6">
        <div class="type-title">载具出库</div>
        <ScanCodeInput
          v-model="boxSearch"
          :clearable="true"
          :showSuffix="true"
          placeholder="请扫描或输入料箱编号"
          @keyup.enter="enterBox"
        />
        <el-scrollbar class="boxes-container base-container">
          <div
            v-for="(item, index) in boxesList"
            :key="index"
            :class="{ 'box-selected': index === currentBoxIndex }"
            class="box-item"
            @click="clickBox(item, index)"
          >
            <div class="box-name">{{ item.vehicleName }}</div>
            <div
              v-for="(material, index) in item.list"
              :key="index"
              class="box-info"
            >
              <div>{{ material.materialName }}</div>
              <div>{{ material.num }}</div>
            </div>
          </div>
        </el-scrollbar>
        <el-button class="sureBtn" type="primary" @click="sureToOut"
          >出库
        </el-button>
      </el-col>
      <el-col :span="6">
        <div class="type-title">捡料位</div>
        <el-scrollbar class="outing-container">
          <div class="boxHeader">载具名称:{{ outingBox?.vehicleName }}</div>
          <div class="boxHeader">载具编码:{{ outingBox?.vehicleCode }}</div>
          <div
            v-for="(material, index) in outingMaterials"
            :key="index"
            class="outing-box"
          >
            <div class="material-title">
              {{ material.materialName }} | {{ material.materialNo }}
            </div>
            <!--            <div class="material-info">-->
            <!--              <div>批次号</div>-->
            <!--              <el-tooltip :content="material.batchCode" placement="top">-->
            <!--                <div class="batchCode">{{ material.batchCode }}</div>-->
            <!--              </el-tooltip>-->
            <!--            </div>-->
            <!--            <div class="material-info">-->
            <!--              <div>位置</div>-->
            <!--              <div>{{ material.locationNo }}</div>-->
            <!--            </div>-->
            <div class="material-info">
              <div>数量</div>
              <div>{{ material.num }}</div>
            </div>
          </div>
        </el-scrollbar>
        <el-button class="sureBtn" type="info" @click="backToStorage"
          >入库
        </el-button>
      </el-col>
      <el-col :span="6">
        <ScanCodeInput
          v-model="boxInputValue"
          :clearable="true"
          placeholder="请扫描或输入载具编号"
          @keyup.enter="enterBoxInput"
        />
        <div class="boxHeader">载具名称:{{ toSendBoxInfo?.vehicleName }}</div>
        <div class="boxHeader">载具编码:{{ toSendBoxInfo?.vehicleCode }}</div>
        <div class="type-title">请扫码物料</div>
        <ScanCodeInput
          v-model="scanCodeInput"
          placeholder="请扫描或输入物料编码"
          @keyup.enter="handleScanCodeInput"
        />
        <el-scrollbar style="height: calc(100vh - 535px); margin-top: 10px">
          <div class="list-container">
            <div
              v-for="(item, index) in materialList"
              :key="index"
              class="list-box"
            >
              <div>
                <div class="name">{{ item.materialName }}</div>
                <div class="spec">{{ item.spec }}</div>
              </div>
              <div class="bottom">
                <NumberInput v-model="item.num" />
                <span class="unit">{{ item.unitDictLabel }}</span>
              </div>
              <i-ep-delete
                class="delete-btn"
                color="#ff4d4f"
                size="20px"
                @click="deleteMaterial(index)"
              />
            </div>
          </div>
        </el-scrollbar>
        <el-button class="sureBtn" type="primary" @click="sureToAdd"
          >确认添加
        </el-button>
      </el-col>
      <el-col :span="6">
        <div class="type-title">流转终点</div>
        <div class="destination">
          <el-scrollbar>
            <div
              v-for="(item, index) in destinationList"
              :key="index"
              :class="{ selected: index === currentDestinationIndex }"
              class="end-box"
              @click="onEndBoxClick(index, item)"
            >
              <div class="name">{{ item.name }}</div>
            </div>
          </el-scrollbar>
        </div>
        <el-button class="sureBtn" type="primary" @click="createTask"
          >派发
        </el-button>
      </el-col>
    </el-row>
  </div>
</template>

<script lang="ts" setup>
//料箱
import {
  addMaterialFlow,
  getBoxDetailByLabel,
  getDestinationList,
  getMaterialInfoByLabel,
} from "@/api/process/materialFlow";
import {
  backToStorageAPI,
  getStorageBoxesList,
  getStorageOrderInfo,
  toOutBox,
} from "@/api/storage/out";
import { useCommonStoreHook } from "@/store";

const commonS = useCommonStoreHook();

const boxSearch = ref("");
const boxesList = ref<any[]>([]);
const currentBox = ref<any>({});
const currentBoxIndex = ref(-1);
const enterBox = () => {
  boxSearch.value = boxSearch.value.trim();
  getStorageBoxesList({}).then((res: any) => {
    boxesList.value = res.data;
  });
};

const clickBox = (box: any, index: number) => {
  currentBox.value = box;
  currentBoxIndex.value = index;
};
const sureToOut = async () => {
  let res: any = await toOutBox({
    vehicleNo: currentBox.value.vehicleNo,
    houseNo: currentBox.value.houseNo,
  });
  commonS.orderId = res.data.orderId;
  commonS.changeBoxType = 2; // 2出库
  ElMessage.success("出库成功,等待料箱到达捡料位置");
  checkHasOuting();
};

//捡料位
let outingRawBoxList: any[] = []; //确认添加的时候会对比捡料位和扫描的数量，多次点击会导致捡料位的数字一直改变，所以用一个变量来保存原始的捡料位数据
const outingBox = ref<any>({});
const outingMaterials = ref<any[]>([]);
let outInterval: number = -1;
const checkHasOuting = () => {
  //   点击出库之后，需要在其他地方（机器）确实已经到达检料位置，才能进行捡料
  //   接口需要传入出库outBox接口返回的orderId转为id传上去， 如果有这个orderId就开始轮询
  // 如果没有数据则停止轮询。数据返回的state是1处理中2启用3处理异常4已完成， 当为3或者4的时候停止轮询，并且在派发后清空oderid。
  if (commonS.orderId != -1) {
    outInterval = setInterval(() => {
      getStorageOrderInfo({ id: commonS.orderId })
        .then((res: any) => {
          if (res.data) {
            if (res.data.state === 3 || res.data.state === 4) {
              clearInterval(outInterval);
              commonS.orderId = -1;

              // 同时也刷新左侧列表数据
              getStorageBoxesList({}).then((res: any) => {
                boxesList.value = res.data;
              });

              if (commonS.changeBoxType === 2) {
                outingBox.value = { ...res.data };
                toSendBoxInfo.value = { ...outingBox.value }; //默认派发出库的盒子，如果返库了，扫码物料上方的载具信息则需要重新获取

                if (res.data.detailsList.length > 0) {
                  outingMaterials.value = outingBox.value.detailsList;
                  outingRawBoxList = JSON.parse(
                    JSON.stringify(outingBox.value.detailsList)
                  );
                  materialList.value = JSON.parse(
                    JSON.stringify(outingBox.value.detailsList)
                  );
                } else {
                  outingRawBoxList = [];
                  outingMaterials.value = [];
                }
              }
            }
          } else {
            clearInterval(outInterval);
          }
        })
        .catch(() => {
          clearInterval(outInterval);
          commonS.orderId = -1;
        });
    }, 5000);
  }
};
const backToStorage = async () => {
  console.log("back to storage");
  let res: any = await backToStorageAPI({
    vehicleCode: outingBox.value.vehicleCode,
    houseNo: outingBox.value.houseNo,
    detailsList: outingMaterials.value,
  });
  commonS.orderId = res.data.orderId;
  commonS.changeBoxType = 1; // 2出库

  ElMessage.success("返库成功,等待料箱到达");
  checkHasOuting();
  outingBox.value = {};
  toSendBoxInfo.value = {};
  outingMaterials.value = [];

  currentBox.value = {};
  currentBoxIndex.value = -1;
  boxSearch.value = "";
  // getStorageBoxesList({}).then((res: any) => {
  //   boxesList.value = res.data;
  // });
};

// 物料
const toSendBoxInfo = ref<any>({}); //扫码物料上方的载具信息，默认是出库的减料位的盒子，也可以通过扫码获取新的盒子
const scanCodeInput = ref("");
const materialList = ref<any[]>([]);

const boxInputValue = ref("");
const enterBoxInput = () => {
  boxInputValue.value = boxInputValue.value.trim();
  getBoxDetailByLabel(boxInputValue.value).then((res: any) => {
    toSendBoxInfo.value = {
      vehicleName: res.data.name,
      vehicleCode: res.data.code,
      vehicleId: res.data.id,
    };
    boxInputValue.value = "";
  });
};

const handleScanCodeInput = () => {
  getMaterialInfoByLabel(scanCodeInput.value).then((res: any) => {
    // 扫描之后要先查看数组中是否有这个物料，有的话就数量相加，没有的话就添加到数组中
    let hasMaterial = false;
    for (let i = 0; i < materialList.value.length; i++) {
      let currentMaterial = materialList.value[i];
      if (currentMaterial.materialCode === res.data.materialCode) {
        hasMaterial = true;
        // SEQ/BATCH 如果是流转卡号数量只能唯1，序列号相加
        if (currentMaterial.codeType === "BATCH") {
          materialList.value[i].num += res.data.num;
          break;
        }
      }
    }
    !hasMaterial && materialList.value.push(res.data);
    scanCodeInput.value = "";
  });
};
const sureToAdd = () => {
  //   循环物料列表，在循环捡料位的列表，进行数量相减，最大数量判断
  // 每次判断之前，先重置数据
  outingMaterials.value = JSON.parse(JSON.stringify(outingRawBoxList));

  for (let i = 0; i < materialList.value.length; i++) {
    let currentMaterial = materialList.value[i];
    for (let j = 0; j < outingMaterials.value.length; j++) {
      let currentOutingMaterial = outingMaterials.value[j];
      if (currentMaterial.materialCode === currentOutingMaterial.materialNo) {
        if (currentMaterial.num > currentOutingMaterial.num) {
          currentMaterial.num = currentOutingMaterial.num;
          currentOutingMaterial.num = 0;
        } else {
          currentOutingMaterial.num -= currentMaterial.num;
        }
        break;
      }
    }
  }
};

const deleteMaterial = (index: number) => {
  materialList.value.splice(index, 1);
};

// 出库终点
const destinationList = ref<any>();
const currentDestination = ref<any>({});
const currentDestinationIndex = ref(-1);

const onEndBoxClick = (index: number, item: any) => {
  currentDestination.value = item;
  currentDestinationIndex.value = index;
};

onMounted(() => {
  let wm = new WeakMap();
  getDestinationList(0).then((res: any) => {
    destinationList.value = res.data;
  });
  getStorageBoxesList({}).then((res: any) => {
    boxesList.value = res.data;
  });
  checkHasOuting();
});

const createTask = () => {
  const params = {
    circulationDetail: [...materialList.value],
    // coordinate: "",
    // houseNo: outingBox.value.houseNo,
    // locationNo: "",
    stationId: currentDestination.value.id,
    targetType: currentDestination.value.targetType,
    vehicleCode: toSendBoxInfo.value.vehicleCode,
    vehicleId: toSendBoxInfo.value.vehicleId,
    vehicleName: toSendBoxInfo.value.vehicleName,
  };

  addMaterialFlow(params).then((res: any) => {
    ElMessage.success(res.msg ?? "派发成功");
    currentBox.value = {};
    currentBoxIndex.value = -1;
    boxSearch.value = "";
    outingBox.value = {};
    outingMaterials.value = [];
    toSendBoxInfo.value = {};
    materialList.value = [];
    currentDestination.value = {};
    currentDestinationIndex.value = -1;
  });
};

onBeforeUnmount(() => {
  clearInterval(outInterval);
});
</script>

<style lang="scss" scoped>
.type-title {
  font-weight: 500;
  font-size: 30px;
  color: rgba(0, 0, 0, 0.9);
  text-align: left;
  margin-bottom: 15px;
}

.base-container {
  width: 100%;
  margin-top: 15px;
  height: calc(100vh - 420px);
}

.boxes-container {
  .box-item {
    background: #fff;
    border-radius: 16px;
    margin-bottom: 15px;
    padding: 10px 8px;
  }

  .box-selected {
    border: 2px solid #0a59f7;
  }

  .box-name {
    font-size: 20px;
    line-height: 40px;
  }

  .box-info {
    display: flex;
    justify-content: space-between;
    align-items: center;
    font-weight: bolder;
    font-size: 24px;
  }
}

.boxHeader {
  font-weight: bolder;
  font-size: 24px;
  text-align: left;
}

.outing-container {
  height: calc(100vh - 354px);

  .outing-box {
    background: #fff;
    border-radius: 16px;
    margin-bottom: 15px;
    padding: 10px 8px;
    position: relative;
  }

  .material-title {
    font-weight: bolder;
    font-size: 24px;
    text-align: left;
  }

  .material-info {
    font-size: 20px;
    display: flex;
    justify-content: space-between;
    align-items: center;
  }

  .batchCode {
    max-width: 60%;
    flex-shrink: 0;
    overflow: hidden;
    text-overflow: ellipsis;
  }
}

.list-container {
  width: 100%;
  display: grid;
  /*行间距*/
  grid-row-gap: 24px;
  /*列间距*/
  //grid-column-gap: 24px;

  grid-template-columns: 1fr;

  .list-box {
    height: 210px;
    background: #fff;
    border-radius: 16px 16px 16px 16px;
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    align-items: start;
    padding: 30px 30px;
    position: relative;

    .delete-btn {
      position: absolute;
      top: 15px;
      right: 15px;
    }

    .name {
      font-weight: 500;
      font-size: 24px;
      color: rgba(0, 0, 0, 0.9);
      text-align: left;
    }

    .spec {
      font-size: 20px;
      color: rgba(0, 0, 0, 0.6);
      text-align: left;
    }

    .bottom {
      display: flex;
      justify-content: start;
      align-items: end;
    }

    .unit {
      font-weight: 500;
      font-size: 24px;
      color: rgba(0, 0, 0, 0.6);
      text-align: left;
      margin-left: 5px;
    }
  }
}

.destination {
  height: calc(100vh - 353px);
  margin-top: 15px;

  .end-box {
    height: 80px;
    background: #ffffff;
    border-radius: 40px;
    display: flex;
    justify-content: center;
    align-items: center;
    font-weight: 500;
    font-size: 24px;
    color: rgba(0, 0, 0, 0.9);
    display: flex;
    justify-content: space-evenly;
    align-items: center;
  }

  .end-box:not(:last-child) {
    margin-bottom: 15px;
  }

  .selected {
    border-radius: 40px;
    border: 2px solid rgba(10, 89, 247, 1);
  }

  .name {
    font-weight: 500;
    font-size: 24px;
    color: rgba(0, 0, 0, 0.9);
  }
}

.sureBtn {
  height: 80px;
  font-size: 24px;
  //background: #0a59f7;
  border-radius: 76px 76px 76px 76px;
  width: 100%;
  margin-top: 10px;
}
</style>
