小程序购物车加减和数字输入的组件,及组件向页面、页面向组件传值

一、组件:

1.wxml页面

<!-- 选择数量组件 -->
<view class="select">
  <text class="reduce {{minusStatus}}" data-num="{{num}}" catchtap="bindMinus" data-price="{{unitPrice}}">-</text>
  <!-- <input type="number" class="number" data-num="{{num}}" bindinput="getNum" bindblur="getNum" catchtap="empty"
    value="{{num}}" data-price="{{unitPrice}}" /> -->
  <view class="number" data-num="{{num}}"  catchtap="bindManual"  data-price="{{unitPrice}}">{{num}}</view>
  <text class="add normal" data-num="{{num}}" catchtap="bindPlus" data-price="{{unitPrice}}">+</text>
</view>

<view class="outBox {{isBox?'show':''}}" catchtap="empty">
  <view class="black" catchtap="closeBox"></view>
  <view class="box">
    <text>请输入数量</text>
    <!-- input输入事件bindinput事件冒泡,此时catchtap给你个空方法,阻止冒泡即可 -->
    <input type="number" class="number" data-num="{{numNew}}" bindblur="getNum" value="{{numNew}}" catchtap="empty"
      data-price="{{unitPrice}}" />
    <view class="btn">
      <view class="cancle" catchtap="closeBox">取消</view>
      <view class="sure" catchtap="sureBox">确认</view>
    </view>
  </view>
</view>
View Code

 

2.wxss样式

/** 选择数量组件样式 **/
.select {
  bottom: 0;
  background: #fff;
  padding: 0 20rpx;
  font-size: 30rpx;
}
.select .reduce,
.select .add {
  float: left;
  font-size: 45rpx;
  width: 60rpx;
  height: 60rpx;
  line-height: 60rpx;
  text-align: center;
  background-color: #F7F8FA;
}
.select .number {
  background-color: #F7F8FA;
  float: left;  
  height: 60rpx;
  line-height: 60rpx;
  text-align: center;
  font-weight: 400;
  width: 80rpx !important;
  box-sizing: border-box;
  margin: 0 2rpx !important;
  border: 0 !important;
}
.select .reduce {
  border-bottom-left-radius: 8rpx;
  border-top-left-radius: 8rpx;
}
.select .add {
  border-bottom-right-radius: 8rpx;
  border-top-right-radius: 8rpx;
}
/*普通样式*/
.select .normal {
  color: #666;
  font-weight: normal;
}
/*禁用样式*/
.select .disabled {
  color: #ccc;
}

.outBox{
  display: none;
}
.show{
  display: block;
}
.black{
  width: 100%;
  height: 100%;
  background: rgba(0,0,0,.3);
  position: absolute;
  top:0;
  left: 0;
  z-index: 10;
}
.box{
  width:75%;
  height:280rpx ;
  background-color: #fff;
  border-radius: 10rpx;
  position: absolute;
  left: 50%;
  top: 50%;
  transform: translate(-50%,-50%);
  z-index: 11;
  box-sizing: border-box;
  padding:45rpx;
}

.box text{
  font-size: 16px;
  color:#666;
  font-weight: 400;
  display: block;
  width: 100%;
}
.box input{
  width:100%;
  border:0;
  box-sizing: border-box;
  text-align: left;
  border-bottom:1px solid #ccc;
  margin: 20rpx 0;
  padding:5px 30rpx;

}
.box .btn {
  width: 200rpx;
  float: right;
  display: flex;
  justify-content: space-between;
}
.box .btn .cancle,.box .btn .sure{
  display: block;
  line-height: 50rpx;
  width: 80rpx;
  text-align: center;
  color:#da2728;
}
View Code

 

3.js

Component({
  /**
   * 组件的初始数据
   */
  data: {
    // 数量增减
    num: 1,
    minusStatus: 'disabled',
    totalPrice: 0, // 定制总价的计算
    isBox: false,
  },
  /**
   * 组件的属性列表 
   */
  properties: {
    unitPrice: { // 接收传递过来的数据
      type: Number,
      value: 0,
    },
    num: { // 接收传递过来的num
      type: Number,
      value: 1,
    },
    tapIndex: { // 点击数量是,当前产品所属的大分类索引
      type: Number,
      value: 0,
    },
    goodIndex: { // 点击时当前购物车产品的索引
      type: Number,
      value: 0,
    },
    cartId: { // 购物车id
      type: String,
    },
  },

  /**
   * 组件的方法列表
   */
  methods: {
    /* 点击减号 */
    bindMinus: function () {
      var num = this.data.num;
      // 定制页面过来的商品单价
      var unitPrice = this.properties.unitPrice;
      // console.log(unitPrice)

      // 如果大于1时,才可以减
      if (num > 1) {
        num--;
      }
      // 只有大于一件的时候,才能normal状态,否则disable状态
      var minusStatus = num <= 1 ? 'disabled' : 'normal';
      // 将数值与状态写回
      this.setData({
        num: num,
        minusStatus: minusStatus,
        totalPrice: num * unitPrice,
      });

      // console.log(this.data.totalPrice)
      // 将数据传递过去
      this.triggerEvent("onBindMinus", {
        "totalPrice": this.data.totalPrice,
        "num": num,
        "tapIndex": this.properties.tapIndex, // 购物车分类索引
        "goodIndex": this.properties.goodIndex, // 购物车当前产品索引
        "cartId": this.properties.cartId, // 当前购物车id
      })
    },
    /* 点击加号 */
    bindPlus: function (e) {
      var num = this.data.num;
      // 定制页面过来的商品单价
      var unitPrice = this.properties.unitPrice;
      // console.log(unitPrice)

      // 数量最多可以选择9999件
      if (num < 9999) {
        num++;
      }
      // 只有大于一件的时候,才能normal状态,否则disable状态
      var minusStatus = num < 1 ? 'disabled' : 'normal';
      // 将数值与状态写回
      this.setData({
        num: num,
        minusStatus: minusStatus,
        totalPrice: num * unitPrice,
      });

      // console.log(this.data.totalPrice)
      // 将数据传递过去
      this.triggerEvent("onBindPlus", {
        "totalPrice": this.data.totalPrice,
        "num": num,
        "tapIndex": this.properties.tapIndex, // 购物车分类索引
        "goodIndex": this.properties.goodIndex, // 购物车当前产品索引
        "cartId": this.properties.cartId, // 当前购物车id
      })
    },
    /* 点击弹出输入数量 */
    bindManual: function (e) {
      this.setData({
        isBox: !this.data.isBox,
      })
    },

    // 关闭弹出框和点击取消
    closeBox: function (e) {
      this.setData({
        num:this.properties.num,
        isBox: false,        
      })
    },

    // 小程序输入框冒泡事件的解决
    empty: function (e) {

    },

    // 获取实时输入的数量
    getNum: function (e) {
      var value = e.detail.value;
      // 定制页面过来的商品单价
      var num = e.detail.value;
      console.log(e.detail.cursor)
      if(num==0||num==""){
        num=1;
      }
      this.setData({
        newNum:num,
      })
    },

    // 确认
    sureBox: function (e) {
      var num = this.data.newNum;
      if (num == 0||num == '') {
        this.setData({
          num: 1,
        })
        this.properties.num = 1;
        wx.showToast({
          title: '该宝贝不能减少了哦',
          icon: 'none',
        })
      }
      this.setData({
        isBox: !this.data.isBox,
      })

      var unitPrice = this.properties.unitPrice;
      this.setData({
        totalPrice: num * unitPrice,
      })

      console.log(this.data.totalPrice)
      // 将数据传递过去
      this.triggerEvent("onGetNum", {
        "totalPrice": this.data.totalPrice,
        "num": num,
        "tapIndex": this.properties.tapIndex, // 购物车分类索引
        "goodIndex": this.properties.goodIndex, // 购物车当前产品索引
        "cartId": this.properties.cartId, // 当前购物车id
      })
    },
  },

  attached() {
    // 第二种方式通过组件的生命周期函数执行代码
    this.setData({
      num: this.properties.num,
      numNew:this.properties.num,
    })
    // console.log('数量:' + this.properties.num)
  },
})
View Code

 

二、页面:

1.json文件:

"calculation":"../comment/calculation/calculation",其中calculation是要在页面中引用时用到的标签
{
  "navigationBarTitleText":"购物车",
  "usingComponents": {
    "calculation":"../comment/calculation/calculation",
    "login":"../comment/authorize/authorize"
  }
}
View Code

2.页面

<calculation unitPrice="{{item.price}}" num="{{item.count}}" tapIndex="{{index}}"
                  goodIndex="{{childindex}}" cartId="{{item.id}}" bind:onBindPlus="onBindPlus"
                  bind:onBindMinus="onBindMinus" bind:onGetNum="onGetNum" wx:if="{{item.isChecked}}">
                </calculation>
View Code

 

3.js

// 1、点击+数量价格变化
  onBindPlus: function (e) {
    this.tapCalculation(e);
  },
  // 2、点击-数量价格变化
  onBindMinus: function (e) {
    this.tapCalculation(e);
  },
  // 3、输入数量价格变化
  onGetNum: function (e) {
    this.tapCalculation(e);
  },

  // 点击数量更新数据及计算价格
  tapCalculation: function (e) {
    // console.log(e.detail)
    let tapIndex = e.detail.tapIndex; // 点击时大分类索引
    let goodIndex = e.detail.goodIndex; // 分类下产品索引
    let count = e.detail.num;

    let index = e.detail.tapindex;
    this.setData({
      ['cartList[' + tapIndex + '].cartGoods[' + goodIndex + '].totalPrice']: e.detail.totalPrice, // 组件过来的总价
      ['cartList[' + tapIndex + '].cartGoods[' + goodIndex + '].count']: count,
    })
    // console.log(this.data.cartList)
    this.updateCount(e.detail.cartId, count)
    this.calaData()
  },
View Code

 

三、传值解析

1.组件向页面传值:

(1)组件js -- this.triggerEvent("页面要用到方法名", {参数});

// 将点击减后的数据传递过去
      this.triggerEvent("onBindMinus", {
        "totalPrice": this.data.totalPrice,
        "num": num,
        "tapIndex": this.properties.tapIndex, // 购物车分类索引
        "goodIndex": this.properties.goodIndex, // 购物车当前产品索引
        "cartId": this.properties.cartId, // 当前购物车id
      })
    },

// 将输入数字的数据传递过去
      this.triggerEvent("onGetNum", { })

 // 将点击+号的数据传递过去
      this.triggerEvent("onBindMinus", {})
    },
View Code

 

 

(2).页面接收传递过来的值:bind:onBindPlus="onBindPlus"  bind:onBindMinus="onBindMinus" bind:onGetNum="onGetNum"

 <calculation unitPrice="{{item.price}}" num="{{item.count}}" tapIndex="{{index}}"
                  goodIndex="{{childindex}}" cartId="{{item.id}}" bind:onBindPlus="onBindPlus"
                  bind:onBindMinus="onBindMinus" bind:onGetNum="onGetNum" wx:if="{{item.isChecked}}">
                </calculation>
View Code
 
(3).js对处理接收的值
  
// 点击-数量价格变化
  onBindMinus: function (e) {
 let tapIndex = e.detail.tapIndex; // 点击时大分类索引
    let goodIndex = e.detail.goodIndex; // 分类下产品索引
    let count = e.detail.num;
 // 取到值再进行相应的价格运算,省略
  },
View Code

 

 
2.页面向组件传值
(1)页面传递值给组件: unitPrice="{{item.price}}" num="{{item.count}}" tapIndex="{{index}}" goodIndex="{{childindex}}" cartId="{{item.id}}" 
 <calculation unitPrice="{{item.price}}" num="{{item.count}}" tapIndex="{{index}}"
                  goodIndex="{{childindex}}" cartId="{{item.id}}" bind:onBindPlus="onBindPlus"
                  bind:onBindMinus="onBindMinus" bind:onGetNum="onGetNum" wx:if="{{item.isChecked}}">
                </calculation>
View Code

 

(2)组件接收传递过来的值(用组件的属性列表properties接收,取值时只需要this.properties.unitPrice

/**
   * 组件的属性列表 
   */
  properties: {
    unitPrice: { // 接收传递过来的数据
      type: Number,
      value: 0,
    },
    num: { // 接收传递过来的num
      type: Number,
      value: 1,
    },
    tapIndex: { // 点击数量是,当前产品所属的大分类索引
      type: Number,
      value: 0,
    },
    goodIndex: { // 点击时当前购物车产品的索引
      type: Number,
      value: 0,
    },
    cartId: { // 购物车id
      type: String,
    },
  },
View Code

 

posted @ 2021-01-25 15:50  骑蝴蝶飞  阅读(550)  评论(0编辑  收藏  举报