<template>
   <div class="proof-detail">
    <div style="position:relative;" class="caozuo" v-if="baseProof && id">
      <common-svg name="cunzhengliebiao-gengduo" class="tubiao" @click.native="showMoreAction = !showMoreAction;"></common-svg>
      <ul class="moreAction" v-show="showMoreAction" style="position:absolute;right:0;top:40px;z-index:1000;width:112px;padding: 20px;
          background:rgba(255,255,255,1);
          box-shadow:0px 2px 10px 0px rgba(0,0,0,0.12);">
        <li @click="delIncrementProof">删除</li>
        <li @click="reSendBlockChain(id)">重新上链</li>
      </ul>
    </div>
    <div class="px-4 bg-white mb">
      <van-field v-model="name" label="填写存证名称" placeholder="请输入" v-if="!proofName" />
    </div>
    <template-detail :detailInformation="detail" class="detail" style="margin-bottom:70px;"></template-detail>
    <div class="btn-group" v-if="!baseProof">
      <div style="overflow:hidden;color:#B6B5BA;font-size:14px;white-space:nowrap;margin-right: 10px;flex:auto;text-align:left;">已选模板:<span style="color:#3F79FE;margin-left:10px;">{{proofType}}</span></div>
      <div class="right" v-show="showBtn"
       style="width:119px;color:#FFFFFF;line-height:40px;
              height:40px;
              background:linear-gradient(360deg,rgba(93,123,246,1) 0%,rgba(108,122,254,1) 100%);
              box-shadow:0px 2px 10px 0px rgba(63,121,254,0.4);
              border-radius:4px;"
              :class="!existFilledField && 'btn-next-disabled'"
        @click="handleClickNext">
        下一步
      </div>
    </div>
    <div class="btn-group" v-else>
       <div
        v-show="showBtn"
        @click="save()"
        class="left"
        >保存</div>
      <van-button
        v-show="showBtn"
        @click="saveAndChain()"
        class="right"
        block
        color="#3F79FE"  
        type="primary" 
        >保存并上链</van-button>
    </div>
    <add-banner v-if="showBanner" :banners.sync="banners" @save="save" @save-and-chain="saveAndChain"></add-banner>
   </div>
</template>
<script lang="ts">
import { Component, Prop, Watch, Vue } from 'vue-property-decorator';
import { Getter, State } from 'vuex-class';
import { TemplateDataItem } from '@/const/interface';
import { Route } from 'vue-router';
import AddBanner from './components/AddBanner.vue';
import { DataType } from '@/const/enum';
import {IFirstLevelField} from "./types"

@Component({
  components: {
    AddBanner,
  },
})
export default class Detail extends Vue {
  @State('userInfo') private userInfo!: any;
  private showBanner: boolean = false;
  private id: number = 0;
  private name: string = '';
  private detail: any[]  = [] ;
  private showBtn: boolean = false;
  private initProof: any = {
    name: '',
    detail: '',
    banners: JSON.stringify([]),
  };
  private proofType: string = '';
  private checkEdited: boolean = true;
  private banners: string[] = [];
  private showMoreAction: boolean = false;
  @Prop({
  })
  private templateId!: number;
  @Prop({
  })
  private proofId!: number;
  @Prop({})
  private preProof!: any;
  @Prop({})
  private baseProof!: any;
  @Prop({})
  private proofName!: string;
  @Prop({})
  private detailStr!:string;

  private lockSaveChain = false

  get addOrTemplate() {
    const { templateId, proofName } = this;
    return {
      templateId,
      proofName,
    };
  }

  public mounted(){
    // 表明是当前组件用作 自定义模板功能（不增加模板）
    if(this.detailStr){
      this.detail = JSON.parse(this.detailStr)
      this.name = this.proofName;
      this.proofType = "临时自定义模板"
    }
  }
  

  @Watch('addOrTemplate', { immediate: true, deep: true })
  private async onRouteChange(newAddOrTemplate: any) {
    const { templateId, proofName } = newAddOrTemplate;
    if (templateId) {
      const { detail, name } = await this.$api.template.get(templateId);
      this.detail = JSON.parse(detail);
      this.proofType = name;
      this.name = proofName ? proofName : name;
      const banners = JSON.stringify([]);
      this.initProof = { name, detail, banners };
      this.showBtn = true;
    }
    // 自定义模板功能（不增加模板）也需要打开btn
    if(this.detailStr){
      this.showBtn = true;
    }
  }
  @Watch('proofId', { immediate: true, deep: true })
  private async onProofIdChange(newProofId: number, oldProofId: number) {
    if (newProofId) {
      const { detail,
              id,
              name,
              note }: any = this.baseProof
                                    ? await this.$api.proof.incrementGet(newProofId)
                                    : await this.$api.proof.get(newProofId);
      const proof: any = JSON.parse(detail);
      const ext: any = proof[proof.length - 1];
      this.detail = proof.slice(0, -1);
      this.id = id;
      this.name = name;
      this.proofType = ext.data.find((item: any) => item.key === '存证类型').data.value;
      this.banners = JSON.parse(note).banners;
      this.initProof = { name, detail: JSON.stringify(this.detail), banners: JSON.stringify(this.banners)};
      this.showBtn = true;
    }
  }
  get isEdited() {
    const { name, detail, banners } = this.initProof;
    const detailStr = JSON.stringify(this.detail);
    const bannersStr = JSON.stringify(this.banners);
    return this.name !== name || detailStr !== detail || banners !== bannersStr;
  }
  get baseProofId() {
    if (this.baseProof) {
      return (JSON.parse(this.baseProof) as any).id;
    }
    return -1;
  }
  get baseProofHash() {
    if (this.baseProof) {
      return (JSON.parse(this.baseProof) as any).hash;
    }
    return 'null';
  }
  get preProofHash() {
    if (this.preProof) {
      return (JSON.parse(this.preProof) as any).hash;
    }
    return 'null';
  }
  get note() {
    const { user , icon } = this.userInfo;
    const note = {
      userName: user, // String 账号名
      userIcon: icon, // String 用户图标图片地址
      evidenceName: this.name, // String 存证名称，ps：溯源时为父级商品名
      stepName: '', // String 溯源时的存证名称，非溯源时为空
      version: 1 , // Number 数据结构版本号，目前写死为 1
      banners: this.banners, // Array banner图数组，hash——图片哈希，target——跳转目标（暂未用到，可置空，某版溯源出现过这需求，作预留）
    };
    let obj: any = {};
    if (this.baseProof) {
      const baseProof = JSON.parse(this.baseProof);
      obj = {
        evidenceName: baseProof.name,
        stepName: this.name,
      };
    }
    return JSON.stringify({...note, ...obj});
  }
  get extData() {
    const baseData: TemplateDataItem = {
        label: 'ext',
        key: '',
        type: 3,
        data: [
            {
              data: {
                      type: 'text',
                      format: 'string',
                      value: this.name,
                    },
              type: 0,
              key: '存证名称',
              label: '存证名称',
            },
            {
              data: {
                      type: 'text',
                      format: 'string',
                      value: this.baseProofHash,
                    },
              type: 0,
              key: 'basehash',
              label: 'basehash',
            },
            {
              data: {
                      type: 'text',
                      format: 'string',
                      value: this.preProofHash,
                    },
              type: 0,
              key: 'prehash',
              label: 'prehash'},
            {
              data: {
                    type: 'text',
                    format: 'string',
                    value: this.proofType,
                  },
              type: 0,
              key: '存证类型',
              label: '存证类型'},
        ],
    };
    return baseData;
  }

  private handleClickNext(){
    if(!this.existFilledField)return;
    this.showBanner = true;
  }

  get existFilledField(){
    if(this.detail){ 
      for(let indexOfFirstLevel = 0; indexOfFirstLevel < this.detail.length; ++indexOfFirstLevel){
        const firstLevelItem: IFirstLevelField = this.detail[indexOfFirstLevel];
        const firstLevelData = firstLevelItem.data;
        for(let indexOfSecondLevel = 0; indexOfSecondLevel < firstLevelData.length; ++indexOfSecondLevel){
          const secondLevel = firstLevelData[indexOfSecondLevel];
          if(Array.isArray(secondLevel.data)){
            const ret = secondLevel.data.some((value)=>value.value !== '');
            if(ret) {
              console.log(1);
              return true
            };
          }else{
            if(Array.isArray(secondLevel.data.value)){
              if(secondLevel.data.value.length !== 0){
                return true;
              }
            }else{
              const value = secondLevel.data.value;
              if(typeof value === 'string'){
                if(value !== '') {
                  return true
                };
              }else if(typeof value === "number"){
                if(value !== 0) {
                  return true
                };
              }
            }
          }
        }
      }
    }
    return false;
  }
  
  private async beforeRouteLeave(to: Route, from: Route, next: (params?: any) => void) {
    if (!this.checkEdited) { return next(); }
    if (!this.isEdited) { return next(); }
    try {
      await this.$dialog.confirm({
        title: '提示',
        message: '返回后，信息不做保存，确定要返回吗？',
        confirmButtonText: '离开',
        cancelButtonText: '继续填写',
      });
    } catch (err) {
      return next(false);
    }
    next();
  }
  get proofAndExt() {
    const { detail, extData } = this;
    return [...detail, extData];
  }
  private async addProof() {
    const result = await this.$api.proof.add(this.name, this.proofAndExt, this.note);
    return result.id;
  }
  private async addIncrementProof() {
    const { baseProofId, baseProofHash, preProofHash , name , note, proofAndExt } = this;
    const result = await this.$api.proof.incrementAdd(
                                                baseProofId,
                                                baseProofHash,
                                                preProofHash,
                                                name,
                                                proofAndExt,
                                                note);
    return result.id;
  }
  private async editProof() {
    await this.$api.proof.update(this.id, this.name, this.proofAndExt, this.note);
  }
  private async editIncrementProof() {
    return await this.$api.proof.incrementEdit(this.id, this.name, this.proofAndExt, this.note);
  }
  private async incrementSendBlockChain(id: number) {
    return await this.$api.proof.incrementSendBlockChain(id);
  }
  private async sendBlockChain(id: number) {
    await this.$api.proof.sendBlockChian(id);
  }
  private async submit(flag: boolean = false) { // flase 仅保存 true: 保存并上链
    this.checkEdited = false;
    let id: number = -1;
    if (this.baseProof) {
      if (this.id) {
        id = this.id;
        await this.editIncrementProof();
      } else {
        if (!this.preProofHash) {
          this.$toast('请先上链上一条增量存证');
          return Promise.reject('请先上链上一条增量存证');
        }
        id = await this.addIncrementProof();
      }
      if (flag) {
        await this.incrementSendBlockChain(id);
      }
    } else {
      if (this.id) {
        id = this.id;
        await this.editProof();
      } else {
        id = await this.addProof();
      }
      if (flag) {
        await this.sendBlockChain(id);
      }
    }
  }
  private async save() {
    await this.submit();
    this.goProofList();
  }
  private async saveAndChain() {
    if(this.lockSaveChain) return;
    this.lockSaveChain = true;
    await this.submit(true);
    this.goProofList();
    this.lockSaveChain = false
  }
  private async delIncrementProof() {
    await this.$api.proof.incrementDelete(this.id);
    this.goProofList();
  }
  private async reSendBlockChain(id: number) {
    await this.incrementSendBlockChain(id);
    this.goProofList();
  }
  private goProofList() {
    this.$router.push({name: 'ProofList'});
  }
}
</script>
<style scoped lang="scss">
.px-4{
  padding: 0 16px;
}
.mb{
  margin-bottom: 10px;
}
.bg-white{
  background: white;
}
  .proof-detail{
    padding: 9px 0px;
    background: #F9F9FB;
    min-height: 100vh;
    ::v-deep .van-field{
      flex-direction: column;
      input{
        font-size: 16px;
        font-weight: 500;
      }
      &__label{
        text-align: left;
        font-size: 14px;
        color: $labelColor;
       
      }
      &__value{
        margin-top: 8px;
        color: $valueColor;
      }
      
    }
    ::v-deep .van-cell{
      padding: 12px 0;
    }
    .van-cell::after{
      left: 0px;
      right: 0px;
    }
    .caozuo{
      .tubiao{
        position:absolute;
        right: 17px;
        top: 10px;
        z-index: 1000;
      }
      .moreAction{
        li{
          line-height: 2em;
        }
      }
    }
    .btn-next-disabled{
      background: #B2C9FF !important;
    }
    .detail{
      margin-bottom: 66px;
    }
    .btn-group{
      z-index: 10;
      .right{
        flex: auto;
      }
      .left{
        width: 160px;
        height: 43.98px;
        line-height: 43.98px;
        margin-right: 10px;
        background: #FFFFFF;
        color: #000000;
        border-radius:4px;
        border:1px solid rgba(238,238,238,1);
      }
    }
   
  }
</style>