1、創建商品分類分支goods_params並push到遠程
創建分支goods_params,並切換到當前:
git checkout -b goods_params
推送到遠程:(以前碼雲中沒有該分支,所以要加-u,如果碼雲中有該分支,則不需要加-u)
git push -u origin goods_params
2、通過路由加載分類參數組件
在goods文件夾和Params.vue文件:
<template> <div> <h3>分類參數組件</h3> </div> </template> <script> export default { } </script> <style lang="less" scoped> </style>
添加路由:
import Params from '../components/goods/Params.vue' const routes = [ { path: '/', redirect: '/login' }, // 重定向 { path: '/login', component: Login }, { path: '/home', component: Home, redirect: '/welcome', // 重定向 children: [ // 子路由 { path: '/welcome', component: Welcome }, { path: '/users', component: Users }, // 用戶列表 { path: '/rights', component: Rights }, // 權限列表 { path: '/roles', component: Roles }, // 角色列表 { path: '/categories', component: Cate }, // 商品分類 { path: '/params', component: Params } // 分類參數 ] } ]
點擊左側菜單的分類參數的效果如圖:
3、渲染分類參數頁面的基本UI布局
還是面包屑和card視圖:
<template> <div> <!--面包屑導航區域--> <el-breadcrumb separator-class="el-icon-arrow-right"> <el-breadcrumb-item :to="{ path: '/home' }">首頁</el-breadcrumb-item> <el-breadcrumb-item>商品管理</el-breadcrumb-item> <el-breadcrumb-item>分類參數</el-breadcrumb-item> </el-breadcrumb> <!--卡片視圖區域--> <el-card> 123 </el-card> </div> </template>
然后是頭部警告區域,需要用到Alert 警告組件,導入element.js里
在 Alert 組件中,你可以設置是否可關閉,關閉按鈕的文本以及關閉時的回調函數。closable
屬性決定是否可關閉,接受boolean
,默認為true
。你可以設置close-text
屬性來代替右側的關閉圖標,注意:close-text
必須為文本。設置close
事件來設置關閉時的回調。通過設置show-icon
屬性來顯示 Alert 的 icon。
<!--卡片視圖區域--> <el-card> <!--警告區域--> <el-alert title="注意:只允許為第三季分類設置相關參數!" type="warning" show-icon :closable="false"></el-alert> <!--選擇商品分類區域--> <el-row class="cat_opt"> <el-col> <span>選擇商品分類:</span> <!--選擇商品分類的級聯選擇框--> </el-col> </el-row> </el-card> <style lang="less" scoped> .cat_opt{margin:15px 0;} </style>
此時效果圖:
4、獲取商品分類列表數據
<script> export default { data() { return { cateList: [], // 商品分類列表數據 } }, created() { this.getCateList() }, methods: { // 獲取所有的商品分類列表 async getCateList() { const { data: res } = await this.$http.get('categories') if (res.meta.status !== 200) { return this.$message.error('獲取商品分類失敗!') } this.cateList = res.data } } } </script>
5、渲染商品分類的級聯選擇框
添加級聯選擇框代碼:
<!--選擇商品分類的級聯選擇框--> <!-- options用來指定數據源 props用來指定配置對象--> <el-cascader v-model="selectedCateKeys" :options="cateList" :props="cateProps" @change="cateChanged" clearable></el-cascader> <script> export default { data() { return { // 指定級聯選擇框的配置對象 cateProps: { expandTrigger: 'hover', // 次級菜單的展開方式 click / hover value: 'cat_id', // 指定選中值的屬性 label: 'cat_name', // 指定選中標簽的名稱 children: 'children' // 指定父子嵌套的屬性 }, selectedCateKeys: [] // 級聯選擇框雙向綁定 選中的商品分類的ID數組 } }, methods: { // 級聯選擇框選中項變化,會觸發這個函數 cateChanged() { console.log(this.selectedCateKeys) } } } </script>
此時點擊級聯選擇框,選中商品效果圖:
6、控制級聯選擇框的選中范圍
以為警告框寫了只允許為第三級分類設置相關參數,所以分類也應該只能選中三級分類:
// 級聯選擇框選中項變化,會觸發這個函數 cateChanged() { // 證明選中的不是三級分類 if (this.selectedCateKeys.length !== 3) { this.selectedCateKeys = [] return } // 證明選中的是三級分類 console.log(this.selectedCateKeys) }
7、渲染分類參數的Tabs標簽組件
v-model實現雙向數據綁定,tab-click點擊事件
label指定標題,name頁簽名稱,自動綁定到v-model的屬性上
Tabs 和 TabPane 需要導入element.js中,然后添加代碼:
<!--Tabs標簽區域--> <el-tabs v-model="activeName" @tab-click="handleTabClick"> <el-tab-pane label="動態參數" name="first">動態參數</el-tab-pane> <el-tab-pane label="靜態屬性" name="second">靜態屬性</el-tab-pane> </el-tabs> <script> export default { data() { return { // 被激活的標簽的名稱,默認為first activeName: 'first' } }, methods: { // tab標簽的點擊事件處理函數 handleTabClick() { console.log(this.activeName) } } } </script>
點擊切換tab標簽效果圖:
8、渲染添加參數按鈕並控制按鈕的禁用狀態
可以使用disabled
屬性來定義按鈕是否可用,它接受一個Boolean
值。
需要添加一個計算屬性,判斷selectedCateKeys的長度不等於3時返回一個布爾值,綁定到按鈕來禁用
<!--添加參數的按鈕--> <el-button type="primary" size="mini" :disabled="isBtnDisabled">添加參數</el-button> <!--添加屬性的按鈕--> <el-button type="primary" size="mini" :disabled="isBtnDisabled">添加屬性</el-button> <script> export default { computed: { // 計算屬性 // 如果按鈕需要被禁用 則返回true,否則返回false isBtnDisabled() { if (this.selectedCateKeys.length !== 3) { return true } return false } } } </script>
效果圖:
9、獲取分類參數列表數據
調用api的分類參數列表接口,請求路徑:categories/:id/attributes,請求方法:get,請求參數:sel [only,many] 不能為空,通過 only 或 many 來獲取分類靜態參數還是動態參數
因為請求參數sel 需要傳遞動態或者靜態,所以把Tabs標簽的name值改為相對應的many 和 only
<!--添加動態參數的面板--> <el-tab-pane label="動態參數" name="many"> <!--添加靜態屬性的面板--> <el-tab-pane label="靜態屬性" name="only"> // 被激活的標簽的名稱,默認為many activeName: 'many'
在級聯選擇框選中三級分類時,請求獲取分類參數列表數據,所以在cateChanged函數中添加代碼:
// 級聯選擇框選中項變化,會觸發這個函數 async cateChanged() { // 證明選中的不是三級分類 if (this.selectedCateKeys.length !== 3) { this.selectedCateKeys = [] return } // 證明選中的是三級分類 console.log(this.selectedCateKeys) // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) },
10、切換Tabs面板后,重新獲取參數列表數據
把根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表這些操作單獨為一個函數,然后級聯選擇框選中項變化和切換tabs標簽時都調用這個函數
// 級聯選擇框選中項變化,會觸發這個函數 cateChanged() { // 證明選中的不是三級分類 if (this.selectedCateKeys.length !== 3) { this.selectedCateKeys = [] return } // 證明選中的是三級分類 console.log(this.selectedCateKeys) this.getParamsList() }, // tab標簽的點擊事件處理函數 handleTabClick() { // console.log(this.activeName) this.getParamsList() }, // 獲取參數的列表數據 async getParamsList() { // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) }
11、將獲取到的參數列表數據掛載到對應的數據源上
在獲取到參數列表數據后,還要判斷是動態參數還是靜態屬性的,然后賦值給對應的數組:
manyTableData: [], // 動態參數的數據列表 onlyTableData: [] // 靜態屬性的數據列表 // 獲取參數的列表數據 async getParamsList() { // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) if (this.activeName === 'many') { this.manyTableData = res.data } else { this.onlyTableData = res.data } }
12、渲染動態參數和靜態屬性的Table表格
添加代碼:
<!--動態參數表格--> <el-table :data="manyTableData" border stripe> <!--展開列--> <el-table-column type="expand"> </el-table-column> <el-table-column type="index" label="#"></el-table-column> <el-table-column label="參數名稱" prop="attr_name"></el-table-column> <el-table-column label="操作"> <!-- 作用域插槽 --> <template slot-scope="scope"> <el-button size="mini" type="primary" icon="el-icon-edit">編輯</el-button> <el-button size="mini" type="danger" icon="el-icon-delete">刪除</el-button> </template> </el-table-column> </el-table> <!--靜態屬性表格--> <el-table :data="onlyTableData" border stripe> <!--展開列--> <el-table-column type="expand"> </el-table-column> <el-table-column type="index" label="#"></el-table-column> <el-table-column label="屬性名稱" prop="attr_name"></el-table-column> <el-table-column label="操作"> <!-- 作用域插槽 --> <template slot-scope="scope"> <el-button size="mini" type="primary" icon="el-icon-edit">編輯</el-button> <el-button size="mini" type="danger" icon="el-icon-delete">刪除</el-button> </template> </el-table-column> </el-table>
此時效果圖:
13、渲染添加參數的對話框
添加動態參數和靜態屬性,共用一個對話框,就需要添加計算屬性做一些判斷
先添加一個計算屬性函數:
// 動態計算添加參數對話框標題的文本 titleText() { if (this.activeName === 'many') { return '動態參數' } else { return '靜態屬性' } }
添加對話框代碼:
<!--參加參數的對話框--> <el-dialog :title="'添加' + titleText" :visible.sync="addDialogVisible" width="50%" @close="addDialogClosed"> <!--內容主體區域--> <el-form :model="addForm" :rules="addFormRules" ref="addFormRef" label-width="90px"> <el-form-item :label="titleText" prop="attr_name"> <el-input v-model="addForm.attr_name"></el-input> </el-form-item> </el-form> <!--底部按鈕區域--> <span slot="footer" class="dialog-footer"> <el-button @click="addDialogVisible = false">取 消</el-button> <el-button type="primary" @click="addDialogVisible = false">確 定</el-button> </span> </el-dialog> <script> export default { data() { return { addDialogVisible: false, // 控制添加參數對話框是否顯示 // 添加參數的表單數據對象 addForm: { attr_name: '' }, // 添加表單的驗證規則對象 addFormRules: { attr_name: [ { required: true, message: '請輸入參數名稱', trigger: 'blur' } ] } } }, methods: { // 監聽 添加參數對話框的關閉事件 addDialogClosed() { // 表單內容重置為空 this.$refs.addFormRef.resetFields() } } } </script>
點擊添加參數按鈕的效果圖:
14、完成動態參數和靜態屬性的添加操作
調用api的添加動態參數或者靜態屬性接口,請求路徑:categories/:id/attributes,請求方法:post,
請求參數:
attr_name 參數名稱 不能為空
attr_sel [only,many] 不能為空
ttr_vals 如果是 many 就需要填寫值的選項,以逗號分隔 【可選參數】
先填寫要添加的參數名稱,然后點擊確定按鈕做表單的預校驗,當預校驗成功后,發起網絡請求,向服務添加對應的參數
先給確定按鈕添加點擊事件:
<el-button type="primary" @click="addParams">確 定</el-button>
addParams事件函數:
// 點擊確認 添加新的參數 addParams() { // console.log(this.addForm) this.$refs.addFormRef.validate(async valid => { // 預校驗 if (!valid) return const { data: res } = await this.$http.post( `categories/${this.cateId}/attributes`, { attr_name: this.addForm.attr_name, attr_sel: this.activeName } ) if (res.meta.status !== 201) { return this.$message.error('添加參數失敗!') } this.$message.success('添加參數成功!') this.getParamsList() this.addDialogVisible = false }) }
效果圖:
15、渲染編輯修改參數的對話框
給編輯按鈕添加點擊事件:
<el-button size="mini" type="primary" icon="el-icon-edit" @click="showEditDialog">編輯</el-button>
// 監聽 展示編輯參數的對話框 showEditDialog(id) { this.editDialogVisible = true }
復制添加參數對話框的代碼,修改為編輯對話框:
<!--編輯參數的對話框--> <el-dialog :title="'編輯' + titleText" :visible.sync="editDialogVisible" width="50%" @close="editDialogClosed" > <!--內容主體區域--> <el-form :model="editForm" :rules="editFormRules" ref="editFormRef" label-width="90px"> <el-form-item :label="titleText" prop="attr_name"> <el-input v-model="editForm.attr_name"></el-input> </el-form-item> </el-form> <!--底部按鈕區域--> <span slot="footer" class="dialog-footer"> <el-button @click="editDialogVisible = false">取 消</el-button> <el-button type="primary" @click="editParams">確 定</el-button> </span> </el-dialog> <script> export default { data() { return { editDialogVisible: false, // 控制編輯參數對話框是否顯示 // 編輯參數的表單數據對象 editForm: {} } }, methods: { // 監聽 展示編輯參數的對話框 showEditDialog() { this.editDialogVisible = true }, // 監聽 編輯參數對話框的關閉事件 editDialogClosed() { // 表單內容重置為空 this.$refs.editFormRef.resetFields() }, // 點擊確認 編輯修改參數 editParams() { } } } </script>
16、完成修改參數的操作
先調用api的根據 ID 查詢參數接口,請求路徑:categories/:id/attributes/:attrId,請求方法:get,
請求參數:
attr_sel [only,many] 不能為空
attr_vals 如果是 many 就需要填寫值的選項,以逗號分隔
修改編輯按鈕:
<el-button size="mini" type="primary" icon="el-icon-edit" @click="showEditDialog(scope.row.attr_id)">編輯</el-button>
完善showEditDialog代碼:
// 監聽 展示編輯參數的對話框 async showEditDialog(attrId) { const { data: res } = await this.$http.get(`categories/${this.cateId}/attributes/${attrId}`, { params: { attr_sel: this.activeName } }) if (res.meta.status !== 200) { return this.$message.error('查詢參數信息失敗') } this.editForm = res.data this.editDialogVisible = true },
修改參數后,需要調用api的編輯提交參數接口,請求路徑:categories/:id/attributes/:attrId,請求方法:put,
請求參數:
attr_name 新屬性的名字 不能為空,攜帶在`請求體`中
attr_sel 屬性的類型[many或only] 不能為空,攜帶在`請求體`中
attr_vals 參數的屬性值 可選參數,攜帶在`請求體`中
點擊確定按鈕做表單的預校驗,當預校驗成功后,發起網絡請求,向服務提交修改的參數:
// 點擊確認 編輯修改參數 editParams() { this.$refs.editFormRef.validate(async valid => { if (!valid) return // 可以發起修改參數信息的網絡請求 const { data: res } = await this.$http.put( `categories/${this.cateId}/attributes/${this.editForm.attr_id}`, { attr_name: this.editForm.attr_name, attr_sel: this.activeName }) if (res.meta.status !== 200) { return this.$message.error('編輯參數信息失敗!') } this.$message.success('編輯參數信息成功!') this.getParamsList() this.editDialogVisible = false }) }
效果圖:
17、完成刪除參數的操作
給刪除按鈕添加點擊事件:
<el-button size="mini" type="danger" icon="el-icon-delete" @click="delParamsDialog(scope.row.attr_id)">刪除</el-button>
調用api的刪除參數接口,請求路徑: categories/:id/attributes/:attrid,請求方法:delete
// 根據id刪除參數對話框 async delParamsDialog(arrtId) { // console.log(arrtId) // 彈框 詢問用戶是否刪除 const confirmResult = await this.$confirm('此操作將永久刪除該參數, 是否繼續?', '提示', { confirmButtonText: '確定', cancelButtonText: '取消', type: 'warning' }).catch(err => err) // 如果用戶確認刪除,則返回值為字符串 confirm // 如果用戶取消刪除,則返回值為字符串 cancel // console.log(confirmResult) if (confirmResult !== 'confirm') { return this.$message.info('已取消刪除') } // console.log('確認刪除') // 發起刪除參數的網絡請求 const { data: res } = await this.$http.delete(`categories/${this.cateId}/attributes/${arrtId}`) if (res.meta.status !== 200) { return this.$message.error('刪除參數信息失敗!') } this.$message.success('刪除參數信息成功!') this.getParamsList() }
效果圖:
18、渲染參數下的可選項
后台返回的數據中attr_vals字段參數給的是字符串類型,不能進行循環渲染,所以要進行改造:
循環data中的每一項,把attr_vals參數的字符串,重新賦值為attr_vals數組,在進行for循環渲染
修改getParamsList函數,在獲取所有參數項后,以空格分隔attr_vals:
// 獲取參數的列表數據 async getParamsList() { // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) // 循環data中的每一項,把attr_vals參數的字符串,重新賦值為item.attr_vals數組 res.data.forEach(item => { item.attr_vals = item.attr_vals.split(' ') }) if (this.activeName === 'many') { this.manyTableData = res.data } else { this.onlyTableData = res.data } },
然后在展開列中進行for循環渲染;
<!--展開列--> <el-table-column type="expand"> <template slot-scope="scope"> <el-tag v-for="(item, i) in scope.row.attr_vals" :key="i" closable>{{item}}</el-tag> </template> </el-table-column>
此時點擊展開列的效果圖:
19、解決attr_vals字段為空字符時的小bug
當attr_vals字段為空時,會顯示一個帶X的空tag標簽,因為空字符串以空格分割時,會返回一個數組,包含一個空字符串,所以就會渲染出一個空白的tag標簽
還是在getParamsList函數中,加一個判斷:
// 獲取參數的列表數據 async getParamsList() { // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) // 循環data中的每一項,把attr_vals參數的字符串,重新賦值為item.attr_vals數組 res.data.forEach(item => { // if (item.attr_vals.length === 0) return // item.attr_vals = item.attr_vals.split(' ') item.attr_vals = item.attr_vals ? item.attr_vals.split(' ') : [] }) if (this.activeName === 'many') { this.manyTableData = res.data } else { this.onlyTableData = res.data } },
20、控制按鈕與文本框的切換顯示
添加代碼:
<!--輸入文本框--> <el-input class="input-new-tag" v-if="inputVisible" v-model="inputValue" ref="saveTagInput" size="small" @keyup.enter.native="handleInputConfirm" @blur="handleInputConfirm"></el-input> <!--添加的按鈕--> <el-button v-else class="button-new-tag" size="small" @click="showInput">+ New Tag</el-button> <script> export default { data() { return { inputVisible: false, // 控制按鈕與文本框的切換顯示 inputValue: '' // 文本框中輸入的內容 } }, methods: { // 文本框失去焦點或按下回車鍵時都會觸發 handleInputConfirm() { console.log('ok') }, // 點擊按鈕展示文本輸入框 showInput() { this.inputVisible = true } } } </script> <style lang="less" scoped> .input-new-tag { width: 120px; } </style>
@keyup.enter.native 表示按下鍵盤的回車鍵
@blur 表示失去焦點的時候
21 、為每一行數據提供單獨的inputVisible和inputValue
在獲取所有參數的getParamsList函數中給每個item單獨添加:
// 獲取參數的列表數據 async getParamsList() { // 根據所選分類的id 和當前所處的面板,獲取對應的參數數據列表 const { data: res } = await this.$http.get( `categories/${this.cateId}/attributes`, { params: { sel: this.activeName } } ) if (res.meta.status !== 200) { return this.$message.error('獲取參數列表失敗') } console.log(res.data) // 循環data中的每一項,把attr_vals參數的字符串,重新賦值為item.attr_vals數組 res.data.forEach(item => { // if (item.attr_vals.length === 0) return // item.attr_vals = item.attr_vals.split(' ') item.attr_vals = item.attr_vals ? item.attr_vals.split(' ') : [] // 控制文本框的顯示與隱藏 item.inputVisible = false // 文本框中輸入的值 item.inputValue = '' }) if (this.activeName === 'many') { this.manyTableData = res.data } else { this.onlyTableData = res.data } },
記得要把data里定義的inputVisible和inputValue刪除掉,因為這里已經定義了。
然后修改代碼:
<!--輸入文本框--> <el-input class="input-new-tag" v-if="scope.row.inputVisible" v-model="scope.row.inputValue" ref="saveTagInput" size="small" @keyup.enter.native="handleInputConfirm" @blur="handleInputConfirm"></el-input> <!--添加的按鈕--> <el-button v-else class="button-new-tag" size="small" @click="showInput(scope.row)">+ New Tag</el-button>
showInput函數修改:
// 點擊按鈕展示文本輸入框 showInput(row) { row.inputVisible = true }
現在就不會聯動了,效果圖:
22、讓文本框自動獲得焦點
在showInput函數里添加代碼:
// 點擊按鈕展示文本輸入框 showInput(row) { row.inputVisible = true // 讓文本框自動獲得焦點 // $nextTick 方法的作用:就是當頁面上元素被重新渲染之后,才會執行回調中的代碼 this.$nextTick(_ => { this.$refs.saveTagInput.$refs.input.focus() }) }
23、實現文本框與按鈕的切換顯示
修改代碼:
<!--輸入文本框--> <el-input class="input-new-tag" v-if="scope.row.inputVisible" v-model="scope.row.inputValue" ref="saveTagInput" size="small" @keyup.enter.native="handleInputConfirm(scope.row)" @blur="handleInputConfirm(scope.row)"></el-input>
handleInputConfirm函數添加代碼:
// 文本框失去焦點或按下回車鍵時都會觸發 handleInputConfirm(row) { // trim() 去除字符串兩端的空格 if (row.inputValue.trim().length === 0) { row.inputValue = '' row.inputVisible = false return } // 如果沒有return,則證明輸入的內容,需要做后續處理 console.log('ok') },
24、完成參數可選項的添加操作
先把row.inputValue的值push到row.attr_vals中,然后發起網絡請求
調用api的編輯提交參數接口,請求路徑:categories/:id/attributes/:attrId,請求方法:put
請求參數:
attr_name 新屬性的名字 不能為空,攜帶在`請求體`中
attr_sel 屬性的類型[many或only] 不能為空,攜帶在`請求體`中
attr_vals 參數的屬性值 可選參數,攜帶在`請求體`中
繼續完善handleInputConfirm函數:
// 文本框失去焦點或按下回車鍵時都會觸發 async handleInputConfirm(row) { // trim() 去除字符串兩端的空格 if (row.inputValue.trim().length === 0) { row.inputValue = '' row.inputVisible = false return } // 如果沒有return,則證明輸入的內容,需要做后續處理 row.attr_vals.push(row.inputValue.trim()) row.inputValue = '' row.inputVisible = false // 發起請求保存操作 const { data: res } = await this.$http.put( `categories/${this.cateId}/attributes/${row.attr_id}`, { attr_name: row.attr_name, attr_sel: row.attr_sel, attr_vals: row.attr_vals.join(' ') } ) if (res.meta.status !== 200) { return this.$message.error('添加修改參數項失敗!') } this.$message.success('添加修改參數項成功!') },
此時效果圖:
25、刪除參數下的可選項
給el-tag標簽綁定close事件:
<!--循環渲染tag標簽--> <el-tag v-for="(item, i) in scope.row.attr_vals" :key="i" closable @close="handleClosed(scope.row, i)">{{item}}</el-tag>
函數handleClosed:
// 根據索引刪除對應參數的可選項 async handleClosed(row, i) { // console.log(row) // console.log(i) row.attr_vals.splice(i, 1) // 發起請求保存操作 const { data: res } = await this.$http.put( `categories/${this.cateId}/attributes/${row.attr_id}`, { attr_name: row.attr_name, attr_sel: row.attr_sel, attr_vals: row.attr_vals.join(' ') } ) if (res.meta.status !== 200) { return this.$message.error('添加修改參數項失敗!') } this.$message.success('添加修改參數項成功!') }
發現保存操作的代碼重復了,可以單獨提出來寫一個函數,獨立出來后記得把上面的handleInputConfirm函數也修改下:
// 文本框失去焦點或按下回車鍵時都會觸發 handleInputConfirm(row) { // trim() 去除字符串兩端的空格 if (row.inputValue.trim().length === 0) { row.inputValue = '' row.inputVisible = false return } // 如果沒有return,則證明輸入的內容,需要做后續處理 row.attr_vals.push(row.inputValue.trim()) row.inputValue = '' row.inputVisible = false // 發起請求保存操作 this.saveAttrVals(row) }, // 將對 attr_vals 的操作保存到數據庫 async saveAttrVals(row) { // 發起請求保存操作 const { data: res } = await this.$http.put( `categories/${this.cateId}/attributes/${row.attr_id}`, { attr_name: row.attr_name, attr_sel: row.attr_sel, attr_vals: row.attr_vals.join(' ') } ) if (res.meta.status !== 200) { return this.$message.error('添加修改參數項失敗!') } this.$message.success('添加修改參數項成功!') }, // 根據索引刪除對應參數的可選項 handleClosed(row, i) { // console.log(row) // console.log(i) row.attr_vals.splice(i, 1) // 發起請求保存操作 this.saveAttrVals(row) }
效果圖:
26、小bug清空表格數據
因為我們設置了只允許選中三級分類,但是當選中三級分類后,又選中二級分類時,下面表格中的三級數據還有顯示。
修改cateChanged函數:
// 級聯選擇框選中項變化,會觸發這個函數 cateChanged() { // 證明選中的不是三級分類 if (this.selectedCateKeys.length !== 3) { this.selectedCateKeys = [] this.manyTableData = [] this.onlyTableData = [] return } // 證明選中的是三級分類 console.log(this.selectedCateKeys) this.getParamsList() },
27、完成靜態屬性表格中的展開列效果
把動態參數的展開列代碼,復制一份,粘貼到靜態屬性的展開列中就可以了。
<!--展開列--> <el-table-column type="expand"> <template slot-scope="scope"> <!--循環渲染tag標簽--> <el-tag v-for="(item, i) in scope.row.attr_vals" :key="i" closable @close="handleClosed(scope.row, i)">{{item}}</el-tag> <!--輸入文本框--> <el-input class="input-new-tag" v-if="scope.row.inputVisible" v-model="scope.row.inputValue" ref="saveTagInput" size="small" @keyup.enter.native="handleInputConfirm(scope.row)" @blur="handleInputConfirm(scope.row)" > </el-input> <!--添加的按鈕--> <el-button v-else class="button-new-tag" size="small" @click="showInput(scope.row)">+ New Tag</el-button> </template> </el-table-column>
ok,測試可以沒問題。
28、將本地goods_params分支的代碼推送到遠程
查看分支:
git branch
查看狀態:
git status
保存到暫存區:
git add .
提交到本地倉庫:
git commit -m "完成了分類參數的開發"
推送到遠程:
git push
合並到master:
git checkout master
git merge goods_params
git push