linwenxin 1 rok pred
rodič
commit
544c71759e

+ 17 - 0
src/api/coupon.js

@@ -1,5 +1,22 @@
 import request from '@/utils/request'
 
+export function couponListPageV2(data) {
+  return request({
+    url: `/coupon/list/pageV2?moduleId=${data.moduleId}`,
+    method: 'post',
+    data
+  })
+}
+
+export function couponListPageV2Export(data, name) {
+  return postBlob({
+    url: '/coupon/list/pageV2Export',
+    data,
+    name
+  })
+}
+
+
 // 获取优惠券列表
 export function getList(params) {
   return request({

+ 1 - 2
src/layout/components/Sidebar/SidebarItem.vue

@@ -1,13 +1,12 @@
 <template>
   <div v-if="!item.hidden || item.noShowingChildren">
-    <template v-if="!item.children || !item.children.length">
+    <template v-if="item.type == 2 || (!item.children || !item.children.length)">
       <app-link v-if="item.meta" :to="item.path">
         <el-menu-item :index="item.path" :class="{ 'submenu-title-noDropdown': !isNest }">
           <item :icon="item.meta.icon || (item.meta && item.meta.icon)" :title="item.meta.title" />
         </el-menu-item>
       </app-link>
     </template>
-
     <el-submenu v-else ref="subMenu" :index="item.path" popper-append-to-body>
       <template slot="title">
         <item v-if="item.meta" :icon="item.meta && item.meta.icon" :title="item.meta.title" />

+ 4 - 1
src/permission.js

@@ -104,9 +104,12 @@ function buildRoute(route, parentUrl = '', bool=true) {
       } catch (e) {
         console.log(e)
       }
+      if(route.children && route.children.length){
+        item.children = route.children.filter(item => item.type !== 3).map(child => buildRoute(child, parentUrl, bool))
+      }
       const roles = []
       const roleItems = []
-      for (var role of route.children) {
+      for (var role of route.children.filter(item => item.type == 3)) {
         roleItems.push({
           code: role.code,
           moduleName: role.moduleName

+ 81 - 17
src/views/mallManagement/activity/coupon_index/index.vue

@@ -21,6 +21,7 @@
 import TemplatePage from '@/components/template/template-page-1.vue'
 import import_mixin from '@/components/template/import_mixin.js'
 import { required, mobileRequired, mobile } from '@/components/template/rules_verify.js'
+import { couponListPageV2, couponListPageV2Export, addCoupon, changeCouponFlag, editCoupon, getCouponDetail, getClassifyList, getGoodsList, getTagList, getMemberList, reissueCoupon } from "@/api/coupon";
 import { storageListPageV2, storagePageExport, addStorage, deleteStorage, editStorage, getList, getStorageDetail } from "@/api/storage";
 export default {
   components: { TemplatePage },
@@ -59,6 +60,7 @@ export default {
         storageMobile: '',
         storageAddress: '',
       },
+      tagList:[]
     }
   },
   computed: {
@@ -73,38 +75,89 @@ export default {
         name: 'el-input',
         attributes: { placeholder: '请输入' },
         formItemAttributes: {
-          label: '仓储名称',
-          prop: 'storageName',
+          label: '优惠券名称',
+          prop: 'couponName',
           rules: [...required]
         }
-      }, {
+      }, 
+      {
         md: 24,
         isShow: true,
-        name: 'el-input',
-        attributes: { placeholder: '请输入' },
+        name: 'el-radio',
+        options: [{ label: "满减券", value: "SATISFY" }, { label: "商品券", value: "GOODS" }],
+        attributes: { filterable: true, placeholder: '请选择' },
         formItemAttributes: {
-          label: '仓储电话',
-          prop: 'storageMobile',
-          rules: [...mobile]
+          label: '优惠券类型',
+          prop: 'couponType',
+          rules: []
         }
-      }, {
+      },
+      {
         md: 24,
         isShow: true,
-        name: 'el-input',
-        attributes: { placeholder: '请输入' },
+        name: 'el-radio',
+        options: [
+          { label: "所有用户", value: 0 }, 
+          { label: "所有会员", value: 4 },
+          { label: "所有业务员", value: 3 },
+          { label: "指定标签", value: 2 },
+          { label: "指定会员", value: 1 },
+        ],
+        attributes: { filterable: true, placeholder: '请选择' },
         formItemAttributes: {
-          label: '仓储地址',
-          prop: 'storageAddress',
+          label: '领取条件',
+          prop: 'receiveCrowd',
           rules: []
         }
-      }]
+      },
+      {
+        md: 24,
+        isShow: true,
+        name: 'el-select',
+        options: this.tagList,
+        attributes: { filterable: true, placeholder: '请选择', disabled:this.formData.flag === 'START' },
+        formItemAttributes: {
+          label: '选择标签',
+          prop: 'tagValue',
+          rules: []
+        }
+      },
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      
+      ]
     }
   },
   methods: {
     // 列表请求函数
-    getList: storageListPageV2,
+    getList: couponListPageV2,
     // 列表导出函数
-    exportList: storagePageExport,
+    exportList: couponListPageV2Export,
     // 表格列解析渲染数据更改
     columnParsing(defaultData) {
       return defaultData
@@ -143,7 +196,18 @@ export default {
       this.openForm()
     },
     openForm() {
-      this.formDialog = true;
+      getTagList({
+        pageNum: 1,
+        pageSize: -1,
+      }).then(res => {
+        this.tagList = res.data.records.map(item=>({
+          label: item.name,
+          value: item.tagId,
+          data: item
+        }));
+        this.formDialog = true;
+      })
+      
     },
     formCancel() {
       this.$refs.formRef.$refs.inlineForm.clearValidate()

+ 1417 - 0
src/views/mallManagement/goods/goods_index/goods_add/index.vue

@@ -0,0 +1,1417 @@
+<template>
+  <div class="app-container">
+
+    <div class="step-container">
+      <el-steps :active="step" simple style="margin-top: 20px">
+        <el-step title="1.编辑基础信息" ></el-step>
+        <el-step title="2.编辑价格库存" ></el-step>
+        <el-step title="3.编辑商品详情" ></el-step>
+      </el-steps>
+    </div>
+
+    <!-- 第一步 -->
+    <div class="form-container" v-show="step == 0">
+      <div class="title">基础信息</div>
+      <el-form ref="step1Form" :model="step1Form" :rules="step1FormRules" label-width="110px">
+        <el-form-item label="商品名称:" prop="goodsName">
+          <el-input v-model="step1Form.goodsName" placeholder="请输入商品名称" maxlength="200" show-word-limit></el-input>
+        </el-form-item>
+        <el-form-item label="商品描述:" prop="goodsDes">
+          <el-input v-model="step1Form.goodsDes" type="textarea" placeholder="请输入商品描述" :autosize="{ minRows: 3, maxRows: 6}" maxlength="100" show-word-limit></el-input>
+        </el-form-item>
+        <el-form-item label="商品主图:" prop="imgUrl">
+          <el-upload
+            class="avatar-uploader"
+            style="height:122px"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            :show-file-list="false"
+            :on-success="uploadSuccess"
+            :before-upload="beforeUpload">
+            <img v-if="step1Form.imgUrl" :src="step1Form.imgUrl" class="avatar">
+            <i v-else class="el-icon-plus avatar-uploader-icon"></i>
+          </el-upload>
+          <div class="tips">
+            <span>建议尺寸:800*800</span>
+          </div>
+        </el-form-item>
+        <el-form-item label="轮播图:" prop="images">
+          <el-upload
+            multiple
+            :limit="6"
+            ref="imageListUpload2"
+            class="avatar-uploader2 imageListUpload2"
+            style="height: 0;"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            name="file"
+            :show-file-list="false"
+            :on-success="uploadSuccess2"
+            :on-exceed="uploadExceed2"
+            :before-upload="beforeUpload2">
+          </el-upload>
+          <div class="images">
+            <div class="item" v-for="(item, index) in step1Form.images" :key="index">
+              <div class="img">
+                <el-image ref="img" :src="item.url" style="width: 120px; height: 120px" fit="cover"></el-image>
+                <div class="mask">
+                  <div class="row">
+                    <div class="it" @click="uploadImage(item.id)"><i class="el-icon-upload2"></i></div>
+                    <div class="it" @click="deleteImage(index)"><i class="el-icon-delete"></i></div>
+                  </div>
+                  <div class="row">
+                    <div class="it" @click="moveForward(index)"><i class="el-icon-back"></i><span>前移</span></div>
+                    <div class="it" @click="moveBack(index)"><span>后移</span><i class="el-icon-right"></i></div>
+                  </div>
+                </div>
+              </div>
+            </div>
+            <div class="item">
+              <div class="add" @click="uploadImage(0)">
+                <i class="el-icon-plus avatar-uploader-icon"></i>
+              </div>
+            </div>
+          </div>
+          <div class="tips" style="margin-top: 0;">
+            <span>建议尺寸:800*800,最多上传6张</span>
+          </div>
+        </el-form-item>
+
+        <el-form-item label="商品视频:" prop="videoUrl">
+          <el-upload
+            class="avatar-uploader"
+            style="height:122px"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            :show-file-list="false"
+            :on-success="uploadSuccess3"
+            :before-upload="beforeUpload3">
+            <!-- <img v-if="step1Form.videoUrl" :src="step1Form.videoUrl" class="avatar"> -->
+            <video v-if="step1Form.videoUrl" :src="step1Form.videoUrl" height="120" style="display: block;"></video>
+            <i v-else class="el-icon-plus avatar-uploader-icon"></i>
+          </el-upload>
+          <div class="tips">
+            <span>建议视频宽高比:16:9,建议时长9-30秒</span>
+          </div>
+        </el-form-item>
+
+        <!-- <el-form-item label="水印图片:" prop="logoUrl">
+          <el-upload
+            class="avatar-uploader"
+            style="height:122px"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            :show-file-list="false"
+            :on-success="uploadSuccess7"
+            :before-upload="beforeUpload7">
+            <img v-if="step1Form.logoUrl" :src="step1Form.logoUrl" class="avatar">
+            <i v-else class="el-icon-plus avatar-uploader-icon"></i>
+          </el-upload>
+        </el-form-item> -->
+
+        <!-- <el-form-item label="水印显示日期:" prop="showDate">
+          <el-date-picker
+            v-model="step1Form.showDate"
+            style="width: 300px"
+            type="daterange"
+            value-format="yyyy-MM-dd"
+            range-separator="至"
+            start-placeholder="开始日期"
+            end-placeholder="结束日期"
+            clearable>
+          </el-date-picker>
+        </el-form-item> -->
+
+        <el-form-item label="商品分类:" prop="classify">
+          <el-cascader
+            placeholder="请选择商品分类"
+            :options="classifyList"
+            :props="{ value: 'categoryId', label:'name' }"
+            v-model="step1Form.classify"
+            style="width: 300px"
+            @change="changeClassify()"
+            filterable
+            clearable>
+          </el-cascader>
+        </el-form-item>
+
+        <el-form-item label="营销活动:" prop="marketing">
+          <el-select v-model="step1Form.marketing" placeholder="请选择营销活动" style="width: 300px" clearable :disabled="!step1Form.classify">
+            <el-option
+              v-for="item in marketingList"
+              :key="item.id"
+              :label="item.name"
+              :value="item.id">
+            </el-option>
+          </el-select>
+        </el-form-item>
+
+        <el-form-item label="商品属性:" prop="attrs">
+          <el-select v-model="step1Form.attrs" multiple placeholder="请选择商品属性" clearable style="width: 300px">
+            <el-option v-for="item in attrList" :key="item" :label="item" :value="item"></el-option>
+          </el-select>
+        </el-form-item>
+
+        <el-form-item label="商品标签:" prop="tags">
+          <el-select v-model="step1Form.tags" multiple placeholder="请选择商品标签" clearable style="width: 300px">
+            <el-option v-for="item in tagList" :key="item" :label="item" :value="item"></el-option>
+          </el-select>
+        </el-form-item>
+      </el-form>
+    </div>
+
+    <!-- 第二步 -->
+    <div class="form-container" v-show="step == 1">
+      <div class="title">价格库存</div>
+      <el-form ref="step2Form" :model="step2Form" :rules="step2FormRules" label-width="140px">
+        <el-form-item label="规格类型:" prop="specType">
+          <el-radio-group v-model="step2Form.specType" @change="changeSpecType">
+            <el-radio :label="false">无</el-radio>
+            <el-radio :label="true">多规格商品</el-radio>
+          </el-radio-group>
+        </el-form-item>
+
+
+        <el-form-item label="商品规格:">
+          <div class="container">
+            <el-form ref="specForm" :model="specForm" size="small" label-position="top">
+              <el-row :gutter="20">
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="规格名称" prop="name" label-position="top">
+                    <el-input v-model="specForm.name" placeholder="请输入规格名称" :disabled="!step2Form.specType"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="规格值" prop="specValue">
+                    <el-input v-model="specForm.specValue" placeholder="请输入规格值" :disabled="!step2Form.specType"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="库存" prop="stockNum">
+                    <el-input v-model="specForm.stockNum" placeholder="请输入库存"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="物料编号" prop="goodsCode">
+                    <el-input v-model="specForm.goodsCode" placeholder="请输入物料编号"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="成本价" prop="costPrice">
+                    <el-input v-model="specForm.costPrice" placeholder="请输入成本价"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="销售价" prop="price">
+                    <el-input v-model="specForm.price" placeholder="请输入销售价"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="佣金" prop="shareAmount">
+                    <el-input v-model="specForm.shareAmount" placeholder="请输入佣金"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="佣金比例(%)" prop="sharePercent">
+                    <el-input v-model="specForm.sharePercent" placeholder="请输入佣金比例"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="内部佣金" prop="innerShareAmount">
+                    <el-input v-model="specForm.innerShareAmount" placeholder="请输入内部佣金"></el-input>
+                  </el-form-item>
+                </el-col>
+                <el-col :xs="24" :sm="12" :lg="6">
+                  <el-form-item label="内部佣金比例(%)" prop="innerSharePercent">
+                    <el-input v-model="specForm.innerSharePercent" placeholder="请输入内部佣金比例"></el-input>
+                  </el-form-item>
+                </el-col>
+
+                <el-col :xs="24" :sm="24" :lg="24">
+                  <el-form-item label="规格图片" prop="imgUrl">
+                    <el-upload
+                      class="avatar-uploader"
+                      :action="baseURL + 'common/upload'"
+                      :headers="myHeaders"
+                      :show-file-list="false"
+                      :on-success="uploadSuccess5"
+                      :before-upload="beforeUpload5">
+                      <img v-if="specForm.imgUrl" :src="specForm.imgUrl" class="avatar">
+                      <i v-else class="el-icon-plus avatar-uploader-icon"></i>
+                    </el-upload>
+                  </el-form-item>
+                </el-col>
+              </el-row>
+            </el-form>
+          </div>
+          <div class="addBtn"><el-button type="primary" size="small" @click="addSpec" v-show="step2Form.specType">添加规格</el-button></div>
+
+          <el-upload
+            class="editSpecimage-uploader"
+            style="height: 0;"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            :show-file-list="false"
+            :on-success="uploadSuccess6"
+            :before-upload="beforeUpload5">
+          </el-upload>
+          <el-table :data="specList" element-loading-text="Loading" border fit highlight-current-row stripe style="margin-bottom: 20px" v-show="step2Form.specType">
+            <el-table-column align="center" label="规格名称" prop="name" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.name"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="规格值" prop="specValue" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.specValue"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="规格图片" prop="imgUrl">
+              <template slot-scope="scope">
+                <el-image style="width: 40px; height: 40px; cursor: pointer;" :src="scope.row.imgUrl" fit="cover" @click="editSpecImage(scope.$index)"></el-image>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="成本价" prop="costPrice" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.costPrice"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="销售价" prop="price" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.price" @change="changeGoodsPrice"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="佣金" prop="shareAmount" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.shareAmount"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="佣金比例(%)" prop="sharePercent" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.sharePercent"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="内部佣金" prop="innerShareAmount" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.innerShareAmount"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="内部佣金比例(%)" prop="innerSharePercent" min-width="130">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.innerSharePercent"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="库存" prop="stockNum" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.stockNum"></el-input>
+              </template>
+            </el-table-column>
+            <el-table-column align="center" label="物料编号" prop="goodsCode" min-width="120">
+              <template slot-scope="scope">
+                <el-input v-model="scope.row.goodsCode"></el-input>
+              </template>
+            </el-table-column>
+
+            <el-table-column align="center" label="操作">
+              <template slot-scope="scope">
+                <!-- <el-button type="text" @click="editExam('theory', scope.row.index)">编辑</el-button> -->
+                <el-popconfirm title="确定删除吗?" @onConfirm="deleteSpec(scope.row.index)" >
+                  <el-button slot="reference" type="text">删除</el-button>
+                </el-popconfirm>
+              </template>
+            </el-table-column>
+          </el-table>
+        </el-form-item>
+
+
+        <el-form-item label="商品价格:" prop="price">
+          <el-input v-model="step2Form.price" placeholder="请输入商品价格" class="small" readonly></el-input>
+        </el-form-item>
+        <el-form-item label="划线价格:" prop="oldPrice">
+          <el-input v-model="step2Form.oldPrice" placeholder="请输入划线价格" class="small"></el-input>
+          <div class="tips2">商品没有优惠的情况下,划线价在商品详情会以划线形式显示</div>
+        </el-form-item>
+        <!-- <el-form-item label="商品库存:" prop="stock">
+          <el-input v-model="step2Form.stock" placeholder="请输入商品库存" class="small"></el-input>
+          <div class="tips2">库存为 0 时,会放到【已售罄】的商品列表里,保存后买家看到的商品可售库存同步更新</div>
+        </el-form-item> -->
+        <el-form-item label="商品详情显示库存:" prop="showStock">
+          <el-radio-group v-model="step2Form.showStock">
+            <el-radio :label="true">显示</el-radio>
+            <el-radio :label="false">隐藏</el-radio>
+          </el-radio-group>
+        </el-form-item>
+        <el-form-item label="已售件数:" prop="sales">
+          <el-input v-model="step2Form.sales" placeholder="请输入已售件数" class="small"></el-input>
+          <div class="tips2">已售件数不计入后台数据统计</div>
+        </el-form-item>
+        <el-form-item label="商品详情显示销量:" prop="showSales">
+          <el-radio-group v-model="step2Form.showSales">
+            <el-radio :label="true">显示</el-radio>
+            <el-radio :label="false">隐藏</el-radio>
+          </el-radio-group>
+        </el-form-item>
+        <div class="title">其他设置</div>
+        <!-- <el-form-item label="快递运费:" prop="freight">
+          <el-radio-group v-model="step2Form.freight">
+            <el-radio label="0">运费模版</el-radio>
+            <el-radio label="1">统一运费</el-radio>
+          </el-radio-group>
+        </el-form-item> -->
+        <el-form-item label="运费模版:" prop="freight">
+          <el-select v-model="step2Form.freight" filterable placeholder="请选择运费模版" style="width: 300px">
+            <el-option v-for="item in freightList" :key="item.freightTemplateId" :label="item.name" :value="item.freightTemplateId">
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item label="商品状态:" prop="status">
+          <el-radio-group v-model="step2Form.status">
+            <el-radio :label="true">上架</el-radio>
+            <el-radio :label="false">下架</el-radio>
+          </el-radio-group>
+        </el-form-item>
+      </el-form>
+    </div>
+
+    <!-- 第三步 -->
+    <div class="form-container" v-show="step == 2">
+      <el-form ref="step3Form" :model="step3Form" :rules="step3FormRules" label-width="80px" label-position="top">
+        <el-form-item label="说明模块" prop="moduleId">
+          <el-select v-model="step3Form.moduleId" filterable placeholder="请选择说明模块" style="width: 300px">
+            <el-option v-for="item in moduleList" :key="item.commonTemplateId" :label="item.name" :value="item.commonTemplateId">
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item label="详情内容" prop="detailContent">
+          <el-upload
+            ref="imageListUpload"
+            class="avatar-uploader2 imageListUpload"
+            :action="baseURL + 'common/upload'"
+            :headers="myHeaders"
+            multiple
+            name="file"
+            :show-file-list="false"
+            :on-success="uploadSuccess4"
+            :on-error="uploadError4"
+            :before-upload="beforeUpload4">
+          </el-upload>
+          <!--富文本编辑器组件-->
+          <el-row v-loading="quillImgLoading">
+            <quill-editor
+              v-model="step3Form.detailContent"
+              ref="myQuillEditor"
+              :options="editorOption">
+            </quill-editor>
+          </el-row>
+        </el-form-item>
+      </el-form>
+    </div>
+
+
+    <div class="page-footer">
+      <div class="footer" :class="classObj">
+        <el-button @click="changeStep(0)" v-show="step > 0">上一步</el-button>
+        <el-button @click="changeStep(1)" v-show="step < 2">下一步</el-button>
+        <el-button type="primary" @click="clickSubmitForm" :loading="formLoading">{{ formLoading ? '提交中 ...' : '提 交' }}</el-button>
+        <el-popconfirm
+          title="确定关闭吗?"
+          @onConfirm="goBack"
+          style="margin-left: 10px;"
+        >
+          <el-button slot="reference">关 闭</el-button>
+        </el-popconfirm>
+      </div>
+    </div>
+
+  </div>
+</template>
+
+<script>
+import { getToken } from '@/utils/auth'
+import { getClassifyList, getFreightList, addGoods, editGoods, getGoodsDetail, getModuleList, getMarketingList, getTagList } from '@/api/goods'
+import { quillEditor } from 'vue-quill-editor'
+import 'quill/dist/quill.core.css'
+import 'quill/dist/quill.snow.css'
+import 'quill/dist/quill.bubble.css'
+
+// 工具栏配置
+const toolbarOptions = [
+  ['bold', 'italic', 'underline', 'strike'],
+  ['blockquote', 'code-block'],
+  [{'header': 1}, {'header': 2}],
+  [{'list': 'ordered'}, {'list': 'bullet'}],
+  [{'script': 'sub'}, {'script': 'super'}],
+  [{'indent': '-1'}, {'indent': '+1'}],
+  [{'direction': 'rtl'}],
+  [{'size': ['small', false, 'large', 'huge']}],
+  [{'header': [1, 2, 3, 4, 5, 6, false]}],
+  [{'color': []}, {'background': []}],
+  [{'font': []}],
+  [{'align': []}],
+  ['link', 'image', 'video'],
+  // ['clean']
+]
+
+export default {
+  components: {
+    quillEditor
+  },
+  data() {
+    return {
+      baseURL: process.env.VUE_APP_BASE_API,
+      myHeaders: {'x-token': getToken()},
+      isEdit: false,
+      editId: '',
+
+      step: 0,
+      step1Form: {
+        goodsName: '',
+        goodsDes: '',
+        imgUrl: '',
+        images: [],
+        videoUrl: '',
+        classify: '',
+        marketing: '',
+        attrs: [],
+        tags: [],
+        // logoUrl: '',
+        // showDate: [],
+      },
+      step1FormRules: {
+        goodsName: [
+          { required: true, message: '请填写商品名称', trigger: 'blur' }
+        ],
+        imgUrl: [
+          { required: true, message: '请上传商品主图', trigger: 'change' }
+        ],
+        images: [
+          { required: true, message: '请上传轮播图', trigger: 'change' }
+        ],
+        classify: [
+          { required: true, message: '请选择商品分类', trigger: 'change' }
+        ]
+      },
+      imagesList: [], // 图片墙展示列表
+
+      classifyList: [],
+      freightList: [],
+      moduleList: [],
+
+      step2Form: {
+        specType: true,
+        price: '',
+        oldPrice: '',
+        // stock: '',
+        showStock: true,
+        sales: '',
+        showSales: true,
+        freight: '',
+        status: true,
+      },
+      step2FormRules: {
+        specType: [
+          { required: true, message: '请选择规格类型', trigger: 'change' }
+        ],
+        freight: [
+          { required: true, message: '请选择运费模版', trigger: 'change' }
+        ],
+      },
+
+      step3Form: {
+        moduleId: '',
+        detailContent: '',
+      },
+      step3FormRules: {
+        detailContent: [
+          { required: true, message: '请输入详情内容', trigger: 'blur' }
+        ],
+      },
+
+      specForm: {
+        name: '',
+        specValue: '',
+        costPrice: '',
+        price: '',
+        shareAmount: '',
+        sharePercent: '',
+        innerShareAmount: '',
+        innerSharePercent: '',
+        stockNum: '',
+        goodsCode: '',
+        imgUrl: '',
+      },
+      specList: [],
+
+      quillImgLoading: false, // 富文本上传图片loading
+      editorOption: { // 富文本配置
+        placeholder: '请输入详情内容',
+        theme: 'snow',
+        modules: {
+          toolbar: {
+            container: toolbarOptions,
+            handlers: {
+              'image': function (value) {
+                if (value) {
+                  document.querySelector('.imageListUpload input').click()
+                } else {
+                  this.quill.format('image', false);
+                }
+              }
+            }
+          }
+        }
+      },
+
+      editorImages: [],
+
+      formLoading: false,
+
+      canChangeGoodsPrice: false,
+
+      uploadImageId: null,
+
+      editSpecImageIdx: null,
+
+      marketingList: [],
+
+      attrList: [],
+      tagList: [],
+
+      canCompute: false,
+    }
+  },
+  computed: {
+    sidebar() {
+      return this.$store.state.app.sidebar
+    },
+    classObj() {
+      return {
+        hideSidebar: !this.sidebar.opened,
+        openSidebar: this.sidebar.opened
+      }
+    },
+  },
+  watch: {
+    'specForm.costPrice': function(){
+      if(this.canCompute) {
+        this.computeShareAmount();
+      }
+    },
+    'specForm.price': function(){
+      this.changeGoodsPrice();
+      if(this.canCompute) {
+        this.computeShareAmount();
+      }
+    },
+    specList: function() {
+      this.changeGoodsPrice();
+    },
+  },
+  async created() {
+    const { id } = this.$route.query;
+    this.isEdit = id ? true : false;
+    this.editId = id;
+
+    await this.getClassifyList();
+
+    this.getTagList();
+
+    this.getFreightList();
+    this.getModuleList();
+
+    if(this.isEdit) {
+      this.canCompute = false;
+      this.getGoodsDetail(id);
+    }else {
+      this.canCompute = true;
+      this.canChangeGoodsPrice = true;
+    }
+
+  },
+  methods: {
+
+    async getClassifyList() {
+      return new Promise((resolve, reject) => {
+        let params = {
+          name: '',
+          categoryLevel: 1,
+          status: true
+        };
+        getClassifyList(params).then(res => {
+          this.classifyList = res.data;
+        }).finally(res => {
+          resolve();
+        })
+      })
+    },
+
+    getMarketingList() {
+      let classifyList = this.classifyList;
+      let categoryId = '';
+      this.classifyList.forEach(item => {
+        classifyList = classifyList.concat(item.children);
+      })
+      if(typeof this.step1Form.classify == 'string') {
+        categoryId = this.step1Form.classify;
+      }else {
+        categoryId = this.step1Form.classify[1];
+      }
+      let type = classifyList[this.$findElem(classifyList, 'categoryId', categoryId)].workOrderType;
+      getMarketingList({
+        type: type === "INSTALL" ? 1 : 2
+      }).then(res => {
+        this.marketingList = res.data;
+      })
+    },
+
+    getTagList() {
+      getTagList({
+        pageNum: 1,
+        pageSize: -1,
+        type: 1
+      }).then(res => {
+        let list = [];
+        res.data.records.forEach(item => {
+          list.push(item.goodsTagName);
+        });
+        this.attrList = list;
+      })
+
+      getTagList({
+        pageNum: 1,
+        pageSize: -1,
+        type: 2
+      }).then(res => {
+        let list = [];
+        res.data.records.forEach(item => {
+          list.push(item.goodsTagName);
+        });
+        this.tagList = list;
+      })
+    },
+
+    getFreightList() {
+      let params = {
+        pageNum: 1,
+        pageSize: 1000,
+        status: true
+      };
+      getFreightList(params).then(res => {
+        this.freightList = res.data.records;
+        console.log(this.freightList);
+      })
+    },
+
+    getModuleList() {
+      let params = {
+        pageNum: 1,
+        pageSize: 1000
+      };
+      getModuleList(params).then(res => {
+        this.moduleList = res.data.records;
+        console.log(this.moduleList);
+      })
+    },
+
+    // 获取详情
+    getGoodsDetail(goodsId) {
+      getGoodsDetail({goodsId}).then(res => {
+        let data = res.data;
+        this.step1Form = {
+          goodsName: data.goodsName,
+          goodsDes: data.describeText,
+          imgUrl: data.imgUrl,
+          videoUrl: data.vedio,
+          classify: data.categoryId,
+          marketing: data.marketingId,
+          attrs: data.tags,
+          tags: data.tagsLabel,
+          // logoUrl: data.logo,
+          // showDate: data.logoStartTime ? [data.logoStartTime.slice(0, 10), data.logoEndTime.slice(0, 10)] : [],
+        }
+        this.$set(this.step1Form, 'images', data.images);
+        this.getMarketingList();
+
+        this.step2Form = {
+          specType: data.hasSpec,
+          price: data.goodsPrice,
+          oldPrice: data.orgGoodsPrice,
+          showStock: data.showDetailStock,
+          showSales: data.showDetailSold,
+          sales: data.soldNum,
+          freight: data.freightTemplateId,
+          classify: data.categoryId,
+          status: data.status,
+        }
+
+        if(data.hasSpec) {
+          this.specList = data.goodsSpecs;
+          this.specList = this.listAddIndex(this.specList);
+        }else {
+          this.specForm = {
+            goodsSpecId: data.goodsSpecs[0].goodsSpecId,
+            name: data.goodsSpecs[0].name,
+            specValue: data.goodsSpecs[0].specValue,
+            costPrice: data.goodsSpecs[0].costPrice,
+            price: data.goodsSpecs[0].price,
+            shareAmount: data.goodsSpecs[0].shareAmount,
+            sharePercent: data.goodsSpecs[0].sharePercent,
+            innerShareAmount: data.goodsSpecs[0].innerShareAmount,
+            innerSharePercent: data.goodsSpecs[0].innerSharePercent,
+            stockNum: data.goodsSpecs[0].stockNum,
+            goodsCode: data.goodsSpecs[0].goodsCode,
+            imgUrl: data.goodsSpecs[0].imgUrl,
+          }
+        }
+
+        this.step3Form = {
+          moduleId: data.templateId,
+          detailContent: data.content
+        }
+
+        setTimeout(() => {
+          this.canChangeGoodsPrice = true;
+        }, 1000)
+
+        this.canCompute = true;
+
+      })
+    },
+
+    // 切换步骤
+    changeStep(type) {
+      if(type == 1) {
+        this.step ++;
+      }else {
+        this.step --;
+      }
+    },
+
+    changeClassify() {
+      this.step1Form.marketing = '';
+      this.getMarketingList();
+    },
+
+    // 将数组加上索引
+    listAddIndex(arr) {
+      arr.forEach((item, index) => {
+        item.index = index;
+      })
+      return arr;
+    },
+
+    // 切换规格类型
+    changeSpecType() {
+      if(this.specList.length > 0 && !this.step2Form.specType && this.specList[0].name != '默认') {
+        this.$errorMsg('请先删除规格');
+        this.step2Form.specType = true;
+        return false;
+      }
+      if(!this.step2Form.specType) {
+        this.specForm.name = '默认';
+        this.specForm.specValue = '默认';
+      }else {
+        this.specForm.name = '';
+        this.specForm.specValue = '';
+      }
+    },
+
+    // 添加规格
+    addSpec() {
+      if(!this.specForm.name) {
+        return this.$errorMsg('请填写规格名称');
+      } else if(!this.specForm.specValue) {
+        return this.$errorMsg('请填写规格值');
+      } else if(!this.specForm.costPrice) {
+        return this.$errorMsg('请填写成本价');
+      } else if(!this.specForm.price) {
+        return this.$errorMsg('请填写销售价');
+      } else if(this.specForm.shareAmount === '') {
+        return this.$errorMsg('请填写佣金');
+      } else if(this.specForm.shareAmount / this.specForm.price > 0.4) {
+        return this.$errorMsg('佣金不能超过销售价的40%');
+      } else if(this.specForm.innerShareAmount === '') {
+        return this.$errorMsg('请填写内部佣金');
+      } else if(this.specForm.innerShareAmount / this.specForm.price > 0.4) {
+        return this.$errorMsg('内部佣金不能超过销售价的40%');
+      } else if(this.specForm.sharePercent === '') {
+        return this.$errorMsg('请填写佣金比例');
+      } else if(Number(this.specForm.sharePercent) < 0 || Number(this.specForm.sharePercent) > 40) {
+        return this.$errorMsg('佣金比例范围0-40');
+      } else if(!this.specForm.stockNum) {
+        return this.$errorMsg('请填写库存');
+      } else if(!this.specForm.imgUrl) {
+        return this.$errorMsg('请上传规格图片');
+      }
+      let item = JSON.parse(JSON.stringify(this.specForm));
+      this.specList.push(item);
+      this.specList = this.listAddIndex(this.specList);
+      console.log(this.specList);
+    },
+
+    // 删除规格
+    deleteSpec(index) {
+      this.specList.splice(index, 1);
+      this.specList = this.listAddIndex(this.specList);
+    },
+
+    // 点击 提交表单
+    clickSubmitForm() {
+      // 验证第一步
+      this.$refs.step1Form.validate((valid) => {
+        if (valid) {
+          // if(this.step1Form.logoUrl && !this.step1Form.showDate) {
+          //   return this.$errorMsg('请选择水印显示日期');
+          // }
+          // 验证第二步
+          this.$refs.step2Form.validate((valid) => {
+            if (valid) {
+              // 验证第三步
+              this.$refs.step3Form.validate((valid) => {
+                if (valid) {
+                  this.submitForm();
+                }else {
+                  this.step = 2;
+                }
+              })
+            }else {
+              this.step = 1;
+            }
+          })
+        }else {
+          this.step = 0;
+        }
+      })
+    },
+
+    // 提交表单
+    submitForm() {
+      this.formLoading = true;
+
+      if(!this.step2Form.specType) {
+        if(!this.specForm.name) {
+          this.formLoading = false;
+          return this.$errorMsg('请填写规格名称');
+        } else if(!this.specForm.specValue) {
+          this.formLoading = false;
+          return this.$errorMsg('请填写规格值');
+        } else if(!this.specForm.costPrice) {
+          this.formLoading = false;
+          return this.$errorMsg('请填写成本价');
+        } else if(!this.specForm.price) {
+          this.formLoading = false;
+          return this.$errorMsg('请填写销售价');
+        } else if(this.specForm.shareAmount === '') {
+          this.formLoading = false;
+          return this.$errorMsg('请填写佣金');
+        } else if(this.specForm.sharePercent === '') {
+          this.formLoading = false;
+          return this.$errorMsg('请填写佣金比例');
+        } else if(this.specForm.shareAmount / this.specForm.price > 0.4) {
+          this.formLoading = false;
+          return this.$errorMsg('佣金不能超过销售价的40%');
+        } else if(Number(this.specForm.sharePercent) < 0 || Number(this.specForm.sharePercent) > 40) {
+          this.formLoading = false;
+          return this.$errorMsg('佣金比例范围0-40');
+        } else if(this.specForm.innerShareAmount === '') {
+          this.formLoading = false;
+          return this.$errorMsg('请填写内部佣金');
+        } else if(this.specForm.innerSharePercent === '') {
+          this.formLoading = false;
+          return this.$errorMsg('请填写内部佣金比例');
+        } else if(this.specForm.innerShareAmount / this.specForm.price > 0.4) {
+          this.formLoading = false;
+          return this.$errorMsg('内部佣金不能超过销售价的40%');
+        } else if(Number(this.specForm.innerSharePercent) < 0 || Number(this.specForm.innerSharePercent) > 40) {
+          this.formLoading = false;
+          return this.$errorMsg('内部佣金比例范围0-40');
+        } else if(!this.specForm.stockNum) {
+          this.formLoading = false;
+          return this.$errorMsg('请填写库存');
+        } else if(!this.specForm.imgUrl) {
+          this.formLoading = false;
+          return this.$errorMsg('请上传规格图片');
+        }
+        let item = JSON.parse(JSON.stringify(this.specForm));
+        this.specList.push(item);
+        this.specList = this.listAddIndex(this.specList);
+        console.log(this.specList);
+      }else {
+        let specList = this.specList;
+        for(let i=0; i<specList.length; i++) {
+          if(specList[i].shareAmount / specList[i].price > 0.4) {
+            this.formLoading = false;
+            this.$errorMsg('单个规格的佣金不能超过销售价的40%');
+            return;
+          }
+          if(Number(specList[i].sharePercent) < 0 || Number(specList[i].sharePercent) > 40) {
+            this.formLoading = false;
+            this.$errorMsg('单个规格的佣金比例范围在0-40');
+            return;
+          }
+          if(specList[i].innerShareAmount / specList[i].price > 0.4) {
+            this.formLoading = false;
+            this.$errorMsg('单个规格的佣金不能超过销售价的40%');
+            return;
+          }
+          if(Number(specList[i].innerSharePercent) < 0 || Number(specList[i].innerSharePercent) > 40) {
+            this.formLoading = false;
+            this.$errorMsg('单个规格的佣金比例范围在0-40');
+            return;
+          }
+        }
+      }
+
+      let images = [];
+      for(let i=0; i<this.step1Form.images.length; i++) {
+        let obj = {};
+        obj.id = this.step1Form.images[i].id;
+        images.push(obj);
+      }
+
+      let categoryId = '';
+      if(typeof this.step1Form.classify == 'string') {
+        categoryId = this.step1Form.classify;
+      }else {
+        categoryId = this.step1Form.classify[1];
+      }
+
+      let marketingName = '';
+      if(this.step1Form.marketing) {
+        marketingName = this.marketingList[this.$findElem(this.marketingList, 'id', this.step1Form.marketing)].name;
+      }
+
+      let params = {
+        goodsName: this.step1Form.goodsName,
+        describeText: this.step1Form.goodsDes,
+        imgUrl: this.step1Form.imgUrl,
+        images: images,
+        vedio: this.step1Form.videoUrl,
+        categoryId: categoryId,
+        marketingId: this.step1Form.marketing,
+        marketingName: marketingName,
+        tags: this.step1Form.attrs,
+        tagsLabel: this.step1Form.tags,
+        // logo: this.step1Form.logoUrl,
+        // logoStartTime: this.step1Form.showDate && this.step1Form.showDate.length ? this.step1Form.showDate[0] + ' 00:00:00' : '',
+        // logoEndTime: this.step1Form.showDate && this.step1Form.showDate.length ? this.step1Form.showDate[1] + ' 23:59:59' : '',
+
+        hasSpec: this.step2Form.specType,
+        goodsSpecs: this.specList,
+        goodsPrice: this.step2Form.price,
+        orgGoodsPrice: this.step2Form.oldPrice,
+        showDetailStock: this.step2Form.showStock,
+        showDetailSold: this.step2Form.showSales,
+        soldNum: this.step2Form.sales,
+        freightTemplateId: this.step2Form.freight,
+        status: this.step2Form.status,
+
+        templateId: this.step3Form.moduleId,
+        content: this.step3Form.detailContent,
+      }
+      console.log(params);
+
+      if(this.isEdit) {
+        params.goodsId = this.editId;
+        editGoods(params).then(res => {
+          this.formLoading = false;
+          // this.$refs.mainForm.resetFields();
+          this.$successMsg('编辑成功');
+          setTimeout(()=>{
+            this.goBack();
+          }, 1000)
+        }).catch(err => {
+          this.formLoading = false;
+        })
+      } else {
+        addGoods(params).then(res => {
+          this.formLoading = false;
+          // this.$refs.mainForm.resetFields();
+          this.$successMsg('新增成功');
+          setTimeout(()=>{
+            this.goBack();
+          }, 1000)
+        }).catch(err => {
+          this.formLoading = false;
+        })
+      }
+    },
+
+    goBack() {
+      this.$router.go(-1);
+      // this.$store.dispatch("tagsView/delView", this.$route);
+    },
+
+    // 商品主图 - 上传成功
+    uploadSuccess(res, file) {
+      this.step1Form.imgUrl = res.data.url;
+    },
+
+    // 商品主图 - 上传前
+    beforeUpload(file) {
+      const fileSuffix = file.name.substring(file.name.lastIndexOf(".") + 1);
+      const whiteList = ['jpg', 'jpeg', 'png'];
+      if (whiteList.indexOf(fileSuffix) === -1) {
+        this.$errorMsg('只支持上传jpg/png文件!');
+        return false;
+      }
+    },
+
+    // 商品视频 - 上传成功
+    uploadSuccess3(res, file) {
+      this.step1Form.videoUrl = res.data.url;
+    },
+
+    // 商品视频 - 上传前
+    beforeUpload3(file) {
+      const fileSuffix = file.name.substring(file.name.lastIndexOf(".") + 1);
+      const whiteList = ['AVI', 'mov', 'rmvb', 'rm', 'FLV', 'mp4'];
+      if (whiteList.indexOf(fileSuffix) === -1) {
+        this.$errorMsg('只支持上传视频文件!');
+        return false;
+      }
+    },
+
+    // 水印logo - 上传成功
+    uploadSuccess7(res, file) {
+      this.step1Form.logoUrl = res.data.url;
+    },
+
+    // 水印logo - 上传前
+    beforeUpload7(file) {
+      const fileSuffix = file.name.substring(file.name.lastIndexOf(".") + 1);
+      const whiteList = ['jpg', 'jpeg', 'png'];
+      if (whiteList.indexOf(fileSuffix) === -1) {
+        this.$errorMsg('只支持上传jpg/png文件!');
+        return false;
+      }
+    },
+
+    // 规格图片 - 上传成功
+    uploadSuccess5(res, file) {
+      this.specForm.imgUrl = res.data.url;
+    },
+
+    // 规格图片 - 上传前
+    beforeUpload5(file) {
+      const fileSuffix = file.name.substring(file.name.lastIndexOf(".") + 1);
+      const whiteList = ['jpg', 'jpeg', 'png'];
+      if (whiteList.indexOf(fileSuffix) === -1) {
+        this.$errorMsg('只支持上传jpg/png文件!');
+        return false;
+      }
+    },
+
+    // 富文本图片 - 上传前
+    beforeUpload4() {
+      this.quillImgLoading = true;
+    },
+
+    // 富文本图片 - 上传成功
+    uploadSuccess4(res, file, fileList) {
+      console.log(fileList);
+      fileList.forEach(item => {
+        if(this.editorImages.indexOf(item.response.data.url) < 0) {
+          this.editorImages.push(item.response.data.url);
+        }
+      })
+      this.showImage()
+      this.quillImgLoading = false;
+    },
+
+    // 富文本图片 - 显示图片
+    showImage() {
+      console.log(this.editorImages);
+      let quill = this.$refs.myQuillEditor.quill;
+      this.editorImages.forEach(item => {
+        // 获取光标所在位置
+        let length = quill.getSelection().index;
+        // 插入图片  res.info为服务器返回的图片地址
+        console.log(item);
+        quill.insertEmbed(length, 'image', item);
+        // this.$refs.imageListUpload.clearFiles()
+        // 调整光标到最后
+        quill.setSelection(length + 1);
+      })
+      this.editorImages = [];
+      this.$refs.imageListUpload.clearFiles();
+    },
+
+    // 富文本图片 - 上传失败
+    uploadError4() {
+      this.quillImgLoading = false;
+      this.$errorMsg('图片插入失败');
+    },
+
+    changeGoodsPrice() {
+      if(!this.canChangeGoodsPrice) { return false };
+      if(!this.step2Form.specType) {
+        this.step2Form.price = this.specForm.price;
+        // this.$set(this.step2Form, 'price', this.specForm.price);
+      }else {
+        if(this.specList.length > 0) {
+          let allPrice = [];
+          this.specList.forEach(item => {
+            allPrice.push(item.price);
+          })
+          this.step2Form.price = Math.min(...allPrice);
+        }else {
+          this.step2Form.price = '';
+        }
+      }
+    },
+
+    computeShareAmount() {
+      this.specForm.shareAmount = (this.specForm.price*100 - this.specForm.costPrice*100) / 100;
+    },
+
+    // 轮播图 - 点击上传图片
+    uploadImage(id) {
+      this.uploadImageId = id;
+      document.querySelector('.imageListUpload2 input').click();
+    },
+
+    // 轮播图 - 上传成功
+    uploadSuccess2(res, file) {
+      if(this.uploadImageId) {
+        let index = this.$findElem(this.step1Form.images, 'id', this.uploadImageId);
+        this.$set(this.step1Form.images, index, res.data);
+      }else {
+        if(this.step1Form.images.length >= 6) {
+          return this.$errorMsg('最多上传6张轮播图');
+        }
+        this.step1Form.images.push(res.data);
+      }
+    },
+
+    // 轮播图 - 超出限制数量
+    uploadExceed2(files, fileList) {
+      return this.$errorMsg('最多上传6张轮播图');
+    },
+
+    // 轮播图 - 上传前
+    beforeUpload2(file) {
+      const fileSuffix = file.name.substring(file.name.lastIndexOf(".") + 1);
+      const whiteList = ['jpg', 'jpeg', 'png'];
+      if (whiteList.indexOf(fileSuffix) === -1) {
+        this.$errorMsg('只支持上传jpg/jpeg/png文件!');
+        return false;
+      }
+    },
+
+    // 轮播图 - 删除图片
+    deleteImage(index) {
+      this.step1Form.images.splice(index, 1);
+    },
+
+    // 轮播图 - 向前移动
+    moveForward(index) {
+      if(index != 0) {
+        let arr = this.step1Form.images;
+        let thisItem = arr[index];
+        let targetItem = arr[index - 1];
+        this.$set(this.step1Form.images, index, targetItem);
+        this.$set(this.step1Form.images, index - 1, thisItem);
+      }else {
+        this.$errorMsg('已经最前,无法前移');
+      }
+    },
+
+    // 轮播图 - 向后移动
+    moveBack(index) {
+      if(index+1 < this.step1Form.images.length) {
+        let arr = this.step1Form.images;
+        let thisItem = arr[index];
+        let targetItem = arr[index + 1];
+        this.$set(this.step1Form.images, index, targetItem);
+        this.$set(this.step1Form.images, index + 1, thisItem);
+      }else {
+        this.$errorMsg('已经最后,无法后移');
+      }
+    },
+
+    // 编辑规格图 - 点击图片
+    editSpecImage(index) {
+      this.editSpecImageIdx = index;
+      document.querySelector('.editSpecimage-uploader input').click();
+    },
+
+    // 编辑规格图 - 上传成功
+    uploadSuccess6(res, file) {
+      this.specList[this.editSpecImageIdx].imgUrl = res.data.url;
+    },
+
+  }
+
+}
+
+</script>
+
+<style scoped lang="scss">
+  .step-container {
+    padding: 0 10%;
+  }
+  .form-container {
+    margin-top: 40px;
+    padding: 0 10%;
+    .title {
+      font-size: 16px;
+      margin-bottom: 30px;
+      padding-left: 10px;
+      font-weight: bold;
+    }
+    .tips {
+      margin-top: 10px;
+      span {
+        display: inline-block;
+        width: 300px;
+        text-align: center;
+        line-height: 32px;
+        background: #ffefef;
+        font-size: 14px;
+        color: #f66460;
+      }
+    }
+    .tips2 {
+      font-size: 12px;
+      color: #999999;
+      line-height: 30px;
+    }
+    .container {
+      padding: 10px 20px 0;
+      background: #f5f5f5;
+      border-radius: 10px;
+    }
+    .addBtn {
+      padding: 10px 0;
+    }
+  }
+  @media only screen and (max-width: 1200px) {
+    .form-container {
+      padding: 0 10%;
+    }
+  }
+  @media only screen and (max-width: 768px) {
+    .step-container {
+      padding: 0;
+    }
+    .form-container {
+      padding: 0 5%;
+    }
+  }
+</style>
+
+<style lang="scss">
+  // 图片墙
+  .el-upload-list--picture-card .el-upload-list__item {
+    width: 100px;
+    height: 100px;
+  }
+  .el-upload--picture-card {
+    width: 100px;
+    height: 100px;
+    line-height: 100px;
+    .avatar-uploader-icon {
+      font-size: 28px;
+      color: #8c939d;
+      width: 100px;
+      height: 100px;
+      line-height: 100px;
+      text-align: center;
+    }
+  }
+
+  .el-input.small input {
+    width: 300px;
+  }
+
+  .avatar-uploader2 {
+    height: 0;
+  }
+
+  .container {
+    .el-form-item__label {
+      padding-bottom: 0;
+    }
+    .el-form-item {
+      margin-bottom: 5px;
+    }
+  }
+  .ql-editor{
+    min-height:300px;
+  }
+</style>
+
+<style scoped lang="scss">
+  .images {
+    display: flex;
+    flex-wrap: wrap;
+    .item {
+      display: flex;
+      flex-direction: column;
+      justify-content: center;
+      align-items: center;
+      width: 120px;
+      margin-right: 20px;
+      margin-bottom: 20px;
+      .img {
+        border: 1px dashed #eaeaea;
+        border-radius: 5px;
+        overflow: hidden;
+        position: relative;
+        .el-image {
+          display: block;
+        }
+        .mask {
+          position: absolute;
+          left: 0;
+          top: 0;
+          width: 120px;
+          height: 120px;
+          background: rgba($color: #000000, $alpha: 0.5);
+          display: flex;
+          align-items: center;
+          justify-content: center;
+          flex-direction: column;
+          opacity: 0;
+          &:hover {
+            opacity: 1;
+          }
+          .row {
+            display: flex;
+            align-items: center;
+            justify-content: center;
+            .it {
+              display: flex;
+              align-items: center;
+              justify-content: center;
+              cursor: pointer;
+              margin: 5px;
+              i {
+                font-size: 20px;
+                color: #ffffff;
+              }
+              span {
+                font-size: 14px;
+                color: #ffffff;
+              }
+            }
+          }
+        }
+      }
+      .add {
+        border: 1px dashed #eaeaea;
+        border-radius: 5px;
+        cursor: pointer;
+        .avatar-uploader-icon {
+          width: 120px;
+          height: 120px;
+          line-height: 120px;
+        }
+        &:hover {
+          border: 1px dashed #66b1ff;
+        }
+      }
+    }
+  }
+</style>

+ 2 - 2
src/views/mallManagement/goods/goods_index/index.vue

@@ -447,12 +447,12 @@ export default {
     addOrEdit(type, id) {
       if(type == 'add') {
         this.$router.push({
-          path: '/goods/goods_add',
+          name: 'goods_add',
           query: {}
         })
       }else {
         this.$router.push({
-          path: '/goods/goods_add',
+          name: 'goods_add',
           query: {
             id
           }

+ 3 - 4
src/views/setting/menu/index.vue

@@ -27,7 +27,7 @@
           </el-table-column>
           <el-table-column align="center" prop="status" label="状态">
             <template slot-scope="scope">
-              <span>{{ ['开启', '关闭'][[true, false].indexOf(scope.row.status)] || '' }}</span>
+              <span>{{ ['显示', '不显示'][[true, false].indexOf(scope.row.status)] || '' }}</span>
             </template>
           </el-table-column>
           <el-table-column align="center" prop="sortNum" label="排序" />
@@ -98,7 +98,7 @@
         <el-form-item label="排序" prop="sort">
           <el-input v-model.number="addParentForm.sort" placeholder="请输入排序" />
         </el-form-item>
-        <el-form-item label="是否使用" prop="status">
+        <el-form-item label="是否显示" prop="status">
           <el-switch
             v-model="addParentForm.status"
             :active-value="true"
@@ -168,7 +168,7 @@
         <el-form-item label="排序" prop="sort">
           <el-input v-model.number="addChildForm.sort" placeholder="请输入排序" />
         </el-form-item>
-        <el-form-item label="是否使用" prop="status">
+        <el-form-item label="是否显示" prop="status">
           <el-switch
             v-model="addChildForm.status"
             :active-value="true"
@@ -268,7 +268,6 @@ export default {
       },
       addParentFormRules: {
         type: [{ required: true, message: '请选择类型', trigger: 'change' }],
-
         oneMenu: [{ required: true, message: '请填写一级菜单名称', trigger: 'blur' }],
         code: [{ required: true, message: '请填写菜单CODE', trigger: 'blur' }],
         url: [{ required: true, message: '请填写菜单URL', trigger: 'blur' }],