微信小程序之 Classify(商品屬性分類)


1.項目目錄

2.邏輯層

broadcast.js

// pages/broadcast/broadcast.js
Page({

  /**
   * 頁面的初始數據
   */
  data: {
    firstIndex: -1,
    //准備數據  
    //數據結構:以一組一組來進行設定  
    commodityAttr: [
      {
        priceId: 1,
        price: 35.0,
        "stock": 8,
        "attrValueList": [
          {
            "attrKey": "型號",
            "attrValue": "2"
          },
          {
            "attrKey": "顏色",
            "attrValue": "白色"
          },
          {
            "attrKey": "大小",
            "attrValue": "小"
          },
          {
            "attrKey": "尺寸",
            "attrValue": "S"
          }
        ]
      },
      {
        priceId: 2,
        price: 35.1,
        "stock": 9,
        "attrValueList": [
          {
            "attrKey": "型號",
            "attrValue": "1"
          },
          {
            "attrKey": "顏色",
            "attrValue": "黑色"
          },
          {
            "attrKey": "大小",
            "attrValue": "小"
          },
          {
            "attrKey": "尺寸",
            "attrValue": "M"
          }
        ]
      },
      {
        priceId: 3,
        price: 35.2,
        "stock": 10,
        "attrValueList": [
          {
            "attrKey": "型號",
            "attrValue": "1"
          },
          {
            "attrKey": "顏色",
            "attrValue": "綠色"
          },
          {
            "attrKey": "大小",
            "attrValue": "大"
          },
          {
            "attrKey": "尺寸",
            "attrValue": "L"
          }
        ]
      },
      {
        priceId: 4,
        price: 35.2,
        "stock": 10,
        "attrValueList": [
          {
            "attrKey": "型號",
            "attrValue": "1"
          },
          {
            "attrKey": "顏色",
            "attrValue": "綠色"
          },
          {
            "attrKey": "大小",
            "attrValue": "大"
          },
          {
            "attrKey": "尺寸",
            "attrValue": "L"
          }
        ]
      }
    ],
    attrValueList: []
  },

  /**
   * 生命周期函數--監聽頁面加載
   */
  onLoad: function (options) {
  
  },

  /**
   * 生命周期函數--監聽頁面初次渲染完成
   */
  onReady: function () {
  
  },

  /**
   * 生命周期函數--監聽頁面顯示
   */
  onShow: function () {
    this.setData({
      includeGroup: this.data.commodityAttr
    });
    this.distachAttrValue(this.data.commodityAttr);
    // 只有一個屬性組合的時候默認選中  
    // console.log(this.data.attrValueList);  
    if (this.data.commodityAttr.length == 1) {
      for (var i = 0; i < this.data.commodityAttr[0].attrValueList.length; i++) {
        this.data.attrValueList[i].selectedValue = this.data.commodityAttr[0].attrValueList[i].attrValue;
      }
      this.setData({
        attrValueList: this.data.attrValueList
      });
    }
  },

  /* 獲取數據 */
  distachAttrValue: function (commodityAttr) {
    /** 
      將后台返回的數據組合成類似 
      { 
        attrKey:'型號', 
        attrValueList:['1','2','3'] 
      } 
    */
    // 把數據對象的數據(視圖使用),寫到局部內  
    var attrValueList = this.data.attrValueList;
    // 遍歷獲取的數據  
    for (var i = 0; i < commodityAttr.length; i++) {
      for (var j = 0; j < commodityAttr[i].attrValueList.length; j++) {
        var attrIndex = this.getAttrIndex(commodityAttr[i].attrValueList[j].attrKey, attrValueList);
        // console.log('屬性索引', attrIndex);   
        // 如果還沒有屬性索引為-1,此時新增屬性並設置屬性值數組的第一個值;索引大於等於0,表示已存在的屬性名的位置  
        if (attrIndex >= 0) {
          // 如果屬性值數組中沒有該值,push新值;否則不處理  
          if (!this.isValueExist(commodityAttr[i].attrValueList[j].attrValue, attrValueList[attrIndex].attrValues)) {
            attrValueList[attrIndex].attrValues.push(commodityAttr[i].attrValueList[j].attrValue);
          }
        } else {
          attrValueList.push({
            attrKey: commodityAttr[i].attrValueList[j].attrKey,
            attrValues: [commodityAttr[i].attrValueList[j].attrValue]
          });
        }
      }
    }
    // console.log('result', attrValueList)  
    for (var i = 0; i < attrValueList.length; i++) {
      for (var j = 0; j < attrValueList[i].attrValues.length; j++) {
        if (attrValueList[i].attrValueStatus) {
          attrValueList[i].attrValueStatus[j] = true;
        } else {
          attrValueList[i].attrValueStatus = [];
          attrValueList[i].attrValueStatus[j] = true;
        }
      }
    }
    this.setData({
      attrValueList: attrValueList
    });
  },
  
  getAttrIndex: function (attrName, attrValueList) {
    // 判斷數組中的attrKey是否有該屬性值  
    for (var i = 0; i < attrValueList.length; i++) {
      if (attrName == attrValueList[i].attrKey) {
        break;
      }
    }
    return i < attrValueList.length ? i : -1;
  },
  isValueExist: function (value, valueArr) {
    // 判斷是否已有屬性值  
    for (var i = 0; i < valueArr.length; i++) {
      if (valueArr[i] == value) {
        break;
      }
    }
    return i < valueArr.length;
  },

  /* 選擇屬性值事件 */
  selectAttrValue: function (e) {
    /* 
    點選屬性值,聯動判斷其他屬性值是否可選 
    { 
      attrKey:'型號', 
      attrValueList:['1','2','3'], 
      selectedValue:'1', 
      attrValueStatus:[true,true,true] 
    } 
    console.log(e.currentTarget.dataset); 
    */
    var attrValueList = this.data.attrValueList;
    var index = e.currentTarget.dataset.index;//屬性索引  
    var key = e.currentTarget.dataset.key;
    var value = e.currentTarget.dataset.value;
    if (e.currentTarget.dataset.status || index == this.data.firstIndex) {
      if (e.currentTarget.dataset.selectedvalue == e.currentTarget.dataset.value) {
        // 取消選中  
        this.disSelectValue(attrValueList, index, key, value);
      } else {
        // 選中  
        this.selectValue(attrValueList, index, key, value);
      }

    }
  },

  /* 選中 */
  selectValue: function (attrValueList, index, key, value, unselectStatus) {
    // console.log('firstIndex', this.data.firstIndex);  
    var includeGroup = [];
    if (index == this.data.firstIndex && !unselectStatus) { // 如果是第一個選中的屬性值,則該屬性所有值可選  
      var commodityAttr = this.data.commodityAttr;
      // 其他選中的屬性值全都置空  
      // console.log('其他選中的屬性值全都置空', index, this.data.firstIndex, !unselectStatus);  
      for (var i = 0; i < attrValueList.length; i++) {
        for (var j = 0; j < attrValueList[i].attrValues.length; j++) {
          attrValueList[i].selectedValue = '';
        }
      }
    } else {
      var commodityAttr = this.data.includeGroup;
    }

    // console.log('選中', commodityAttr, index, key, value);  
    for (var i = 0; i < commodityAttr.length; i++) {
      for (var j = 0; j < commodityAttr[i].attrValueList.length; j++) {
        if (commodityAttr[i].attrValueList[j].attrKey == key && commodityAttr[i].attrValueList[j].attrValue == value) {
          includeGroup.push(commodityAttr[i]);
        }
      }
    }
    attrValueList[index].selectedValue = value;

    // 判斷屬性是否可選  
    for (var i = 0; i < attrValueList.length; i++) {
      for (var j = 0; j < attrValueList[i].attrValues.length; j++) {
        attrValueList[i].attrValueStatus[j] = false;
      }
    }
    for (var k = 0; k < attrValueList.length; k++) {
      for (var i = 0; i < includeGroup.length; i++) {
        for (var j = 0; j < includeGroup[i].attrValueList.length; j++) {
          if (attrValueList[k].attrKey == includeGroup[i].attrValueList[j].attrKey) {
            for (var m = 0; m < attrValueList[k].attrValues.length; m++) {
              if (attrValueList[k].attrValues[m] == includeGroup[i].attrValueList[j].attrValue) {
                attrValueList[k].attrValueStatus[m] = true;
              }
            }
          }
        }
      }
    }
    // console.log('結果', attrValueList);  
    this.setData({
      attrValueList: attrValueList,
      includeGroup: includeGroup
    });

    var count = 0;
    for (var i = 0; i < attrValueList.length; i++) {
      for (var j = 0; j < attrValueList[i].attrValues.length; j++) {
        if (attrValueList[i].selectedValue) {
          count++;
          break;
        }
      }
    }
    if (count < 2) {// 第一次選中,同屬性的值都可選  
      this.setData({
        firstIndex: index
      });
    } else {
      this.setData({
        firstIndex: -1
      });
    }
  },

  /* 取消選中 */
  disSelectValue: function (attrValueList, index, key, value) {
    var commodityAttr = this.data.commodityAttr;
    attrValueList[index].selectedValue = '';

    // 判斷屬性是否可選  
    for (var i = 0; i < attrValueList.length; i++) {
      for (var j = 0; j < attrValueList[i].attrValues.length; j++) {
        attrValueList[i].attrValueStatus[j] = true;
      }
    }
    this.setData({
      includeGroup: commodityAttr,
      attrValueList: attrValueList
    });

    for (var i = 0; i < attrValueList.length; i++) {
      if (attrValueList[i].selectedValue) {
        this.selectValue(attrValueList, i, attrValueList[i].attrKey, attrValueList[i].selectedValue, true);
      }
    }
  },

  /* 點擊確定 */
  submit: function () {
    var value = [];
    for (var i = 0; i < this.data.attrValueList.length; i++) {
      if (!this.data.attrValueList[i].selectedValue) {
        break;
      }
      value.push(this.data.attrValueList[i].selectedValue);
    }
    if (i < this.data.attrValueList.length) {
      wx.showToast({
        title: '請完善屬性',
        icon: 'loading',
        duration: 1000
      })
    } else {
      wx.showToast({
        title: '選擇的屬性:' + value.join('-'),
        icon: 'sucess',
        duration: 1000
      })
    }
  }
})

3.頁面布局

broadcast.wxml

<!--pages/broadcast/broadcast.wxml-->
<view class="title">商品屬性值聯動選擇</view>  
<!--options-->  
<view class="commodity_attr_list">  
  <!--每組屬性-->  
  <view class="attr_box" wx:for="{{attrValueList}}" wx:for-item="attrValueObj" wx:for-index="attrIndex" wx:key="id">  
    <!--屬性名-->  
    <view class="attr_name">{{attrValueObj.attrKey}}</view>  
    <!--屬性值-->  
    <view class="attr_value_box">  
      <!--每個屬性值-->  
      <view class="attr_value {{attrIndex==firstIndex || attrValueObj.attrValueStatus[valueIndex]?(value==attrValueObj.selectedValue?'attr_value_active':''):'attr_value_disabled'}}" bindtap="selectAttrValue" data-status="{{attrValueObj.attrValueStatus[valueIndex]}}"  
      data-value="{{value}}" data-key="{{attrValueObj.attrKey}}" data-index="{{attrIndex}}" data-selectedvalue="{{attrValueObj.selectedValue}}" wx:for="{{attrValueObj.attrValues}}" wx:for-item="value" wx:for-index="valueIndex" wx:key="id">{{value}}</view>  
    </view>  
  </view>  
</view>  
<!--button-->  
<view class="weui-btn-area">  
  <button class="weui-btn" type="primary" bindtap="submit">確定</button>  
</view>

4.樣式

broadcast.wxss

/* pages/broadcast/broadcast.wxss */
.title {  
  padding: 10rpx 20rpx;  
  margin: 10rpx 0;  
  border-left: 4rpx solid #ccc;  
}  
  
/*全部屬性的主盒子*/  
.commodity_attr_list {  
  background: #fff;  
  padding: 0 20rpx;  
  font-size: 26rpx;  
  overflow: hidden;  
  width: 100%;  
}  
/*每組屬性的主盒子*/  
.attr_box {  
  width: 100%;  
  overflow: hidden;  
  border-bottom: 1rpx solid #ececec;  
}  
/*屬性名*/  
.attr_name {  
  width: 20%;  
  float: left;  
  padding: 15rpx 0;  
}  
/*屬性值*/  
.attr_value_box {  
  width: 80%;  
  float: left;  
  padding: 15rpx 0;  
  overflow: hidden;  
}  
/*每個屬性值*/  
.attr_value {  
  float: left;  
  padding: 0 10rpx;  
  margin: 0 10rpx;  
  border: 1rpx solid #ececec;  
}  
/*每個屬性選中的當前樣式*/  
.attr_value_active {  
  background: #FFCC00;  
  border-radius: 10rpx;  
  color: #fff;  
  padding: 0 10rpx;  
}  
/*禁用屬性*/  
.attr_value_disabled {  
  color: #ccc;  
}  
  
/*button*/  
.btn-area {  
  margin: 1.17647059em 15px 0.3em;  
}  
  
.btn {  
  margin-top: 15px;  
  background-color:#FFCC00;  
  color: #fff;  
}  
.btn:first-child {  
  margin-top: 0;  
}

5.效果圖


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM