微信小程序项目开发实战:用WePY、mpvue、Taro打造高效的小程序
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

2.1 小程序的视图容器

视图容器作为小程序最常见的组件之一,如Web开发中的<div></div>一样常用,或者说,<view></view>就和基础的<div></div>效果一样。而使用不同视图容器,可以让开发者迅速开发出不同的视图效果。

因篇幅有限,本书并没有罗列出所有组件的每一种属性。本书的目的是告诉读者组件的基本用法和常见应用场景并给出实例,未对所有组件的每个属性进行详细解析。微信官方的文档提供了非常好的教学内容、相关实例和更好的查阅方式。当读者需要实现某种功能并且确定使用的组件时,可以在微信公众平台的小程序文档中非常快地查阅和学习。

2.1.1 最基础的组件:view

view是最基础的视图组件,相当于HTML中的<div></div>组件,但和网页开发不同的是,小程序的开发并不推荐大量使用该标签。作为一个崇尚性能和精简的轻量程序,大量嵌套使用view标签,可能导致小程序性能降低。

view组件最常见的用法如下所示。

<view style="font-size:20rpx;color:#ababab">
这是view组件
</view>

上述代码实现了一个最简单的<view></view>标签,并且在该标签中显示了一些文字。在该标签上进行了简单的文字样式设定,包括设定字体大小和字体颜色。小程序的所有标签还支持定义class的样式。

注意:这里的rpx是小程序中特有的单位,该单位会随着客户端手机分辨率的不同而进行自主的调节,推荐所有的字体单位都使用rpx。

2.1.2 可滚动视图区域:scroll-view

可滚动视图区域并不常见,最大的一个应用应该是实现整页的滚动视图。通过scroll-view组件,可以实现一个单页面的切换,以实现view组件不容易实现的页面轮播或其他应用。

2.1.3 轮播图片:swiper

swiper是用于实现轮播图片的一个自带组件,只需要简单地进行图片的配置,以及切换动画、时间、位置等的配置。

swiper的结构如下所示。

<swiper indicator-dots="{{indicatorDots}}"
  autoplay="{{autoplay}}" interval="{{interval}}" duration="{{duration}}">
  <block wx:for="{{imgUrls}}">
    <swiper-item>
      <image src="{{item}}" class="slide-image" width="355" height="150"/>
    </swiper-item>
  </block>
</swiper>
Page({
  data: {
    imgUrls: [
      'http://img02.tooopen.com/images/20150928/tooopen_sy_143912755726.jpg',
      'http://img06.tooopen.com/images/20160818/tooopen_sy_175866434296.jpg',
      'http://img06.tooopen.com/images/20160818/tooopen_sy_175833047715.jpg'
    ],
    indicatorDots: false,
    autoplay: false,
    interval: 5000,
    duration: 1000
  },
}]

在<swiper>标签中,每一张图片和内容需要使用一个<swiper-item>进行包裹,当有多个节点时,可以使用wx:for或者WePY中的<repeat>标签进行循环显示。

2.1.4 可移动视图容器:movable-view

movable-view组件用于完成一些特殊样式的视图容器,可以在页面中实现拖曳滑动,并且可以控制滑动的方向,甚至提供滑动时的惯性、阻尼、摩擦等。

movable-view组件提供了两个特殊事件,如表2-1所示。

表2-1 movable-view组件提供了两个特殊事件

注意:movable-view必须设置width和height属性,默认为10px。movable-view默认为绝对定位,top和left属性为0px。movable-view必须位于<movable-area/>组件中,并且必须是直接子节点,否则不能移动。

在movable-view中需要移动的区域使用movable-area标签进行包裹。该组件可以组合放置在需要拖动的场景中,比如在某些更换头像或者生成背景的小程序中,原本使用Canvas才可以实现的效果。通过该组件可以减少资源的使用。

当然,这类组件也可用于实现类似于安卓中的抽屉,或左右滑动删除、切换的操作。

movable-view基本的使用方法如下所示。

<view>移动视图控件</view>
<!-- 创建一个move-area -->
<movable-area style="width:100%;height:1000rpx;background:gray;">
  <!-- 可以移动view黄色、宽高100rpx-->
  <movable-view style='background:yellow;width:100rpx;height:100rpx;' direction=
"all">
  </movable-view>
  <!-- 可以移动view红色、宽高100rpx-->
  <movable-view style='background:red;width:100rpx;height:100rpx;' direction=
"all" bindtap='redclcik' bindtouchmove='redmove'>
  </movable-view>
</movable-area>
redclcik:function(sender){
    wx.showModal({
      title: '单击红色',
      content: '',
    })
    console.log(sender);
  },
  redmove:function(sender){
    console.log(sender);
    // console.log(sender.changedTouches[0].pageX);

  },

2.1.5 超过原生组件的层级:cover-view和cover-image

使用过Canvas、map、video等原生组件的开发者都知道,在小程序中,原生组件的层级是直接覆盖于所有的组件之上的,即不受z-index属性的影响。这样虽然保证了原生组件的效果,但是极大影响了一些业务的展开。为了解决这个问题,小程序为我们提供了新的组件。

cover-view和cover-image是覆盖在原生组件之上的文本视图,可覆盖的原生组件包括map、video、canvas、camera、live-player、live-pusher,只支持嵌套cover-view、cover-image,可在cover-view中使用button。

注意:从基础库2.2.4起支持touch相关事件,从基础库2.1.0起支持设置scale rotate的css样式,在自定义组件嵌套cover-view时,自定义组件的slot及其父节点暂不支持通过wx:if控制显示和隐藏,否则会导致cover-view不显示。

虽然并不是非常完善的功能,但是对于一些需要覆盖在原生组件上的业务场景,已经完全足够了,其使用方法如下所示。

.controls {
  position: relative;
  top: 50%;
  height: 50px;
  margin-top: -25px;
  display: flex;
}
.play,.pause,.time {
  flex: 1;
  height: 100%;
}
.time {
  text-align: center;
  background-color: rgba(0,0,0,.5);
  color: white;
  line-height: 50px;
}
.img {
  width: 40px;
  height: 40px;
  margin: 5px auto;
}
<video id="myVideo" src="http://wxsnsdy.tc.qq.com/105/20210/
snsdyvideodownload?filekey=30280201010421301f0201690402534804102ca905ce620b124
1b726bc41dcff44e00204012882540400&bizid=1023&hy=SH&fileparam=302c0201010425302
30204136ffd93020457e3c4ff02024ef202031e8d7f02030f42400204045a320a0201000400"
controls="{{false}}" event-model="bubble">
  <cover-view class="controls">
    <cover-view class="play" bindtap="play">
      <cover-image class="img" src="/path/to/icon_play" />
    </cover-view>
    <cover-view class="pause" bindtap="pause">
      <cover-image class="img" src="/path/to/icon_pause" />
    </cover-view>
    <cover-view class="time">00:00</cover-view>
  </cover-view>
</video>
Page({
  onReady(){
    this.videoCtx = wx.createVideoContext('myVideo')
  },
  play(){
    this.videoCtx.play()
  },
  pause(){
    this.videoCtx.pause()
  }
})

具体的实例可以参照2.3.4节使用的cover-view效果。