zl程序教程

您现在的位置是:首页 >  前端

当前栏目

vue后台(四)

2023-09-11 14:20:08 时间

一,在spu商品列表页,点击修改按钮,初始化请求页面数据

1.1。点击修改按钮,在spu组件中给子组件spuForn设置ref属性,调用子组件的函数(传递属性id,接口函数的参数),子组件调用四个接口函数,获取数据

 

 

 <el-button
                type="primary"
                icon="el-icon-edit"
                size="mini"
                title="修改spu"
                @click="showUpdateSpuForm(row.id)"
              ></el-button>
<skuForm v-show="isShowSkuForm" ></skuForm>
      <spuForm  v-show="isShowSpuForm" @visible="isShowSpuForm =$event"  ref="spu"></spuForm>

js代码

    // 点击修改spu按钮
    showUpdateSpuForm(spuId){
      this.isShowSpuForm =true

      // 获取子组件spuForm,调用他里头的方法,发送四个接口函数,获取数据
      this.$refs.spu.initUpdateSpuForm(spuId)
    },

 

在子组件spuForm中定义该函数,调用四个接口函数,获取数据

 //在spu管理列表页,点击修改按钮,父组件在该子组件中定义该函数
    async initUpdateSpuForm(spuId) {
      //发送四个请求获取对应的初始化数据
      //获取对应的spu的详情信息
      ///admin/product/getSpuById/670
      const spuinfoResult = await this.$API.spu.get(spuId);
      if (spuinfoResult.code === 200) {
        this.spuInfo = spuinfoResult.data;
      }

      //获取对应的spu图片列表  因为图片列表数据并没有在spu详情里面,需要单独发请求
      ///admin/product/spuImageList/670
      const imageResult = await this.$API.sku.getSpuImageList(spuId);
      if (imageResult.code === 200) {
        this.spuImageList = imageResult.data;
      }
      //所有的品牌信息
      ///admin/product/baseTrademark/getTrademarkList

      const trademarkResult = await this.$API.trademark.getAll();
      if (trademarkResult.code === 200) {
        this.trademarkList = trademarkResult.data;
      }

      //所有的spu基础销售属性
      ///admin/product/baseSaleAttrList
      const baseSaleAttrResult = await this.$API.spu.getSaleList();
      if (baseSaleAttrResult.code === 200) {
        this.baseSaleAttrList = baseSaleAttrResult.data;
      }
    },

数据收集

  data() {
    return {
      dialogImageUrl: "",
      dialogVisible: false,
      // spu的详情信息
      spuInfo: {},
      //图片信息
      spuImageList: [],
      // 所有的品牌信息
      trademarkList: [],
      // 基础销售属性
      baseSaleAttrList: []
    };
  },

 

2.动态展示spu名称,描述,品牌数据,渲染页面(el-select中收集的id是el-option中的id)

    <el-form label-width="100px" :inline="false" size="normal" :model="spuInfo">
      <el-form-item label="SPU名称">
        <el-input placeholder="请输入spu名称"  v-model="spuInfo.spuName"></el-input>
      </el-form-item>
      <el-form-item label="品牌">
        <el-select placeholder="请选择品牌" value="" v-model="spuInfo.tmId">
          <el-option :value="trademark.id" :label="trademark.tmName"  v-for="(trademark, index) in trademarkList" :key="trademark.id"> </el-option>
        </el-select>
      </el-form-item>
      <el-form-item label="SPU描述">
        <el-input
          placeholder="请输入spu描述"
          type="textarea"
          rows="4"
          v-model="spuInfo.description"
        ></el-input>
      </el-form-item>

 

3.动态展示spu图片列表

element-ui的upload有个属性file-list,上传图片墙的文件列表,需要url和name属性

 

 而我们返回的spuImageList数据没有该属性,需要更改属性名称

  <el-form-item label="SPU描述">
        <el-upload
          action="https://jsonplaceholder.typicode.com/posts/"
          list-type="picture-card"
          :on-preview="handlePictureCardPreview"
          :on-remove="handleRemove"
          :file-list="spuImageList"
        >
          <i class="el-icon-plus"></i>
        </el-upload>
        <el-dialog :visible.sync="dialogVisible">
          <img width="100%" :src="dialogImageUrl" alt="" />
        </el-dialog>
      </el-form-item>

 

对返回的数据进行整理
  //获取对应的spu图片列表  因为图片列表数据并没有在spu详情里面,需要单独发请求
      ///admin/product/spuImageList/670
      const imageResult = await this.$API.sku.getSpuImageList(spuId);
      if (imageResult.code === 200) {

        let spuImageList = imageResult.data
        spuImageList.forEach(item=>{
             item.name = item.imgName;
             item.url = item.imgUrl;
        })
        this.spuImageList = imageResult.data;
      }

 

4.动态展示spu销售属性(表格当中部分)

 

 

 <el-table
          border
          style="width: 100%; margin-top:20px"
          :data="spuInfo.spuSaleAttrList"
        >
          <el-table-column align="center" type="index" label="序号" width="80">
          </el-table-column>
          <el-table-column prop="saleAttrName" label="属性名" width="150">
          </el-table-column>
          <el-table-column  label="属性值列表" width="width">
            <template slot-scope="{row,$index}">
              <el-tag
                :key="spuSaleAttrValue.id"
                v-for="(spuSaleAttrValue, index) in row.spuSaleAttrValueList"
                closable
                :disable-transitions="false"
           
              >
                {{spuSaleAttrValue.saleAttrValueName}}
              </el-tag>
              <!-- isEdict先放在属性spuSaleAttrList中,新增的tag也放在属性中 ,编辑模式,查看模式-->
              <el-input
               
                v-if="row.isEdict"
                v-model="row.saleAttrValueName"
                ref="saveTagInput"
                size="small"
            
              >
              </el-input>
              <el-button
                v-else
                class="button-new-tag"
                size="small"
      
                >+ 新增属性值</el-button
              >
            </template>
          </el-table-column>
          <el-table-column prop="prop" label="操作" width="150">
              <template slot-scope="{row,$index}">
              <el-button
                type="danger"
                size="mini"
                icon="el-icon-delete"
       
              >删除</el-button>
            </template>
          </el-table-column>
        </el-table>

 

5.动态展示未使用的基础销售属性(计算属性)

computed:{
    ///计算未使用的基础销售属性列表
    //根据两个数组计算  一个是所有的基础销售属性数组baseSaleAttrList  和  spu的销售属性数组 spuInfo.spuSaleAttrList
    //从baseSaleAttrList拿到每一个  都去spuInfo.spuSaleAttrList里面对比所有的  如果前面拿到的和后面所有的名字都不相同,就是我们要
    //拿的,放进新数组  
      unusedBaseSaleAttrList(){
          return this.baseSaleAttrList.filter(baseSaleAttr => 
          this.spuInfo.spuSaleAttrList.every(spuSaleAttr=>
           baseSaleAttr.name !== spuSaleAttr.saleAttrName))
      }
  },
 <el-form-item label="销售属性">
        <el-select :placeholder="unusedBaseSaleAttrList.length >1 ? `还有${unusedBaseSaleAttrList.length}个` : `没有了`" v-model="unusedBaseSaleAttrId">
          <el-option value="unusedBaseSaleAttr.id"  :label="unusedBaseSaleAttr.name"
          v-for="(unusedBaseSaleAttr,index) in unusedBaseSaleAttrList" :key="unusedBaseSaleAttr.id"></el-option>
        </el-select>
        <el-button type="primary" icon="el-icon-plus">添加销售属性</el-button>

 

6.收集spu的图片列表

 

 

  <el-form-item label="SPU描述">
        <el-upload
          action="/dev-api/admin/product/fileUpload"
          list-type="picture-card"
          :on-preview="handlePictureCardPreview"
          :on-remove="handleRemove"
          :on-success="handleUploadSuccess"
          :file-list="spuImageList"
        >
          <i class="el-icon-plus"></i>
        </el-upload>
        <el-dialog :visible.sync="dialogVisible">
          <img width="100%" :src="dialogImageUrl" alt="" />
        </el-dialog>
      </el-form-item>

js,函数

   handleRemove(file, fileList) {
        //file 被删除的那一张图片信息
      //fileList  删除过后剩余的图片列表
      // console.log(file, fileList);
      console.log(file, fileList);
    },
    handlePictureCardPreview(file) {
      this.dialogImageUrl = file.url;
      this.dialogVisible = true;
    },

    handleUploadSuccess(response,file, fileList){
        console.log(response,file, fileList)
        // 上传成功后的图片列表中有部分没有response,新上传的有
        this.spuImageList = fileList
    }

 

7.添加spu销售属性

选择销售属性,点击添加销售属性值,table会新增属性值

 

 

选中的属性收集的是id和name

      <el-form-item label="销售属性">
        <el-select :placeholder="unusedBaseSaleAttrList.length >0 ? `还有${unusedBaseSaleAttrList.length}个` : `没有了`" v-model="unusedBaseSaleAttrIdAndName">
          <el-option :value="unusedBaseSaleAttr.id + ':' + unusedBaseSaleAttr.name "  :label="unusedBaseSaleAttr.name"
          v-for="(unusedBaseSaleAttr,index) in unusedBaseSaleAttrList" :key="unusedBaseSaleAttr.id"></el-option>
        </el-select>
        <el-button type="primary" icon="el-icon-plus"  @click="addSaleAttr">添加销售属性</el-button>
  // 添加销售属性
    addSaleAttr() {
      //   {
      //   "baseSaleAttrId": "1",
      //   "saleAttrName": "选择颜色",
      //   "spuSaleAttrValueList": [
      //     {
      //       "saleAttrValueName": "a",
      //       "baseSaleAttrId": "1"
      //     }
      //   ]
      // }
      let [
        baseSaleAttrId,
        saleAttrName,
      ] = this.unusedBaseSaleAttrIdAndName.split(":"); //从select选中项收集数据当中提取id和name
      //构造销售属性的对象数据添加到销售属性列表当中
      this.spuInfo.spuSaleAttrList.push({
        baseSaleAttrId,
        saleAttrName,
        spuSaleAttrValueList: [],
      });

      this.unusedBaseSaleAttrIdAndName = ""; //清空select的选中项
    },

 

8. 添加spu销售属性属性值

 

 

点击添加属性值按钮 ,将查看模式修改成编辑模式

<el-tag
                :key="spuSaleAttrValue.id"
                v-for="(spuSaleAttrValue,index) in row.spuSaleAttrValueList"
                closable
                :disable-transitions="false"
                @close="row.spuSaleAttrValueList.splice(index,1)"
              >{{spuSaleAttrValue.saleAttrValueName}}</el-tag>
              <!-- 删除属性值,在对应的事件当中去删除当前下标对应的属性值对象 -->
              <el-input
                placeholder="请输入"
                style="width:150px"
                v-if="row.isEdit"
                v-model="row.saleAttrValueName"
                ref="saveTagInput"
                size="small"
                @keyup.enter.native="handleInputConfirm(row)"
                @blur="handleInputConfirm(row)"
              ></el-input>

              <el-button v-else class="button-new-tag" size="small" @click="showInput(row)">+ 添加属性值</el-button>
            </template>
          </el-table-column>

js代码

 //点击添加属性值的按钮切换为编辑模式 input
    showInput(row) {
      //要想后期添加的属性数据是响应式,必须使用以下写法 不能用点语法
      this.$set(row, "isEdit", true);
      //自动获取焦点
      this.$nextTick(() => {
        this.$refs.saveTagInput.focus();
      });
    },

 

切换成input编辑模式后,失去焦点后,需要将属性值添加到属性值列表中spuSaleAttrValueList

<!-- isEdict先放在属性spuSaleAttrList中,新增的tag也放在属性中 -->
              <el-input
               style="width:50%"
               placeholder="请输入"
                v-if="row.isEdict"
                v-model="row.saleAttrValueName"
                ref="saveTagInput"
                size="small"
               @keyup.enter.native="handleInputConfirm(row)"
                @blur="handleInputConfirm(row)"
            
              >
              </el-input>
              <el-button
                v-else
                class="button-new-tag"
                size="small"
                @click="showInput(row)"
                >+ 新增属性值</el-button
              >

js代码

  //input输入数据之后,数据被收集到了属性对象身上,回车或者失去焦点后
    handleInputConfirm(row) {
      let { saleAttrValueName, baseSaleAttrId } = row;

      if (!saleAttrValueName.trim()) return;
      //前面平台属性属性值判定的时候要出去自身  因为平台属性先添加的对象,然后往对象内部才输入的值,最后失去焦点的
      //现在我们根本没有添加对象,我们只需要去判断我们输入的属性值名称和目前已有的所有属性值名称对比就好了
      let isRepeat = row.spuSaleAttrValueList.some(
        (item) => item.saleAttrValueName === saleAttrValueName
      );
      if (isRepeat) {
        this.$message.warning("不能重复");
        // row.saleAttrValueName = ''
        return;
      }

      // {
      //     "saleAttrValueName": "a",
      //     "baseSaleAttrId": "1"
      // }
      //构造属性值对象添加到对应的数组当中
      row.spuSaleAttrValueList.push({
        saleAttrValueName,
        baseSaleAttrId,
      });

      row.isEdict = false; //切换为查看模式

      row.saleAttrValueName = ""; //清空input输入框
    },

 

9.删除属性值和删除属性的操作
<el-table-column label="属性值列表" width="width">
            <template slot-scope="{row,$index}">
              <el-tag
                :key="spuSaleAttrValue.id"
                v-for="(spuSaleAttrValue,index) in row.spuSaleAttrValueList"
                closable
                :disable-transitions="false"
                @close="row.spuSaleAttrValueList.splice(index,1)"
              >{{spuSaleAttrValue.saleAttrValueName}}</el-tag>
              <!-- 删除属性值,在对应的事件当中去删除当前下标对应的属性值对象 -->
              <el-input
                placeholder="请输入"
                style="width:150px"
                v-if="row.isEdit"
                v-model="row.saleAttrValueName"
                ref="saveTagInput"
                size="small"
                @keyup.enter.native="handleInputConfirm(row)"
                @blur="handleInputConfirm(row)"
              ></el-input>

              <el-button v-else class="button-new-tag" size="small" @click="showInput(row)">+ 添加属性值</el-button>
            </template>
  <el-table-column label="操作" width="150">
            <template slot-scope="{row,$index}">
              <el-button
                type="danger"
                size="mini"
                icon="el-icon-delete"
                @click="spuInfo.spuSaleAttrList.splice($index,1)"
              >删除</el-button>
            </template>