Browse Source

add inner edit table

Sendya 6 years ago
parent
commit
9e89d3069b

+ 1 - 2
idea.config.js

@@ -2,7 +2,7 @@
 const path = require('path')
 
 function resolve(dir) {
-    return path.join(__dirname, '.', dir)
+  return path.join(__dirname, '.', dir)
 }
 
 module.exports = {
@@ -10,7 +10,6 @@ module.exports = {
     resolve: {
         extensions: ['.js', '.vue', '.json'],
         alias: {
-            'vue$': 'vue/dist/vue.esm.js',
             'config': resolve('config'),
             '@': resolve('src'),
             '@views': resolve('src/views'),

+ 1 - 1
package.json

@@ -11,9 +11,9 @@
     "@antv/data-set": "^0.8.9",
     "ant-design-vue": "^1.0.3",
     "axios": "^0.18.0",
+    "dayjs": "^1.7.5",
     "js-cookie": "^2.2.0",
     "md5": "^2.2.1",
-    "moment": "^2.22.2",
     "nprogress": "^0.2.0",
     "viser-vue": "^2.3.0",
     "vue": "^2.5.17",

+ 81 - 33
src/components/table/index.js

@@ -3,6 +3,10 @@ export default {
   data() {
     return {
       needTotalList: [],
+
+      selectedRows: [],
+      selectedRowKeys: [],
+
       localLoading: false,
       localDataSource: [],
       localPagination: Object.assign({}, T.props.pagination)
@@ -24,7 +28,11 @@ export default {
     showSizeChanger: {
       type: Boolean,
       default: true
-    }
+    },
+    showAlertInfo: {
+      type: Boolean,
+      default: true
+    },
   }),
   watch: {
     'localPagination.current' (val) {
@@ -49,7 +57,18 @@ export default {
       this.localPagination = Object.assign({}, this.localPagination, {
         showSizeChanger: val
       });
-    }
+    },
+    /*
+    'selectedRows': function (selectedRows) {
+      this.needTotalList = this.needTotalList.map(item => {
+        return {
+          ...item,
+          total: selectedRows.reduce( (sum, val) => {
+            return sum + val[item.dataIndex]
+          }, 0)
+        }
+      })
+    }*/
   },
   created() {
     this.localPagination = Object.assign({}, this.localPagination, {
@@ -115,6 +134,7 @@ export default {
     },
     updateSelect (selectedRowKeys, selectedRows) {
       this.selectedRowKeys = selectedRowKeys
+      this.selectedRows = selectedRows
       let list = this.needTotalList
       this.needTotalList = list.map(item => {
         return {
@@ -124,16 +144,42 @@ export default {
           }, 0)
         }
       })
-      this.$emit('change', selectedRowKeys, selectedRows)
+      // this.$emit('change', selectedRowKeys, selectedRows)
+    },
+    updateEdit() {
+      this.selectedRows = []
     },
     onClearSelected () {
       this.selectedRowKeys = []
       this.updateSelect([], [])
     },
     renderMsg(h) {
-      let d = this.needTotalList.map(item => {
-        return h('span', `${item.title} 总计 ${item.customRender ? item.customRender(item.total) : item.total}`)
-      })
+      const _vm = this
+      let d = []
+      // 构建 已选择
+      d.push(
+        h('span', { style: { marginRight: '12px' } }, ['已选择 ', h('a', { style: { fontWeight: 600 }}, this.selectedRows.length)])
+      );
+
+      // 构建 列统计
+      this.needTotalList.map(item => {
+        d.push( h('span',
+          { style: { marginRight: '12px' } },
+          [
+            `${ item.title }总计 `,
+            h('a', { style: { fontWeight: 600 }}, `${ item.customRender ? item.customRender(item.total) : item.total }`)
+          ] )
+        )
+      });
+
+      // 构建 清空选择
+      d.push( h('a', {
+        style: { marginLeft: '24px' },
+        on: {
+          click: _vm.onClearSelected
+        }
+      }, '清空') )
+
       return d
     },
     renderAlert(h) {
@@ -141,7 +187,7 @@ export default {
       return h('span', {
         slot: 'message'
       }, this.renderMsg(h))
-    }
+    },
   },
   render(h) {
     const _vm = this
@@ -157,37 +203,39 @@ export default {
       return props[k] = _vm[k];
     })
 
-    /*return h("a-table", {
+    // 显示信息提示
+    if (this.showAlertInfo) {
+
+      props.rowSelection = { selectedRowKeys: this.selectedRowKeys, onChange: this.updateSelect };
+
+      return h('div', {}, [
+        h("a-alert", {
+          style: {
+            marginBottom: '16px'
+          },
+          props: {
+            type: 'info',
+            showIcon: true
+          }
+        }, [ _vm.renderAlert(h) ]),
+        h("a-table", {
+          tag: "component",
+          attrs: props,
+          on: {
+            change: _vm.loadData
+          },
+          scopedSlots: this.$scopedSlots
+        })
+      ]);
+    }
+
+    return h("a-table", {
       tag: "component",
       attrs: props,
       on: {
         change: _vm.loadData
       },
       scopedSlots: this.$scopedSlots
-    });*/
-
-    return h('div', {
-
-    }, [
-      h("a-alert", {
-        style: {
-          marginBottom: '16px'
-        },
-        props: {
-          type: 'info',
-          showIcon: true
-        }
-      }, [ _vm.renderAlert(h) ]),
-      h("a-table", {
-        tag: "component",
-        attrs: props,
-        on: {
-          change: _vm.loadData
-        },
-        scopedSlots: this.$scopedSlots
-      })
-    ]);
-
-
+    });
   }
 };

+ 5 - 0
src/main.js

@@ -9,9 +9,14 @@ import Antd from 'ant-design-vue'
 import Viser from 'viser-vue'
 import 'ant-design-vue/dist/antd.less';  // or 'ant-design-vue/dist/antd.less'
 
+import * as dayjs from 'dayjs' // 日期时间支持库
 
 import '@/permission' // permission control
 
+Vue.filter('dayjs', function(dataStr, pattern = 'YYYY-MM-DD HH:mm:ss') {
+  return dayjs(dataStr).format(pattern)
+})
+
 Vue.use(Antd)
 Vue.use(VueAxios, router)
 Vue.use(Viser)

+ 1 - 0
src/permission.js

@@ -26,6 +26,7 @@ router.beforeEach((to, from, next) => {
         store.dispatch('GetInfo').then(res => {
           const roles = res.result && res.result.role
           store.dispatch('GenerateRoutes', { roles }).then(() => { // 根据roles权限生成可访问的路由表
+
             router.addRoutes(store.getters.addRouters) // 动态添加可访问路由表
             next({ ...to, replace: true }) // hack方法 确保addRoutes已完成 ,set the replace: true so the navigation will not leave a history record
           })

+ 11 - 4
src/router/index.js

@@ -115,6 +115,12 @@ export const asyncRouterMap = [
         component: () => import('../views/list/TableList'),
         meta: { title: '查询表格' }
       },
+      {
+        path: '/list/edit-table',
+        name: 'EditList',
+        component: () => import('@/views/list/TableInnerEditList'),
+        meta: { title: '内联编辑表格' }
+      },
       {
         path: '/list/basic-list',
         name: 'BasicList',
@@ -130,23 +136,24 @@ export const asyncRouterMap = [
       {
         path: '/list/search',
         name: 'SearchList',
-        redirect: '/list/search/articles',
+        component: () => import('@/views/list/search/SearchLayout'),
+        redirect: '/list/search/article',
         meta: { title: '搜索列表' },
         children: [
           {
-            path: '/list/search/articles',
+            path: '/list/search/article',
             name: 'SearchArticles',
             component: () => import('../views/list/TableList'),
             meta: { title: '搜索列表(文章)' }
           },
           {
-              path: '/list/search/projects',
+              path: '/list/search/project',
               name: 'SearchProjects',
               component: () => import('../views/list/TableList'),
               meta: { title: '搜索列表(项目)' }
           },
           {
-              path: '/list/search/applications',
+              path: '/list/search/application',
               name: 'SearchApplications',
               component: () => import('../views/list/TableList'),
               meta: { title: '搜索列表(应用)' }

+ 1 - 1
src/utils/auth.js

@@ -1,6 +1,6 @@
 import Cookies from 'js-cookie'
 
-const TokenKey = 'Access-Token'
+export const TokenKey = 'Access-Token'
 
 export function getToken() {
   return Cookies.get(TokenKey)

+ 246 - 0
src/views/list/TableInnerEditList.vue

@@ -0,0 +1,246 @@
+<template>
+  <a-card :bordered="false">
+    <div :class="advanced ? 'search' : null">
+      <a-form layout="horizontal">
+        <div :class="advanced ? null : 'fold'">
+          <a-row :gutter="48">
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="规则编号"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}"
+              >
+                <a-input placeholder="请输入"/>
+              </a-form-item>
+            </a-col>
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="使用状态"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}"
+              >
+                <a-select placeholder="请选择">
+                  <a-select-option value="1">关闭</a-select-option>
+                  <a-select-option value="2">运行中</a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="调用次数"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}"
+              >
+                <a-input-number style="width: 100%" placeholder="请输入"/>
+              </a-form-item>
+            </a-col>
+          </a-row>
+
+          <a-row :gutter="48" v-if="advanced">
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="更新日期"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}">
+                <a-date-picker style="width: 100%" placeholder="请输入更新日期"/>
+              </a-form-item>
+            </a-col>
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="使用状态"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}">
+                <a-select placeholder="请选择">
+                  <a-select-option value="1">关闭</a-select-option>
+                  <a-select-option value="2">运行中</a-select-option>
+                </a-select>
+              </a-form-item>
+            </a-col>
+            <a-col :md="8" :sm="24">
+              <a-form-item
+                label="描述"
+                :labelCol="{span: 5}"
+                :wrapperCol="{span: 18, offset: 1}"
+              >
+                <a-input placeholder="请输入"/>
+              </a-form-item>
+            </a-col>
+          </a-row>
+        </div>
+
+        <span style="float: right; margin-top: 3px;">
+          <a-button type="primary">查询</a-button>
+          <a-button style="margin-left: 8px">重置</a-button>
+          <a @click="toggleAdvanced" style="margin-left: 8px">
+            {{ advanced ? '收起' : '展开' }}
+            <a-icon :type="advanced ? 'up' : 'down'"/>
+          </a>
+        </span>
+      </a-form>
+    </div>
+
+    <s-table
+      ref="table"
+      size="default"
+      :columns="columns"
+      :data="loadData"
+      :rowSelection="{ selectedRowKeys: selectedRowKeys, onChange: onChange }"
+    >
+      <template v-for="col in columns" v-if="col.scopedSlots" :slot="col.dataIndex" slot-scope="text, record, index">
+        <div>
+          <a-input
+            v-if="record.editable"
+            style="margin: -5px 0"
+            :value="text"
+            @change="e => handleChange(e.target.value, record.key, col)"
+          />
+          <template v-else>{{text}}</template>
+        </div>
+      </template>
+      <template slot="action" slot-scope="text, record, index">
+        <div class='editable-row-operations'>
+          <span v-if="record.editable">
+            <a @click="() => save(record)" style="margin-right: 12px">Save</a>
+            <a-popconfirm title='Sure to cancel?' @confirm="() => cancel(record)">
+              <a>Cancel</a>
+            </a-popconfirm>
+          </span>
+          <span v-else>
+            <a @click="() => edit(record, index)">Edit</a>
+          </span>
+        </div>
+      </template>
+    </s-table>
+
+  </a-card>
+</template>
+
+<script>
+  import STable from '@/components/table/'
+
+  export default {
+    name: "TableList",
+    components: {
+      STable
+    },
+    data () {
+      return {
+        // 高级搜索 展开/关闭
+        advanced: false,
+        // 查询参数
+        queryParam: {},
+        // 表头
+        columns: [
+          {
+            title: '规则编号',
+            dataIndex: 'no'
+          },
+          {
+            title: '描述',
+            dataIndex: 'description',
+            scopedSlots: { customRender: 'description' },
+          },
+          {
+            title: '服务调用次数',
+            dataIndex: 'callNo',
+            sorter: true,
+            needTotal: true,
+            scopedSlots: { customRender: 'callNo' },
+            // customRender: (text) => text + ' 次'
+          },
+          {
+            title: '状态',
+            dataIndex: 'status',
+            needTotal: true,
+            scopedSlots: { customRender: 'status' },
+          },
+          {
+            title: '更新时间',
+            dataIndex: 'updatedAt',
+            sorter: true,
+            scopedSlots: { customRender: 'updatedAt' },
+          },
+          {
+            table: '操作',
+            dataIndex: 'action',
+            width: '150px',
+            scopedSlots: { customRender: 'action' },
+          }
+        ],
+        // 加载数据方法 必须为 Promise 对象
+        loadData: parameter => {
+          return this.$http.get('/service', {
+            params: Object.assign(parameter, this.queryParam)
+          }).then(res => {
+            return res.result
+          })
+        },
+
+        selectedRowKeys: [],
+        selectedRows: []
+      }
+    },
+    methods: {
+
+      handleChange (value, key, column) {
+        console.log(value, key, column)
+      },
+      edit (row) {
+        row.editable = true
+        row = Object.assign({}, row)
+        this.$refs.table.updateEdit()
+      },
+      save (row) {
+        delete row.editable
+        this.$refs.table.updateEdit()
+      },
+      cancel (row) {
+        delete row.editable
+        this.$refs.table.updateEdit()
+      },
+
+      onChange (selectedRowKeys, selectedRows) {
+        this.selectedRowKeys = selectedRowKeys
+        this.selectedRows = selectedRows
+      },
+      toggleAdvanced () {
+        this.advanced = !this.advanced
+      },
+    },
+    watch: {
+      /*
+      'selectedRows': function (selectedRows) {
+        this.needTotalList = this.needTotalList.map(item => {
+          return {
+            ...item,
+            total: selectedRows.reduce( (sum, val) => {
+              return sum + val[item.dataIndex]
+            }, 0)
+          }
+        })
+      }
+      */
+    }
+  }
+</script>
+
+<style lang="scss" scoped>
+  .search {
+    margin-bottom: 54px;
+  }
+
+  .fold {
+    width: calc(100% - 216px);
+    display: inline-block
+  }
+
+  .operator {
+    margin-bottom: 18px;
+  }
+
+  @media screen and (max-width: 900px) {
+    .fold {
+      width: 100%;
+    }
+  }
+</style>

+ 9 - 9
src/views/list/TableList.vue

@@ -69,13 +69,13 @@
         </div>
 
         <span style="float: right; margin-top: 3px;">
-                  <a-button type="primary">查询</a-button>
-                  <a-button style="margin-left: 8px">重置</a-button>
-                  <a @click="toggleAdvanced" style="margin-left: 8px">
-                    {{ advanced ? '收起' : '展开' }}
-                    <a-icon :type="advanced ? 'up' : 'down'"/>
-                  </a>
-                </span>
+          <a-button type="primary">查询</a-button>
+          <a-button style="margin-left: 8px">重置</a-button>
+          <a @click="toggleAdvanced" style="margin-left: 8px">
+            {{ advanced ? '收起' : '展开' }}
+            <a-icon :type="advanced ? 'up' : 'down'"/>
+          </a>
+        </span>
       </a-form>
     </div>
 
@@ -176,14 +176,13 @@
       onChange (selectedRowKeys, selectedRows) {
         this.selectedRowKeys = selectedRowKeys
         this.selectedRows = selectedRows
-
-        console.log(this.selectedRowKeys, this.selectedRows)
       },
       toggleAdvanced () {
         this.advanced = !this.advanced
       },
     },
     watch: {
+      /*
       'selectedRows': function (selectedRows) {
         this.needTotalList = this.needTotalList.map(item => {
           return {
@@ -194,6 +193,7 @@
           }
         })
       }
+      */
     }
   }
 </script>

+ 70 - 0
src/views/list/search/SearchLayout.vue

@@ -0,0 +1,70 @@
+<template>
+  <div>
+    <div class="search-head">
+      <div class="search-input">
+        <a-input-search style="width: 522px" placeholder="请输入..." size="large" enterButton="搜索" />
+      </div>
+      <div style="padding: 0 24px">
+        <a-tabs :tabBarStyle="{margin: 0}" @change="callback" :activeKey="activeKey">
+          <a-tab-pane tab="文章" key="1"></a-tab-pane>
+          <a-tab-pane tab="项目" key="2"></a-tab-pane>
+          <a-tab-pane tab="应用" key="3"></a-tab-pane>
+        </a-tabs>
+      </div>
+    </div>
+    <div class="search-content">
+      <router-view />
+    </div>
+  </div>
+</template>
+
+<script>
+  export default {
+    name: "SearchLayout",
+    computed: {
+      activeKey () {
+        switch (this.$route.path) {
+          case '/list/search/article':
+            return '1'
+          case '/list/search/project':
+            return '2'
+          case '/list/search/application':
+            return '3'
+          default:
+            return '1'
+        }
+      }
+    },
+    methods: {
+      callback (key) {
+        switch (key) {
+          case '1':
+            this.$router.push('/list/search/article')
+            break
+          case '2':
+            this.$router.push('/list/search/project')
+            break
+          case '3':
+            this.$router.push('/list/search/application')
+            break
+          default:
+            this.$router.push('/workplace')
+        }
+      }
+    }
+  }
+</script>
+
+<style lang="scss" scoped>
+  .search-head{
+    background-color: #fff;
+    margin: -25px -24px -24px;
+    .search-input{
+      text-align: center;
+      margin-bottom: 16px;
+    }
+  }
+  .search-content{
+    margin-top: 48px;
+  }
+</style>

+ 16 - 0
vue.config.js

@@ -1,3 +1,9 @@
+const path = require('path')
+
+function resolve (dir) {
+  return path.join(__dirname, dir)
+}
+
 // vue.config.js
 module.exports = {
   pages: {
@@ -8,6 +14,16 @@ module.exports = {
   },
   configureWebpack: {
 
+  },
+  chainWebpack: (config) => {
+    config.resolve.alias
+      .set('@$', resolve('src'))
+      .set('@api', resolve('src/api'))
+      .set('@assets', resolve('src/assets'))
+      .set('@comp', resolve('src/components'))
+      .set('@views', resolve('src/views'))
+      .set('@layout', resolve('src/layout'))
+      .set('@static', resolve('src/static'))
   },
   css: {
     loaderOptions: {

+ 5 - 1
yarn.lock

@@ -2554,6 +2554,10 @@ date-now@^0.1.4:
   version "0.1.4"
   resolved "https://registry.yarnpkg.com/date-now/-/date-now-0.1.4.tgz#eaf439fd4d4848ad74e5cc7dbef200672b9e345b"
 
+dayjs@^1.7.5:
+  version "1.7.5"
+  resolved "https://registry.yarnpkg.com/dayjs/-/dayjs-1.7.5.tgz#14715cb565d1f8cb556a8531cb14bf1fc33067cc"
+
 de-indent@^1.0.2:
   version "1.0.2"
   resolved "https://registry.yarnpkg.com/de-indent/-/de-indent-1.0.2.tgz#b2038e846dc33baa5796128d0804b455b8c1e21d"
@@ -4937,7 +4941,7 @@ mkdirp@0.5.1, mkdirp@0.5.x, "mkdirp@>=0.5 0", mkdirp@^0.5.0, mkdirp@^0.5.1, mkdi
   dependencies:
     minimist "0.0.8"
 
-moment@^2.21.0, moment@^2.22.2:
+moment@^2.21.0:
   version "2.22.2"
   resolved "https://registry.yarnpkg.com/moment/-/moment-2.22.2.tgz#3c257f9839fc0e93ff53149632239eb90783ff66"