<template>
  <div v-loading="loading" element-loading-spinner="el-icon-loading" :element-loading-text="loadingText" class="flex-v"
       :class="{'full-height':fullHeight}">
    <Panel :title="titleSearchForm" v-if="titleSearchForm && allowQuery">
      <template slot="buttons">
        <el-button @click="pageTable.handleLoad()" class="blue" icon="el-icon-search">查询</el-button>
        <el-button @click="pageTable.handleReset()" class="yellow" icon="el-icon-refresh">重置</el-button>
      </template>
      <el-form inline :label-position="queryFormLabelPosition" :model="pageTable.param" ref="queryform" @submit.native.prevent>
        <slot name="search-form" v-bind:formData="pageTable.param"/>
      </el-form>
    </Panel>
    <Panel :title="titleDataTable" class="flex-1">
      <template slot="buttons">
        <slot name="table-buttons" :data="pageTable"/>
        <el-button v-if="allowRefresh" @click="pageTable.handleLoad()" class="blue" icon="el-icon-search">刷新</el-button>
        <el-button v-if="allowAdd" class="green" @click="handleAdd" icon="el-icon-plus" :title="'新增'+titleEditor">新增</el-button>
        <el-button v-if="allowDeleteBatch" class="red" @click="handleDeleteBatch" icon="el-icon-close" :title="'批量删除'+titleEditor">
          删除
        </el-button>
      </template>
      <div class="flex-v full-height">
        <el-table class="flex-1"
                  border
                  highlight-current-row
                  :data="pageTable.data"
                  v-loading="pageTable.isLoading"
                  element-loading-spinner="el-icon-loading"
                  element-loading-text="数据加载中"
                  :max-height="tableMaxHeight"
                  @selection-change="selection=>pageTable.selection=selection"
                  ref="table">
          <slot name="table-columns" v-if="tableActionAlign==='right'"/>
          <el-table-column v-if="allowEdit || allowDelete" label="操作" :width="tableActionWidthReal" align="center">
            <template slot-scope="scope">
              <slot name="table-column-actions" :row="scope.row" :column="scope.column"/>
              <el-button v-if="allowCopy" class="blue" @click="handleCopy(scope.row)">复制</el-button>
              <el-button v-if="allowEdit" class="blue" @click="handleEdit(scope.row)" :disabled="scope.row.$isReadonly">编辑
              </el-button>
              <el-button v-if="allowDelete" class="red" @click="handleDelete(scope.row)" :disabled="scope.row.$isReadonly">
                删除
              </el-button>
            </template>
          </el-table-column>
          <slot name="table-columns" v-if="tableActionAlign==='left'"/>
        </el-table>
        <div class="la-panel--tableFooter" v-if="allowExport  || allowPagination">
          <export-ctrl v-if="allowExport" class="pull-left" @export="pageTable.handleExport($event, $refs.table)"/>
          <el-pagination v-if="allowPagination" background :page-size.sync="pageTable.size" :current-page.sync="pageTable.curr" :total="pageTable.total"/>
          <div style="clear:both"></div>
        </div>

      </div>
    </Panel>
    <el-dialog close-on-press-escape :visible.sync="editor.visible" :width="editorWidth" append-to-body>
      <div slot="title" class="font-white">
        <i class="el-icon-edit"/>
        {{editor.title}}
      </div>
      <div v-if="editor.visible" element-loading-spinner="el-icon-loading" v-loading="editor.loading">
        <slot name="editor" :data="editor.data" v-if="editor.ready"/>
        <div class="text-center">
          <slot name="buttons"/>
          <el-button class="blue" @click="handleSave" icon="el-icon-fa-save" size="mini">保存</el-button>
        </div>
      </div>
    </el-dialog>
  </div>
</template>

<script>
  import PageTable from '../libs/PageTable'

  let TrueFunc = () => {
    return () => true
  };
  let EmptyFunc = () => {
    return {}
  };


  export default {
    name: "CurdPanel",
    props: {
      allowExport: {type: Boolean, default: true},
      allowPagination: {type: Boolean, default: true},
      allowAdd: {type: Boolean, default: true},
      allowEdit: {type: Boolean, default: true},
      allowCopy: {type: Boolean, default: false},
      allowDelete: {type: Boolean, default: true},
      allowDeleteBatch: {type: Boolean, default: false},
      allowQuery: {type: Boolean, default: true},
      allowRefresh: {type: Boolean, default: false},
      titleSearchForm: {type: String, require: true},
      titleDataTable: {type: String, require: true},
      titleEditor: {type: String, require: true},
      editorWidth: {type: String, require: true},
      editorDefaultData: {type: Object, require: false, default: EmptyFunc},
      tableMaxHeight: {type: [String, Number]},
      tableActionWidth: {type: Number, default: 0},
      tableActionAlign: {type: String, default: 'right'},
      fullHeight: {type: Boolean, require: false},
      editorValidate: {type: Function, default: TrueFunc},
      searchParam: {type: Object},
      doQuery: {type: Function},
      doGet: {type: Function},
      doSave: {type: Function},
      doDelete: {type: Function},
      closeOnSave: {type: Boolean, default: false},
      autoLoad: {type: Boolean, default: false},

      queryFormLabelPosition: {type: String, default: 'left'}
    },
    data() {
      return {
        loadingText: "系统加载中...",
        loading: false,
        tableActionWidthReal: this.tableActionWidth,
        editor: {
          data: this.editorDefaultData,
          loading: false,
          ready: false,
          title: this.titleEditor,
          visible: false
        },
        pageTable: new PageTable({
          autoLoad: this.autoLoad,
          doLoad: this.doQuery,
          param: Object.assign({}, this.searchParam),
          log: false
        })
      }
    },
    beforeMount() {
      if (this.tableActionWidth > 0) {
        this.tableActionWidthReal = this.tableActionWidth;
      } else {
        let width = 0;
        if (this.allowCopy) {
          width += 40;
        }
        if (this.allowEdit) {
          width += 40;
        }
        if (this.allowDelete) {
          width += 40;
        }
        this.tableActionWidthReal = width;
      }
    },
    methods: {
      async handleAdd(defaultData) {
        this.editor.ready = false;
        this.editor.title = this.titleEditor + ' - 新建';
        this.editor.uuid = "";
        this.editor.data = Object.assign({}, this.editorDefaultData, defaultData);
        this.editor.visible = true;
        this.$emit("before-edit", this.editor.data);
        this.editor.ready = true;
      },
      async handleSave() {
        await this.editorValidate();
        await this.confirm(this.editor.data, "点击确定提交数据,请确认您的数据填写正确?");
        this.editor.loading = true;
        try {
          this.$emit("before-save", this.editor.data);
          let resp = await this.doSave.call(this, this.editor.data);
          await this.pageTable.handleLoad();
          if (this.closeOnSave) {
            this.editor.visible = false;
          }
          Object.assign(this.editor.data, resp.data || {});
          this.$emit("after-save", this.editor.data);
        } finally {
          this.editor.loading = false;
        }
      },
      async handleCopy(row) {
        try {
          let uuid = row.uuid;
          this.editor.ready = false;
          this.editor.title = this.titleEditor + ' - 复制';
          this.editor.visible = true;
          this.editor.loading = true;
          this.editor.uuid = "";
          let data = await this.doGet.call(this, uuid);
          delete data['uuid'];
          this.$emit("before-copy", data);
          this.editor.data = data;
          this.editor.ready = true;
        } finally {
          this.editor.loading = false;
        }
      },
      async handleEdit(row) {
        try {
          let uuid = row.uuid;
          this.editor.ready = false;
          this.editor.title = this.titleEditor + ' - 编辑';
          this.editor.loading = true;
          this.editor.visible = true;
          this.editor.uuid = row.uuid;
          this.editor.data = await this.doGet.call(this, uuid);
          this.$emit("before-edit", this.editor.data);
          this.editor.ready = true;
        } finally {
          this.editor.loading = false;
        }
      },
      async handleDelete(row) {
        let uuid = row.uuid;
        await this.confirm();
        await this.doDelete.call(this, uuid);
        this.$emit("after-delete", uuid);
        await this.pageTable.handleLoad();
      },
      async handleDeleteBatch() {
        if (this.pageTable.selection.length === 0) return this.$message.error("请先选择数据");
        await this.confirm();
        let selection = [].concat(this.pageTable.selection);
        let uuidArray = selection.map(s => s.uuid);
        await this.doDelete.call(this, uuidArray.join(","));
        this.$emit("after-delete-batch", selection);
        await this.pageTable.handleLoad();
      }
    }
  }
</script>