第五章 “我要点爆”微信小程序云开发实例之从云端获取数据制作首页

下面我们来实现从云端获取数据,完成首页世界页面index的制作,首页分为4个数据列表导航页面,页面具体内容如下:

推荐:为用户推荐最新的点爆信息,它包含文本点爆内容和语音点爆内容。

文爆:筛选出文字点爆内容,只显示文字点爆内容。

音爆:筛选出语音点爆内容,只显示语音点爆内容。

爆榜:将点爆内容取出前20名进入排行。

【实现页面内数据列表的滚动和导航切换后,每个导航下数据列表都在顶部】

由于我们使用的头部导航栏是通过数据绑定在同一页面进行切换,所以当一个页面内数据列表向下滚动后,切换导航后页面的scroolTop值已经改变,所以当从一个滚动过的导航数据列表切换到到另一个导航数据列表时,不能保持当前导航下数据列表在顶部,而会包含一个scroolTop值,下面我们就来实现导航切换后,数据列表为顶部位置。

在wxml中使用可滚动试图区域scrool-view组件做为数据列表的容器,wxml中设置组件scroll-y="true"为y轴滚动,同时通过数据绑定scroll-top="{{scrollTop}}"设置竖向滚动条位置,设置组件绝对定位样式。

<scroll-view scroll-y="true" scroll-top="{{scrollTop}}" style="position:absolute; top:0; left:0; right:0; bottom:0;">
</scroll-view>

在js中,我们给scrollTop设置初值为0,让页面打开时滚动条就在顶部

data: {
  scrollTop: 0,
}

在每一次导航切换时,都将scrollTop的值重新赋值为0,保证当前导航页面滚动条在顶部。

this.setData({
  scrollTop: 0
})

【实现数据列表加载功能】

在组件中使用wx:for进行控制属性绑定一个数组,使用数组中各项的数据重复渲染该组件。
wx:for-item制定数组当前元素变量名,将数据的id赋值给wx:key以便提高渲染效率,同时将数据的id赋值给id属性,方便跳转到详情页面。

block标签,使用block标签来进行条件渲染, 并不是一个组件,它仅仅是一个包装元素,不会在页面中做任何渲染,只接受控制属性。使用block标签来进行条件渲染是一个很好的选择。

<view class="content_item"  wx:for="{{tarray}}"
wx:for-item="recommend" wx:key="{{recommend._id}}" id="{{recommend._id}}">
  <block wx:if="{{recommend.text}}">
    <text>{{recommend.text}}</text>
  </block>
</view>

当然,我们也可以直接在组件中使用wx:if,例如在文爆中控制只显示文本类爆文

<view class="content_item" bindtap="goopen" wx:for="{{tarray}}"
wx:for-item="textbao" wx:key="{{textbao._id}}" id="{{textbao.detailId}}"
 wx:if="{{textbao.text}}">
</view>

在data中初始化一个数组tarray,用于保存从数据库中获取到的推荐爆文数据

data: {
  tarray: [],
}

orderBy指定按照时间逆序排序,limit指定查询结果集数量上限为20,即最开始只从数据库获取20条数据,通过上拉加载来获取更多的数据

// 推荐数据
  db.collection('bao').orderBy('time',     'desc').limit(20)
    .get();

上拉加载,设置一个lnum1变量来记录当前页面有多少条数据,每次上拉获取10条数据,使用skip实现上拉加载更多,skip指定返回结果从指定序列后的结果开始返回

// 推荐数据
db.collection('bao').orderBy('wtime', 'desc').skip(lnum1).limit(10)
.get();

index.wxml完整代码

<!--index.wxml-->
<view class="header">
  <label>
    <input type="text" bindtap="search"/>
  </label>
  <view class="navbar">
      <text class="item {{currentTab==index ? 'active' : ''}}" wx:for="{{navber}}"
      data-index="{{index}}" wx:key="unique" bindtap="navbarTap">{{item}}</text>
  </view>
</view>
<scroll-view  class="content" scroll-y="true" scroll-top="{{scrollTop}}"
bindscrolltolower="thebottom" style="position:absolute; top:0; left:0; right:0; bottom:0;">
<view class="content_box">
<!-- 推荐数据列表 -->
  <view class="recommend {{currentTab==0 ? 'show' : 'hide'}}">
    <view class="content_item" bindtap="goopen" wx:for="{{tarray}}"
    wx:for-item="recommend" wx:key="{{recommend._id}}" id="{{recommend._id}}">
      <view class="citem_left">
        <image src="/images/tou1.png"></image>
      </view>
      <block wx:if="{{recommend.text}}">
        <view class="citem_mid">
          <text>{{recommend.text}}</text>
          <text>点爆方式:</text><text>{{recommend.wway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{recommend.temperature}}</text>
        </view>
      </block>
      <block wx:if="{{recommend.filename}}">
        <view class="citem_mid">
          <image src="/images/yuyin.png"></image>
          <text>点爆方式:</text><text>{{recommend.yway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{recommend.temperature}}</text>
        </view>
      </block>
    </view>
  </view>
  <!-- 文爆 -->
  <view class="textbao {{currentTab==1 ? 'show' : 'hide'}}">
    <view class="content_item" bindtap="goopen" wx:for="{{tarray}}"
    wx:for-item="textbao" wx:key="{{textbao._id}}" id="{{textbao.detailId}}" wx:if="{{textbao.text}}">
      <view class="citem_left">
        <image src="/images/tou1.png"></image>
      </view>
      <view class="citem_mid">
        <text>{{textbao.text}}</text>
        <text>点爆方式:</text><text>{{textbao.wway}}</text>
      </view>
      <view class="citem_right">
        <image src="/images/re.png"></image>
        <text>{{textbao.temperature}}</text>
      </view>
    </view>
  </view>
  <!-- 音爆 -->
  <view class="voicebao {{currentTab==2 ? 'show' : 'hide'}}">
    <view class="content_item" bindtap="goopen" wx:for="{{tarray}}"
    wx:for-item="voicebao" wx:key="{{voicebao._id}}" id="{{voicebao.detailId}}" wx:if="{{voicebao.filename}}">
      <view class="citem_left">
        <image src="/images/tou1.png"></image>
      </view>
      <view class="citem_mid">
        <image src="/images/yuyin.png"></image>
        <text>点爆方式:</text><text>{{voicebao.yway}}</text>
      </view>
      <view class="citem_right">
        <image src="/images/re.png"></image>
        <text>{{voicebao.temperature}}</text>
      </view>
    </view>
  </view>
  <!-- 爆榜 -->
  <view class="rankings {{currentTab==3 ? 'show' : 'hide'}}">
    <view class="content_item" bindtap="goopen" wx:for="{{barray}}"
    wx:for-item="rankings" wx:key="{{rankings._id}}" id="{{rankings._id}}">
      <view class="number">
        {{index+1}}
      </view>
      <view class="citem_left">
        <image src="/images/tou1.png"></image>
      </view>
      <block wx:if="{{rankings.text}}">
        <view class="citem_mid">
          <text>{{rankings.text}}</text>
          <text>点爆方式:</text><text>{{rankings.wway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{rankings.temperature}}</text>
        </view>
      </block>
      <block wx:if="{{rankings.filename}}">
        <view class="citem_mid">
          <image src="/images/yuyin.png"></image>
          <text>点爆方式:</text><text>{{rankings.yway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{rankings.temperature}}</text>
        </view>
      </block>
    </view>
  </view>
</view>
</scroll-view>

index.js完整代码

//index.js
//获取应用实例
const app = getApp()
Page({
  data: {
    navber: ['推荐', '文爆', '音爆', '爆榜'],
    currentTab: 0,
    tarray: [],
    barray: [],
    lnum1: 20,//记录当前已有数据数量
    stext: '',
    scrollTop: 0,
  },
  //上导航切换
  navbarTap: function (e) {
    this.setData({
      scrollTop: 0
    })
    this.setData({
      currentTab: e.currentTarget.dataset.index
    })
  },
  search: function (e) {
    wx.navigateTo({
      url: '../search/search'
    })
  },
  onLoad: function () {
    wx.showLoading({
      title: '加载中',
      mask: true
    })
    const db = wx.cloud.database()
    // 推荐数据
    db.collection('bao').orderBy('time', 'desc').limit(20)
      .get({
        success: res => {
          this.setData({
            tarray: res.data
          })
        }
      });
    // 排行数据
    db.collection('bao').orderBy('temperature', 'desc').limit(20)
      .get({
        success: res => {
          this.setData({
            barray: res.data
          })
        }
      });
    //模拟加载
    setTimeout(function () {
      wx.hideLoading()
    }, 1500);
  },
  goopen: function (e) {
    //获取当前内容的标识id,保存,方便进入查询
    var id = e.currentTarget.id
    wx.setStorageSync('id', id)
    wx.navigateTo({
      url: '../detail/detail',
    });
  },
  //下拉刷新
  onPullDownRefresh: function () {
    wx.showNavigationBarLoading() //在标题栏中显示加载
    wx.showLoading({
      title: '加载中',
      mask: true
    })
    const db = wx.cloud.database()
    // 推荐数据
    db.collection('bao').orderBy('time', 'desc').limit(20)
      .get({
        success: res => {
          this.setData({
            tarray: res.data
          })
        }
      });
    // 排行数据
    db.collection('bao').orderBy('temperature', 'desc').limit(20)
      .get({
        success: res => {
          this.setData({
            barray: res.data
          })
        }
      });
    //模拟加载
    setTimeout(function () {
      // complete
      wx.hideNavigationBarLoading() //完成停止加载
      wx.stopPullDownRefresh() //停止下拉刷新
      wx.hideLoading()
    }, 1500);
  },
  //上拉加载
  thebottom: function () {
    var lnum1 = this.data.lnum1
    const db = wx.cloud.database()
    if (this.data.currentTab == 0) {
      // 显示加载图标
      wx.showLoading({
        title: '玩命加载中',
      })
      // 推荐数据
      db.collection('bao').orderBy('wtime', 'desc').skip(lnum1).limit(10)
        .get({
          success: res => {
            this.setData({
              tarray: this.data.tarray.concat(res.data),
              lnum1: lnum1 + 10
            })
            // 隐藏加载框
            wx.hideLoading()
          }
        });
    }
  }
})

运行效果图:

搜索框搜索页面的实现

app.json中加入search页面路径,编写搜索页面样式

search.wxml

<view class="header">
  <label>
    <input type="text" bindconfirm="search" bindinput="content"
    confirm-type="search" focus="true"/>
    <icon type="search" size="25" bindtap="search"/>
  </label>
</view>
<view class="content">
  <text class="nohave {{bol ? 'show' : 'hide'}}">你搜的什么吖,我莫得!</text>
  <view class="searchArray">
    <view class="content_item" bindtap="goopen" wx:for="{{tarray}}"
    wx:for-item="searchArray" wx:key="{{searchArray._id}}" id="{{searchArray._id}}">
      <view class="citem_left">
        <image src="/images/tou1.png"></image>
      </view>
      <block wx:if="{{searchArray.text}}">
        <view class="citem_mid">
          <text>{{searchArray.text}}</text>
          <text>点爆方式:</text><text>{{searchArray.wway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{searchArray.temperature}}</text>
        </view>
      </block>
      <block wx:if="{{searchArray.filename}}">
        <view class="citem_mid">
          <image src="/images/yuyin.png"></image>
          <text>点爆方式:</text><text>{{searchArray.yway}}</text>
        </view>
        <view class="citem_right">
          <image src="/images/re.png"></image>
          <text>{{searchArray.temperature}}</text>
        </view>
      </block>
    </view>
  </view>
</view>

db.RegExp介绍:数据库支持正则表达式查询,开发者可以在查询语句中使用 JavaScript 原生正则对象或使用 db.RegExp 方法来构造正则对象然后进行字符串匹配。在查询条件中对一个字段进行正则匹配即要求该字段的值可以被给定的正则表达式匹配,注意正则表达式不可用于 db.command 内(如 db.command.in)。

使用db.RegExp方法构造正则对象然后进行字符串匹配,通过在对bao集合中text内容进行查询时,给text赋值一个db.RegExp正则对象,这样就实现了对text的模糊查询。

db.collection('bao').where({
      //使用正则查询,实现对搜索的模糊查询
      text: db.RegExp({
        regexp: value,
        //从搜索栏中获取的value作为规则进行匹配。
        options: 'im',
        //大小写不区分
      })
    }).get()

search.js完整代码

// pages/search/search.js
Page({
  data: {
    tarray: [],
    stext: '',
    bol: false,
  },
  search: function () {
    wx.showLoading({
      title: '玩命加载中',
    })
    this.setData({
      tarray: []
    })
    //连接数据库
    const db = wx.cloud.database()
    var that = this
    var value = this.data.stext
    db.collection('bao').where({
      //使用正则查询,实现对搜索的模糊查询
      text: db.RegExp({
        regexp: value,
        //从搜索栏中获取的value作为规则进行匹配。
        options: 'im',
        //大小写不区分
      })
    }).get({
      success: res => {
        console.log(res)
        if (res.data.length == 0) {
          that.setData({
            bol: true
          })
        } else {
          that.setData({
            tarray: res.data
          })
        }
        wx.hideLoading()
      }
    })
  },
  content: function (e) {
    this.setData({
      stext: e.detail.value
    })
  },
  goopen: function (e) {
    //获取当前内容的标识id,保存,方便进入查询
    var id = e.currentTarget.id
    wx.setStorageSync('id', id)
    wx.navigateTo({
      url: '../detail/detail',
    });
  },
})

运行效果图

至此,首页就制作完成了,可以说小程序的主体已经差不多了,云开发的便利我们也都尝试了。那么大家就快进行实践吧!

原文地址:https://www.cnblogs.com/xiedong2016/p/10926040.html

时间: 2024-10-09 20:44:05

第五章 “我要点爆”微信小程序云开发实例之从云端获取数据制作首页的相关文章

微信小程序云开发-从0打造云音乐全栈小程序

第1章 首门小程序“云开发”课程,你值得学习本章主要介绍什么是小程序云开发以及学习云开发的重要性,并介绍项目的整体架构,真机演示项目功能,详细介绍整体课程安排.课程适用人群以及需要掌握的前置知识.通过本章的学习,能够使大家对本门课程有一个整体的了解.... 第2章 云开发介绍以及从0构建项目本章会详细介绍小程序云开发与Serverless,并介绍如何开通小程序云开发及控制台的功能,并且初始化项目代码,讲解airbnb/javascript代码规范. 第3章 播放列表功能实现本章完成歌单列表与歌曲

微信小程序云开发

使用微信小程序云开发,可以不需要后端的参与,前端直接使用数据库. 第一步,新建一个空的云开发项目 在project.config.json 文件可以看见 "miniprogramRoot": "miniprogram/",   表示为小程序页面的文件 "cloudfunctionRoot": "cloudfunctions/", 表示云函数文件,即 在云端定义一些函数,运行环境为 nodejs, 可以做一些运算操作,然后将结果

【微信小程序云开发】从陌生到熟悉

前言 微信小程序在9月10号正式上线了云开发的功能,弱化后端和运维概念,以前开发一个小程序需要申请一个小程序,准备一个https的域名,开发需要一个前端一个服务端,有了云开发只有申请一个小程序,一个前端就能搞定,真的是零成本. 云开发三大基础能力 云函数:运行在微信服务器上的函数,处理微信相关操作有天然优势,如获得用户信息异常方便(以前服务端解析很麻烦) 数据库:一个小程序可以直接操作的JSON数据库,可以直接操作数据库,不在需要服务端了. 存储:用来存储文件和图片 阅读本文之前最好对微信小程序

微信小程序云开发入门到发布上线

初始化项目 起步说明[非小白教程] 适合人群[建议快速看文档,对着写一遍] 看过官方文档,并简单的写过 起步教程 云开发文档 熟悉vue/es6 小程序注册[微信公众平台] 获取appid[微信公众平台-开发-开发设置] 新建小程序云开发项目 新建项目选择一个空目录,填入 AppID(使用云开发能力必须填写 AppID) 勾选创建 "小程序云开发 " 点击新建即可得到一个展示云开发基础能力的示例小程序. 该小程序与普通 QuickStart 小程序有以下不同需注意: 无游客模式.也不可

微信小程序云开发更换云开发环境

小程序云开发环境初始化默认是第一个环境,但是我们可以指定环境id //app.js App({ onLaunch: function () { if (!wx.cloud) { console.error('请使用 2.2.3 或以上的基础库以使用云能力') } else { wx.cloud.init({ env: "kindear-fd77cd", traceUser: true, }) } this.globalData = {} } }) 就可以成功更换云开发环境. 原文地址:

微信小程序云开发之云函数创建

云函数 云函数是一段运行在云端的代码,无需管理服务器,在开发工具内编写.一键上传部署即可运行后端代码. 小程序内提供了专门用于云函数调用的 API.开发者可以在云函数内使用 wx-server-sdk 提供的 getWXContext 方法获取到每次调用的上下文(appid.openid 等),无需维护复杂的鉴权机制,即可获取天然可信任的用户登录态(openid). 1. 云函数创建 根据官网提示,创建一个云函数,命名为 add, 功能是将 a , b 两数相加,步骤如下: 在文件夹 cloud

微信小程序云开发导入json数据报错:导入数据库失败, Error: Poll error, 导入数据任务(id:528440)异常,错误信息:line 1, column 750: bare &quot; in non-quoted-field

错误信息如下: 导入数据库失败, Error: Poll error, 导入数据任务(id:528440)异常,错误信息:line 1, column 750: bare " in non-quoted-field 导入数据库失败, Error: Poll error, 导入数据任务(id:528445)异常,错误信息:解析json文档错误,请检查导入文件格式,错误详情如下:invalid character ',' looking for beginning of value 导入JSON格式

微信小程序云开发--数据库操作

在app.json中开通云服务功能: "cloud":true, 在app.js中找到对应的云开发环境: 一般可以有两个环境 App({ onLaunch: function () { if (!wx.cloud) { console.error('请使用 2.2.3 ') } else { wx.cloud.init({ env:'partyassistant-bdd77f', traceUser: true, }) } this.globalData = { } } }) 在需要使

微信小程序 云开发 数据库 请求数据

js: data:{ listDatas:null//请求的数据存在这个数组里面 } onLoad: function (options) { const db = wx.cloud.database(); db.collection('otheritems').get().then(res => {//otheritems是数据库里面集合的名称 console.log(res); //如果更新数据成功则输出成功信息 var that = this; that.setData({ listDat