TDesign电商小程序模板解析02-首页功能(二)

本文涉及的产品
云解析 DNS,旗舰版 1个月
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
全局流量管理 GTM,标准版 1个月
简介: TDesign电商小程序模板解析02-首页功能(二)

3 goods-card组件


在components文件夹下再新建一个goods-card文件夹

然后在goods-card文件夹新建一个Page

index.json

{
    "component": true,
    "usingComponents": {
        "price": "/components/price/index",
        "t-icon": "tdesign-miniprogram/icon/icon",
        "t-image": "/components/webp-image/index"
    }
    }


好家伙真还是俄罗斯套娃,这个组件又套了两个组件,需要继续新建

index.js

Component({
  options: {
    addGlobalClass: true,
  },
  properties: {
    id: {
      type: String,
      value: '',
      observer(id) {
        this.genIndependentID(id);
        if (this.properties.thresholds?.length) {
          this.createIntersectionObserverHandle();
        }
      },
    },
    data: {
      type: Object,
      observer(data) {
        if (!data) {
          return;
        }
        let isValidityLinePrice = true;
        if (data.originPrice && data.price && data.originPrice < data.price) {
          isValidityLinePrice = false;
        }
        this.setData({ goods: data, isValidityLinePrice });
      },
    },
    currency: {
      type: String,
      value: '¥',
    },
    thresholds: {
      type: Array,
      value: [],
      observer(thresholds) {
        if (thresholds && thresholds.length) {
          this.createIntersectionObserverHandle();
        } else {
          this.clearIntersectionObserverHandle();
        }
      },
    },
  },
  data: {
    independentID: '',
    goods: { id: '' },
    isValidityLinePrice: false,
  },
  lifetimes: {
    ready() {
      this.init();
    },
    detached() {
      this.clear();
    },
  },
  pageLifeTimes: {},
  methods: {
    clickHandle() {
      this.triggerEvent('click', { goods: this.data.goods });
    },
    clickThumbHandle() {
      this.triggerEvent('thumb', { goods: this.data.goods });
    },
    addCartHandle(e) {
      const { id } = e.currentTarget;
      const { id: cardID } = e.currentTarget.dataset;
      this.triggerEvent('add-cart', {
        ...e.detail,
        id,
        cardID,
        goods: this.data.goods,
      });
    },
    genIndependentID(id) {
      let independentID;
      if (id) {
        independentID = id;
      } else {
        independentID = `goods-card-${~~(Math.random() * 10 ** 8)}`;
      }
      this.setData({ independentID });
    },
    init() {
      const { thresholds, id } = this.properties;
      this.genIndependentID(id);
      if (thresholds && thresholds.length) {
        this.createIntersectionObserverHandle();
      }
    },
    clear() {
      this.clearIntersectionObserverHandle();
    },
    intersectionObserverContext: null,
    createIntersectionObserverHandle() {
      if (this.intersectionObserverContext || !this.data.independentID) {
        return;
      }
      this.intersectionObserverContext = this.createIntersectionObserver({
        thresholds: this.properties.thresholds,
      }).relativeToViewport();
      this.intersectionObserverContext.observe(
        `#${this.data.independentID}`,
        (res) => {
          this.intersectionObserverCB(res);
        },
      );
    },
    intersectionObserverCB() {
      this.triggerEvent('ob', {
        goods: this.data.goods,
        context: this.intersectionObserverContext,
      });
    },
    clearIntersectionObserverHandle() {
      if (this.intersectionObserverContext) {
        try {
          this.intersectionObserverContext.disconnect();
        } catch (e) {}
        this.intersectionObserverContext = null;
      }
    },
  },
});


这个组件里边的代码会更复杂一点


index.wxml

<view
  id="{{independentID}}"
  class="goods-card"
  bind:tap="clickHandle"
  data-goods="{{ goods }}"
>
  <view class="goods-card__main">
  <view class="goods-card__thumb" bind:tap="clickThumbHandle">
    <t-image
     wx:if="{{ !!goods.thumb }}"
     t-class="goods-card__img"
     src="{{ goods.thumb }}"
     mode="aspectFill"
     lazy-load
    />
  </view>
  <view class="goods-card__body">
    <view class="goods-card__upper">
    <view wx:if="{{ goods.title }}" class="goods-card__title">
      {{ goods.title }}
    </view>
    <view wx:if="{{ goods.tags && !!goods.tags.length }}" class="goods-card__tags">
      <view
       wx:for="{{ goods.tags }}"
       wx:key="index"
       wx:for-item="tag"
       class="goods-card__tag"
       data-index="{{index}}"
      >
      {{tag}}
      </view>
    </view>
    </view>
    <view class="goods-card__down">
    <price
      wx:if="{{ goods.price }}"
      wr-class="spec-for-price"
      symbol-class="spec-for-symbol"
      symbol="{{currency}}"
      price="{{goods.price}}"
    />
    <price
      wx:if="{{ goods.originPrice && isValidityLinePrice }}"
      wr-class="goods-card__origin-price"
      symbol="{{currency}}"
      price="{{goods.originPrice}}"
      type="delthrough"
    />
    <t-icon
      class="goods-card__add-cart"
      prefix="wr"
      name="cartAdd"
      id="{{independentID}}-cart"
      data-id="{{independentID}}"
      catchtap="addCartHandle"
      size="48rpx"
      color="#FA550F"
    />
    </view>
  </view>
  </view>
</view>


index.wxss

.goods-card {
  box-sizing: border-box;
  font-size: 24rpx;
  border-radius: 0 0 16rpx 16rpx;
  border-bottom: none;
}
.goods-card__main {
  position: relative;
  display: flex;
  line-height: 1;
  padding: 0;
  background: transparent;
  width: 342rpx;
  border-radius: 0 0 16rpx 16rpx;
  align-items: center;
  justify-content: center;
  margin-bottom: 16rpx;
  flex-direction: column;
}
.goods-card__thumb {
  flex-shrink: 0;
  position: relative;
  width: 340rpx;
  height: 340rpx;
}
.goods-card__thumb:empty {
  display: none;
  margin: 0;
}
.goods-card__img {
  display: block;
  width: 100%;
  height: 100%;
  border-radius: 16rpx 16rpx 0 0;
  overflow: hidden;
}
.goods-card__body {
  display: flex;
  flex: 1 1 auto;
  background: #fff;
  border-radius: 0 0 16rpx 16rpx;
  padding: 16rpx 24rpx 18rpx;
  flex-direction: column;
}
.goods-card__upper {
  display: flex;
  flex-direction: column;
  overflow: hidden;
  flex: 1 1 auto;
}
.goods-card__title {
  flex-shrink: 0;
  font-size: 28rpx;
  color: #333;
  font-weight: 400;
  display: -webkit-box;
  height: 72rpx;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  overflow: hidden;
  word-break: break-word;
  line-height: 36rpx;
}
.goods-card__tags {
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  margin: 8rpx 0 0 0;
}
.goods-card__tag {
  color: #fa4126;
  background: transparent;
  font-size: 20rpx;
  border: 1rpx solid #fa4126;
  padding: 0 8rpx;
  border-radius: 16rpx;
  line-height: 30rpx;
  margin: 0 8rpx 8rpx 0;
  display: block;
  overflow: hidden;
  white-space: nowrap;
  word-break: keep-all;
  text-overflow: ellipsis;
}
.goods-card__down {
  display: flex;
  position: relative;
  flex-direction: row;
  justify-content: flex-start;
  align-items: baseline;
  line-height: 32rpx;
  margin: 8rpx 0 0 0;
}
.goods-card__origin-price {
  white-space: nowrap;
  font-weight: 700;
  order: 2;
  color: #bbbbbb;
  font-size: 24rpx;
  margin: 0 0 0 8rpx;
}
.goods-card__add-cart {
  order: 3;
  margin: auto 0 0 auto;
  position: absolute;
  bottom: 0;
  right: 0;
}
.spec-for-price {
  font-size: 36rpx;
  white-space: nowrap;
  font-weight: 700;
  order: 1;
  color: #fa4126;
  margin: 0;
}
.spec-for-symbol {
  font-size: 24rpx;
}


总结


看首页功能,其实看wxml文件并不复杂,复杂在了既调用了组件库中的组件,又自己封装了很多组件,而且是俄罗斯套娃,一层嵌套一层,这么个看要想用熟练一套模板也不是简单的事情。

相关文章
|
17天前
|
缓存 NoSQL Java
京东电商下单黄金链路:防止订单重复提交与支付的深度解析
【10月更文挑战第21天】在电商领域,尤其是在像京东这样的大型电商平台中,防止订单重复提交与支付是一项至关重要的任务。
81 44
|
4月前
|
小程序 视频直播 UED
电商直播小程序系统开发:打造“直播+电商+社交”闭环
电商直播小程序成为商家与消费者互动的关键,通过微信提供的实时视频工具,实现流畅购物体验。系统功能包括直播预览、主播管理、红包互动、用户管理及闭环购物。它强化品牌效应,利用私域流量,简化流程并转化会员。开发涉及需求分析、设计规划、功能开发、测试优化及上线维护。企业需关注用户体验,以保持竞争力。寻求开发合作可联系相关人员。
|
3月前
|
机器学习/深度学习 供应链 大数据
【2023Mathorcup大数据】B题 电商零售商家需求预测及库存优化问题 python代码解析
本文提供了2023年MathorCup大数据竞赛B题的电商零售商家需求预测及库存优化问题的Python代码解析,涉及数据预处理、特征工程、时间序列预测、聚类分析以及模型预测性能评价等步骤。
173 0
|
1月前
|
编译器 C++
【C++】模板进阶:深入解析模板特化
【C++】模板进阶:深入解析模板特化
|
2月前
|
C# Android开发 开发者
Uno Platform 高级定制秘籍:深度解析与实践样式和模板应用,助你打造统一且高效的跨平台UI设计
【9月更文挑战第7天】Uno Platform 是一个强大的框架,支持使用 C# 和 XAML 创建跨平台 UI 应用,覆盖 Windows、iOS、Android、macOS 和 WebAssembly。本文介绍 Uno Platform 中样式和模板的应用,助力开发者提升界面一致性与开发效率。样式定义控件外观,如颜色和字体;模板则详细定制控件布局。通过 XAML 定义样式和模板,并可在资源字典中全局应用或嵌套扩展。合理利用样式和模板能简化代码、保持设计一致性和提高维护性,帮助开发者构建美观高效的跨平台应用。
50 1
|
3月前
|
小程序 前端开发 JavaScript
【电商新机遇】支付宝小程序如何助你打造爆款电商解决方案?揭秘背后的技术奥秘!
【8月更文挑战第27天】本文详细介绍如何利用支付宝小程序构建电商应用,覆盖从项目初始化、页面设计、功能开发到数据分析的全流程。首先,需注册开发者账号并安装相关工具;随后创建项目,并按示例配置基本页面结构;接着设计商品列表等界面布局;再实现商品展示等功能;最后运用支付宝提供的工具进行数据分析,以优化用户体验及营销策略。跟随本教程,您将能打造出一款完整的电商小程序。
88 1
|
3月前
|
存储 数据采集 API
提升店铺好评秘籍:淘宝商品评论接口与电商 API 接口的深度解析
该接口名为item_review,用于获取淘宝商品评论信息,支持HTTP GET或POST请求,体验API为c0b.cc/R4rbK2。主要请求参数包括商品ID(num_iid)、排序方式(sort)、页码(page)。响应参数涵盖评论内容(rate_content)、评论日期(rate_date)、评论图片(pics)、买家昵称(display_user_nick)、商品属性(auction_sku)
|
4月前
|
中间件 数据库 开发者
解析Python Web框架的四大支柱:模板、ORM、中间件与路由
【7月更文挑战第20天】Python Web框架如Django、Flask、FastAPI的核心包括模板(如Django的DTL和Flask的Jinja2)、ORM(Django的内置ORM与Flask的SQLAlchemy)、中间件(Django的全局中间件与Flask的装饰器实现)和路由(Django的urls.py配置与Flask的@app.route()装饰器)。这些组件提升了代码组织和数据库操作的便捷性,确保了Web应用的稳定性和可扩展性。
63 0
|
22天前
|
移动开发 小程序 数据可视化
基于npm CLI脚手架的uniapp项目创建、运行与打包全攻略(微信小程序、H5、APP全覆盖)
基于npm CLI脚手架的uniapp项目创建、运行与打包全攻略(微信小程序、H5、APP全覆盖)
148 3
|
29天前
|
小程序 API
微信小程序更新提醒uniapp
在小程序开发中,版本更新至关重要。本方案利用 `uni-app` 的 `uni.getUpdateManager()` API 在启动时检测版本更新,提示用户并提供立即更新选项,自动下载更新内容,并在更新完成后重启小程序以应用新版本。适用于微信小程序,确保用户始终使用最新版本。以下是实现步骤: ### 实现步骤 1. **创建更新方法**:在 `App.vue` 中创建 `updateApp` 方法用于检查小程序是否有新版本。 2. **测试**:添加编译模式并选择成功状态进行模拟测试。
40 0
微信小程序更新提醒uniapp

推荐镜像

更多