# 第一章:uniapp的介绍与使用
# 1.1:uni-app基本使用
# uni-app介绍 官方网页 (opens new window)
uni-app
是一个使用 Vue.js (opens new window) 开发所有前端应用的框架,开发者编写一套代码,可发布到iOS、Android、Web(响应式)、以及各种小程序(微信/支付宝/百度/头条/QQ/快手/钉钉/淘宝)、快应用等多个平台。
uni-app继承自Vue.js
,提供了完整的Vue.js
开发体验。
uni-app组件规范和扩展api与微信小程序的基本相同
即使不不做跨端应用,uni-app
同时也是更好的小程序开发框架。
具有vue和微信小程序的开发经验的人员,可快速上手uni-app
,开发出兼容多端的应用。
对于技术人员而言 :不用学习那么多的平台开发技术,研究那么多的前端框架,学会基于 vue 的 uni-app 就够了。
对公司而言 :更低的成本,覆盖更多的用户,uni-app 就是一个更高效的利器。
# 环境的搭建
安装编辑器 HbuilderX 下载地址 (opens new window)
HBuilderX是通用的前端开发工具,但为uni-app
做了特别强化。
下载App开发版,可开箱即用
配合使用微信开发者工具 下载地址 (opens new window)
# 初始化项目与运行
# 新建项目
- 点击 HbuilderX 菜单栏,文件 --> 新建 --> 项目
- 选择 uni-app ,填写项目名称与创建路径
# 运行项目
- 浏览器中运行:进入 uni-app项目,在菜单栏中点击运行 --> 运行到浏览器 --> 选择浏览器即可运行(不推荐使用)
- 微信开发者工具中运行:进入 uni-app项目,在菜单栏中点击运行 --> 运行到小程序模拟器 --> 选择微信开发者工具
- 手机模拟器中运行:进入 uni-app项目,在菜单栏中点击运行 --> 运行到手机或模拟器 --> 选择调试的手机
!注意:
- 如果是第一次使用微信小程序运行,需要先配置 微信开发者工具 的相关路径才能运行成功
- 如果是运行到手机或手机模拟器中,则需要先下载真机运行插件
# uni-app开发规范与目录结构
# 开发规范
为了实现微信小程序、原生App的跨端兼容,综合考虑编译速度、运行性能等因素,uni-app
约定了如下开发规范:
# 页面规范: Vue 单文件组件 (SFC) 规范
.vue
文件是一个自定义的文件类型,用类 HTML 语法描述一个 Vue 组件。每个 .vue
文件包含三种类型的顶级语言块 <template>
、<script>
和 <style>
,还允许添加可选的自定义块:
<template>
<div>
<p class="pColor">{{text}}</p>
</div>
</template>
<script>
export default {
data(){
return{
text:'文本'
}
}
}
</script>
<style>
.pColor{
color: red;
}
</style>
# 模板
- 每个
.vue
文件最多包含一个<template>
块。 - 每个
<template>
块中必须有一个根元素。
<template>
<div>
</div>
</template>
这里的 div
就是根元素,代码都写到这个根元素里面
# 脚本
- 每个
.vue
文件最多包含一个<script>
块。 - 任何匹配
.js
文件的 webpack 规则都将会运用到这个<script>
块的内容中。
# 样式
- 一个
.vue
文件可以包含多个<style>
标签。 <style>
标签可以有 scoped 属性来帮助你将样式封装到当前组件。具有不同封装模式的多个<style>
标签可以在同一个组件中混合使用。
<style scoped>
</style>
# Src 导入
如果喜欢把 .vue
文件分隔到多个文件中,你可以通过 src
属性导入外部文件:
<template src="./template.html"></template>
<style src="./style.css"></style>
<script src="./script.js"></script>
需要注意的是 src
导入遵循和 webpack 模块请求相同的路径解析规则,这意味着:
- 相对路径需要以
./
开始
# 组件标签靠近微信小程序规范
详见 uni-app 组件规范 (opens new window)
这里需要注意 不能使用标准HTML 标签,也不能用 js 对 dom 进行操作
# 接口能力(JS API)靠近微信小程序规范
但需将前缀 wx
替换为 uni
,详见uni-app接口规范 (opens new window)
# 数据绑定及事件处理同 Vue.js 规范
# 为兼容多端运行,建议使用flex布局进行开发
# 目录结构
pages.json
文件用来对 uni-app 进行全局配置,决定页面文件的路径、窗口样式、原生的导航栏、底部的原生tabbar 等
manifest.json
文件是应用的配置文件,用于指定应用的名称、图标、权限等。
App.vue
是我们的跟组件,所有页面都是在App.vue
下进行切换的,是页面入口文件,可以调用应用的生命周期函数。
main.js
是我们的项目入口文件,主要作用是初始化vue
实例并使用需要的插件。
uni.scss
文件的用途是为了方便整体控制应用的风格。比如按钮颜色、边框风格,uni.scss
文件里预置了一批scss变量预置。
pages
所有的页面存放目录
static
静态资源目录,例如图片等
components
组件存放目录
# 资源路径说明
# 模板内引入静态资源
template
内引入静态资源,如image
、video
等标签的src
属性时,可以使用相对路径或者绝对路径,形式如下
<!-- 绝对路径 -->
<image class="logo" src="/static/logo.png"></image>
<image class="logo" src="@/static/logo.png"></image>
<!-- 相对路径 -->
<image class="logo" src="../../static/logo.png"></image>
注意:
@
代表项目根目录,在cli项目中@指向src目录- 支付宝小程序组件内 image 标签不可使用相对路径
# js文件引入
js
文件或script
标签内引入js
文件时,可以使用相对路径和绝对路径,形式如下
// 绝对路径,@指向项目根目录,在cli项目中@指向src目录
import add from '@/common/add.js'
// 相对路径
import add from '../../common/add.js'
注意
- js文件不支持使用
/
开头的方式引入
# css引入静态资源
css
文件或style标签
内引入css
文件时(scss、less文件同理),可以使用相对路径或绝对路径(HBuilderX 2.6.6
)
/* 绝对路径 */
@import url('/common/uni.css');
@import url('@/common/uni.css');
/* 相对路径 */
@import url('../../common/uni.css');
注意
- 自
HBuilderX 2.6.6
起支持绝对路径引入静态资源,旧版本不支持此方式
css
文件或style标签
内引用的图片路径可以使用相对路径也可以使用绝对路径,需要注意的是,有些小程序端css文件不允许引用本地文件。
/* 绝对路径 */
background-image: url(/static/logo.png);
background-image: url(@/static/logo.png);
/* 相对路径 */
background-image: url(../../static/logo.png);
# 页面样式与布局
# 尺寸单位
uni-app
支持的通用 css 单位包括 px、rpx
- px 即屏幕像素
- rpx 即响应式px,一种根据屏幕宽度自适应的动态单位。以750宽的屏幕为基准,750rpx恰好为屏幕宽度。屏幕变宽,rpx 实际显示效果会等比放大,但在 App 端和 H5 端屏幕宽度达到 960px 时,默认将按照 375px 的屏幕宽度进行计算。
以下是对 rpx
的详细说明:
设计师在提供设计图时,一般只提供一个分辨率的图。
严格按设计图标注的 px 做开发,在不同宽度的手机上界面很容易变形。
而且主要是宽度变形。高度一般因为有滚动条,不容易出问题。由此,引发了较强的动态宽度单位需求。
微信小程序设计了 rpx 单位解决这个问题。uni-app
在 App 端、H5 端都支持了 rpx
,并且可以配置不同屏幕宽度的计算方式。
rpx 是相对于基准宽度的单位,可以根据屏幕宽度进行自适应。uni-app
规定屏幕基准宽度 750rpx。
开发者可以通过设计稿基准宽度计算页面元素 rpx 值,设计稿 1px 与框架样式 1rpx 转换公式如下:
设计稿 1px / 设计稿基准宽度 = 框架样式 1rpx / 750rpx
换言之,页面元素宽度在 uni-app
中的宽度计算公式:
750 * 元素在设计稿中的宽度 / 设计稿基准宽度
举例说明:
- 若设计稿宽度为 750px,元素 A 在设计稿上的宽度为 100px,那么元素 A 在
uni-app
里面的宽度应该设为:750 * 100 / 750
,结果为:100rpx。 - 若设计稿宽度为 640px,元素 A 在设计稿上的宽度为 100px,那么元素 A 在
uni-app
里面的宽度应该设为:750 * 100 / 640
,结果为:117rpx。 - 若设计稿宽度为 375px,元素 B 在设计稿上的宽度为 200px,那么元素 B 在
uni-app
里面的宽度应该设为:750 * 200 / 375
,结果为:400rpx。
注意:
- 注意 rpx 是和宽度相关的单位,屏幕越宽,该值实际像素越大。如不想根据屏幕宽度缩放,则应该使用 px 单位。
- 如果开发者在字体或高度中也使用了 rpx ,那么需注意这样的写法意味着随着屏幕变宽,字体会变大、高度会变大。如果你需要固定高度,则应该使用 px 。
- rpx不支持动态横竖屏切换计算,使用rpx建议锁定屏幕方向。
- 设计师可以用 iPhone6 作为视觉稿的标准(750px)。
- 如果设计稿不是750px,HBuilderX提供了自动换算的工具,他会在你写单位的时候自动转换成rpx单位
- App端,在 pages.json 里的 titleNView 或页面里写的 plus api 中涉及的单位,只支持 px,不支持 rpx。
HBuilderX 自带的换算工具详解
如果不想自己计算,HBuilderX里面提供了自动换算
实际配置方法: 若设计稿的宽度为 750px,那么换算比例应该为 750 / 2 / 750
,结果为 0.5
实际配置方式:
- 打开 HBuilderX 编辑器,工具 -> 设置 -> 编辑器配置 -> px转rpx/upx比例
# 内联样式
框架组件上支持使用 style、class 属性来控制组件的样式。
style 接收动态的样式,在运行时会进行解析,请尽量避免将静态的样式写进 style 中,以免影响渲染速度。
<view :style="{color:color}" />
注意:
- 内联样式通常都是用在 动态改变样式的情况下
# 选择器
. | class选择器 |
---|---|
# | id选择器 |
element | 组件选择器 |
::after | 伪类选择器 |
::before | 伪类选择器 |
注意:
- 仅支持
::after
和::before
俩种伪类选择器
在
uni-app
中不能使用*
选择器。微信小程序自定义组件中仅支持 class 选择器
page
相当于body
节点,例如:<!-- 设置页面背景颜色,使用 scoped 会导致失效 --> page { background-color:#ccc; }
# 全局样式与局部样式
定义在 App.vue 中的样式为全局样式,作用于每一个页面。
在 pages 目录下 的 vue 文件中定义的样式为局部样式,只作用在对应的页面,并会覆盖 App.vue 中相同的选择器。
注意:
- App.vue 中通过
@import
语句可以导入外联样式,一样作用于每一个页面。
# Flex布局
为支持跨平台,框架建议使用Flex布局
# 字体图标
uni-app
支持使用字体图标,使用方式与普通 web
项目相同
使用方式
- 将矢量图下载到本地,并放到项目 static 静态文件夹中
- 配置css样式
- 使用矢量图
案例:
<template>
<view>
<view class="iconfont"></view>
</view>
</template>
<style>
@font-face {
font-family: 'iconfont';
src: url('/static/font/iconfont.woff2?t=1630486462761') format('woff2'),
url('/static/font/iconfont.woff?t=1630486462761') format('woff'),
url('/static/font/iconfont.ttf?t=1630486462761') format('truetype');
}
.iconfont {
font-family: "iconfont" !important;
font-size: 16px;
font-style: normal;
}
</style>
注意:
- 配置完css后需要注意, url 的路径必须得正确
# 1.2:全局配置与页面配置
# 通过globalStyle进行全局配置
用于设置应用的状态栏、导航条、标题、窗口背景色等。详细见官方文档 (opens new window)
属性 | 类型 | 默认值 | 描述 | 平台差异说明 |
---|---|---|---|---|
navigationBarBackgroundColor | HexColor | #F7F7F7 | 导航栏背景颜色(同状态栏背景色) | APP与H5为#F7F7F7,小程序平台请参考相应小程序文档 |
navigationBarTextStyle | String | white | 导航栏标题颜色及状态栏前景颜色,仅支持 black/white | |
navigationBarTitleText | String | 导航栏标题文字内容 | ||
backgroundColor | HexColor | #ffffff | 下拉显示出来的窗口的背景色 | 微信小程序 |
backgroundTextStyle | String | dark | 下拉 loading 的样式,仅支持 dark / light | 微信小程序 |
enablePullDownRefresh | Boolean | false | 是否开启下拉刷新 | |
onReachBottomDistance | Number | 50 | 页面上拉触底事件触发时距页面底部距离,单位只支持px |
# 通过pages进行页面配置
uni-app
通过 pages 节点配置应用由哪些页面组成,pages 节点接收一个数组,数组每个项都是一个对象,其属性值如下:
属性 | 类型 | 默认值 | 描述 |
---|---|---|---|
path | String | 配置页面路径 | |
style | Object | 配置页面窗口表现 |
注意:
- pages节点的第一项为应用入口页(即首页)
- 应用中新增/减少页面,都需要对 pages 数组进行修改
- 文件名不需要写后缀,框架会自动寻找路径下的页面资源
"pages": [
{
"path":"pages/message/message"//首页
},
{
"path": "pages/index/index",
"style": {
"navigationBarTitleText": "uni-app"
}
}
]
通过style设置每个页面的状态栏、导航条、标题、窗口背景色等。配置项与全局配置项基本一致
"pages": [
{
"path" : "pages/about/about",
"style" : {
"navigationBarTitleText": "about",
"enablePullDownRefresh": true,
"navigationBarTextStyle":"white",
"navigationBarBackgroundColor":"#0077AA",
"backgroundColor":"#00aa00"
}
}
]
# 配置tabBar
如果应用是一个多 tab 应用,可以通过 tabBar 配置项指定一级导航栏,以及 tab 切换时显示的对应页。
在 pages.json 中提供 tabBar 配置,不仅仅是为了方便快速开发导航,更重要的是在App和小程序端提升性能。在这两个平台,底层原生引擎在启动时无需等待js引擎初始化,即可直接读取 pages.json 中配置的 tabBar 信息,渲染原生tab。
注意
- 当设置 position 为 top 时,将不会显示 icon
- tabBar 中的 list 是一个数组,只能配置最少2个、最多5个 tab,tab 按数组的顺序排序。
属性说明:
属性 | 类型 | 必填 | 默认值 | 描述 | 平台差异说明 |
---|---|---|---|---|---|
color | HexColor | 是 | tab 上的文字默认颜色 | ||
selectedColor | HexColor | 是 | tab 上的文字选中时的颜色 | ||
backgroundColor | HexColor | 是 | tab 的背景色 | ||
borderStyle | String | 否 | black | tabbar 上边框的颜色,可选值 black/white | App 2.3.4+ 支持其他颜色值、H5 3.0.0+ |
list | Array | 是 | tab 的列表,详见 list 属性说明,最少2个、最多5个 tab | ||
position | String | 否 | bottom | 可选值 bottom、top | top 值仅微信小程序支持 |
fontSize | String | 否 | 10px | 文字默认大小 | App 2.3.4+、H5 3.0.0+ |
iconWidth | String | 否 | 24px | 图标默认宽度(高度等比例缩放) | App 2.3.4+、H5 3.0.0+ |
spacing | String | 否 | 3px | 图标和文字的间距 | App 2.3.4+、H5 3.0.0+ |
height | String | 否 | 50px | tabBar 默认高度 | App 2.3.4+、H5 3.0.0+ |
其中 list 接收一个数组,数组中的每个项都是一个对象,其属性值如下
属性 | 类型 | 必填 | 说明 |
---|---|---|---|
pagePath | String | 是 | 页面路径,必须在 pages 中先定义 |
text | String | 是 | tab 上按钮文字,在 App 和 H5 平台为非必填。例如中间可放一个没有文字的+号图标 |
iconPath | String | 否 | 图片路径,icon 大小限制为40kb,建议尺寸为 81px * 81px,当 position 为 top 时,此参数无效,不支持网络图片,不支持字体图标 |
selectedIconPath | String | 否 | 选中时的图片路径,icon 大小限制为40kb,建议尺寸为 81px * 81px ,当 position 为 top 时,此参数无效 |
代码案例:
"tabBar": {
"color": "#7A7E83",
"selectedColor": "#3cc51f",
"borderStyle": "black",
"backgroundColor": "#ffffff",
"list": [
{
"pagePath": "pages/component/index",
"iconPath": "static/image/icon_component.png",
"selectedIconPath": "static/image/icon_component_HL.png",
"text": "组件"
}, {
"pagePath": "pages/API/index",
"iconPath": "static/image/icon_API.png",
"selectedIconPath": "static/image/icon_API_HL.png",
"text": "接口"
}
]
}
# 第二章:组件的使用
# 2.1:uniapp生命周期
生命周期的概念:一个对象从出生创建、运行、销毁的整个过程被成为生命周期。
生命周期函数:在生命周期中,每个阶段都会伴随某个函数的触发,这些函数则被称为生命周期函数。
# 应用生命周期
uni-app
支持如下应用生命周期函数(常用):详见官方文档 (opens new window)
函数名 | 说明 |
---|---|
onLaunch | 当uni-app 初始化完成时触发(全局只触发一次) |
onShow | 当 uni-app 启动或从后台进入前台显示 |
onHide | 当 uni-app 从前台进入后台 |
onError | 当 uni-app 报错时触发 |
注意
- 应用生命周期仅可在
App.vue
中监听,在其它页面监听无效。
<script>
// 只能在App.vue里监听应用的生命周期
export default {
onLaunch: function() {
console.log('App Launch')
},
onShow: function() {
console.log('App Show')
},
onHide: function() {
console.log('App Hide')
}
}
</script>
# 页面生命周期
uni-app
支持如下页面生命周期函数(常用):详见官方文档 (opens new window)
函数名 | 说明 | 平台差异说明 | 最低版本 |
---|---|---|---|
onLoad | 监听页面加载,其参数为上个页面传递的数据,参数类型为 Object(用于页面传参) | ||
onShow | 监听页面显示。页面每次出现在屏幕上都触发,包括从下级页面点返回露出当前页面 | ||
onReady | 监听页面初次渲染完成。注意如果渲染速度快,会在页面进入动画完成前触发 | ||
onHide | 监听页面隐藏 | ||
onUnload | 监听页面卸载 | ||
onPullDownRefresh | 监听用户下拉动作,一般用于下拉刷新,参考示例 (opens new window) | ||
onReachBottom | 页面滚动到底部的事件(不是scroll-view滚到底),常用于下拉下一页数据。具体见下方注意事项 | ||
onTabItemTap | 点击 tab 时触发,参数为Object,具体见下方注意事项 | 微信小程序、QQ小程序、支付宝小程序、百度小程序、H5、App(自定义组件模式) |
# 2.2:组件的基本使用
uni-app提供了丰富的基础组件给开发者,开发者可以像搭积木一样,通过组件来搭建自己的应用。
uni-app中的组件,就像 HTML
中的 div
、p
、span
等标签的作用一样,用于搭建页面的基础结构
- 组件是视图层的基本组成单元。
- 组件是一个单独且可复用的功能模块的封装。
每个组件,包括如下几个部分:以组件名称为标记的开始标签和结束标签、组件内容、组件属性、组件属性值。
- 组件名称由尖括号包裹,称为标签,它有开始标签和结束标签。结束标签的
<
后面用/
来表示结束。结束标签也称为闭合标签。如下面示例的<view>
是开始标签,</view>
是结束标签。 - 在开始标签和结束标签之间,称为组件内容。如下面示例的
content
- 开始标签上可以写属性,属性可以有多个,多个属性之间用空格分割。如下面示例的
class
和property
。注意闭合标签上不能写属性。 - 每个属性通过
=
赋值。如下面的示例中,属性property
的值被设为字符串value
。
注意:所有组件与属性名都是小写,单词之间以连字符
-
连接。
<view class="iconfont" property="value">
content
</view>
# 视图容器组件
# view
视图容器。
它类似于传统html中的div
,用于包裹各种元素内容。
属性说明
属性名 | 类型 | 默认值 | 说明 |
---|---|---|---|
hover-class | String | none | 指定按下去的样式类。当 hover-class="none" 时,没有点击态效果 |
<template>
<view hover-class="aa">
按钮
</view>
</template>
<style scoped="scoped">
view{
width: 234.19rpx;
height: 117.09rpx;
line-height: 117.09rpx;
text-align: center;
background: red;
}
.aa{
color: #4CD964;
}
</style>
# swiper
滑块视图容器。
一般用于左右滑动或上下滑动,比如banner轮播图。
注意:
- swiper下的每个swiper-item是一个滑动切换区域,不能停留在2个滑动区域之间。
常用属性说明
属性名 | 类型 | 默认值 | 说明 | 平台差异说明 |
---|---|---|---|---|
indicator-dots | Boolean | false | 是否显示面板指示点 | |
indicator-color | Color | rgba(0, 0, 0, .3) | 指示点颜色 | |
indicator-active-color | Color | #000000 | 当前选中的指示点颜色 | |
autoplay | Boolean | false | 是否自动切换 | |
current | Number | 0 | 当前所在滑块的 index | |
interval | Number | 5000 | 自动切换时间间隔 | |
duration | Number | 500 | 滑动动画时长 | app-nvue不支持 |
circular | Boolean | false | 是否采用衔接滑动,即播放到末尾后重新回到开头 | |
vertical | Boolean | false | 滑动方向是否为纵向 |
**案例:**轮播图
<swiper indicator-dots circular indicator-color="#00aaff" indicator-active-color="#aaff00" autoplay interval="2000">
<swiper-item>
<image src="../../static/images/i1.jpg"></image>
</swiper-item>
<swiper-item>
<image src="../../static/images/i2.jpeg"></image>
</swiper-item>
<swiper-item>
<image src="../../static/images/i3.jpg"></image>
</swiper-item>
</swiper>
# 基础内容组件
# text
文本组件。用于包裹文本内容。
属性说明
属性名 | 类型 | 默认值 | 说明 |
---|---|---|---|
selectable | Boolean | false | 文本是否可选 |
user-select | Boolean | false | 文本是否可选 |
space | String | 显示连续空格,可选参数:ensp 、emsp 、nbsp |
space 值说明
值 | 说明 |
---|---|
ensp | 中文字符空格一半大小 |
emsp | 中文字符空格大小 |
nbsp | 根据字体设置的空格大小 |
注意
text
组件相当于行内标签、在同一行显示- 除了文本节点以外的其他节点都无法长按选中
# 表单组件
# button
按钮组件
常用属性说明
属性名 | 类型 | 默认值 | 说明 | 生效时机 | 平台差异说明 |
---|---|---|---|---|---|
size | String | default | 按钮的大小 | ||
type | String | default | 按钮的样式类型 | ||
plain | Boolean | false | 按钮是否镂空,背景色透明 | ||
disabled | Boolean | false | 是否禁用 | ||
loading | Boolean | false | 名称前是否带 loading 图标 | App-nvue 平台,在 ios 上为雪花,Android上为圆圈 | |
form-type | String | 用于 <form> 组件,点击分别会触发 <form> 组件的 submit/reset 事件 | |||
open-type | String | 开放能力 |
size 有效值
值 | 说明 |
---|---|
default | 默认大小 |
mini | 小尺寸 |
button
组件默认独占一行,设置size
为mini
时可以在一行显示多个
type 有效值
值 | 说明 |
---|---|
primary | 微信小程序、360小程序为绿色,App、H5、百度小程序、支付宝小程序、快应用为蓝色,字节跳动小程序为红色,QQ小程序为浅蓝色。如想在多端统一颜色,请改用default,然后自行写样式 |
default | 白色 |
warn | 红色 |
form-type 有效值
值 | 说明 |
---|---|
submit | 提交表单 |
reset | 重置表单 |
open-type 有效值
这里需要注意:open-type是针对于小程序来设置的
值 | 说明 | 平台差异说明 |
---|---|---|
feedback | 打开“意见反馈”页面,用户可提交反馈内容并上传日志 | App、微信小程序、QQ小程序 |
share | 触发用户转发 | 微信小程序、百度小程序、支付宝小程序、字节跳动小程序、QQ小程序、快手小程序 |
getUserInfo | 获取用户信息,可以从@getuserinfo回调中获取到用户信息 | 微信小程序、百度小程序、QQ小程序、快手小程序 |
contact | 打开客服会话,如果用户在会话中点击消息卡片后返回应用,可以从 @contact 回调中获得具体信息 | 微信小程序、百度小程序 |
getPhoneNumber | 获取用户手机号,可以从@getphonenumber回调中获取到用户信息 | 微信小程序、百度小程序、字节跳动小程序、支付宝小程序、快手小程序。App平台另见一键登陆 (opens new window) |
launchApp | 小程序中打开APP,可以通过app-parameter属性设定向APP传的参数 | 微信小程序 (opens new window)、QQ小程序 (opens new window) |
openSetting | 打开授权设置页 | 微信小程序、百度小程序 |
getAuthorize | 支持小程序授权 | 支付宝小程序 |
contactShare | 分享到通讯录好友 | 支付宝小程序 |
lifestyle | 关注生活号 | 支付宝小程序 |
openGroupProfile | 呼起QQ群资料卡页面,可以通过group-id属性设定需要打开的群资料卡的群号,同时manifest中必须配置groupIdList | QQ小程序基础库1.4.7版本+ |
<button size='mini' type='primary'>前端</button>
<button size='mini' type='default' disabled='true'>前端</button>
<button size='mini' type='warn' loading='false'>前端</button>
# checkbox
多项选择器组件
checkbox-group
多项选择器,内部由多个 checkbox 组成。
属性说明
属性名 | 类型 | 默认值 | 说明 |
---|---|---|---|
@change | EventHandle | <checkbox-group> 中选中项发生改变是触发 change 事件,detail = {value:[选中的checkbox的value的数组]} |
checkbox
多选项目。
属性说明
属性名 | 类型 | 默认值 | 说明 |
---|---|---|---|
value | String | <checkbox> 标识,选中时触发 <checkbox-group> 的 change 事件,并携带 <checkbox> 的 value。 | |
disabled | Boolean | false | 是否禁用 |
checked | Boolean | false | 当前是否选中,可用来设置默认选中 |
color | Color | checkbox的颜色,同css的color |
案例:
<template>
<view class="content">
<checkbox-group @change="fn">
<label>
<checkbox value="苹果" checked /><text>苹果</text>
</label>
<label>
<checkbox value="梨" /><text>梨</text>
</label>
<label>
<checkbox value="香蕉" disabled /><text>香蕉</text>
</label>
</checkbox-group>
</view>
</template>
<script>
export default {
methods: {
fn(e){
console.log(e)
}
}
}
</script>
# input
输入框组件
属性说明
属性名 | 类型 | 默认值 | 说明 | 平台差异说明 |
---|---|---|---|---|
value | String | 输入框的初始内容 | ||
type | String | text | input 的类型 | H5 暂未支持动态切换,详见下方 Tips,请使用 v-if 进行整体切换 |
password | Boolean | false | 是否是密码类型 | H5和App写此属性时,type失效 |
placeholder | String | 输入框为空时占位符 | ||
maxlength | Number | 140 | 最大输入长度,设置为 -1 的时候不限制最大长度 | |
focus | Boolean | false | 获取焦点。 |
type 有效值
值 | 说明 | 平台差异说明 |
---|---|---|
text | 文本输入键盘 | |
number | 数字输入键盘 | 均支持,App平台、H5平台 3.1.22 以下版本 vue 页面在 iOS 平台显示的键盘包含负数和小数。 |
idcard | 身份证输入键盘 | 微信、支付宝、百度、QQ小程序、快手小程序 |
digit | 带小数点的数字键盘 | 均支持,App平台、H5平台 vue 页面在 iOS 平台显示的键盘包含负数。 |
tel | 电话输入键盘 | 仅App的nvue页面支持 |
<input class="uni-input" focus placeholder="自动获得焦点" />
<input class="uni-input" maxlength="10" placeholder="最大输入长度为10" />
<input class="uni-input" type="number" placeholder="这是一个数字输入框" />
<input class="uni-input" password type="text" placeholder="这是一个密码输入框" />
# picker
从底部弹起的滚动选择器。支持五种选择器,通过mode来区分,分别是普通选择器,多列选择器,时间选择器,日期选择器,省市区选择器,默认是普通选择器。
属性说明
属性名 | 类型 | 默认值 | 说明 | 平台差异说明 |
---|---|---|---|---|
range | Array / Array<Object> | [] | mode为 selector 或 multiSelector 时,range 有效 | |
range-key | String | 当 range 是一个 Array<Object> 时,通过 range-key 来指定 Object 中 key 的值作为选择器显示内容 | ||
value | Number | 0 | value 的值表示选择了 range 中的第几个(下标从 0 开始) | |
@change | EventHandle | value 改变时触发 change 事件,event.detail = {value: value} | ||
disabled | Boolean | false | 是否禁用 | 快手小程序不支持 |
@cancel | EventHandle | 取消选择或点遮罩层收起 picker 时触发 | 快手小程序不支持 |
注意
- picker在各平台的实现是有UI差异的,有的平台如百度、支付宝小程序的Android端是从中间弹出的;有的平台支持循环滚动如百度小程序;有的平台没有取消按钮如App-iOS端。但均不影响功能使用。
案例:选择年份
<template>
<view>
<picker :range="years" @change="yearsChange">
<view>{{years[yearIndex]}}</view>
</picker>
</view>
</template>
<script>
export default {
data() {
return {
years:['请选择年份',2015,2016,2017,2018,2019,2020,2021],
yearIndex:0
}
},
methods: {
yearsChange: function(e) {
this.yearIndex = e.detail.value
}
}
}
</script>
# 路由与页面跳转组件
# navigator
页面跳转。该组件类似HTML中的<a>
标签,但只能跳转本地页面。目标页面必须在pages.json中注册。
常用属性说明
属性名 | 类型 | 默认值 | 说明 | |
---|---|---|---|---|
url | String | 应用内的跳转链接,值为相对路径或绝对路径,如:"../first/first","/pages/first/first",注意不能加 .vue 后缀 | ||
open-type | String | navigate | 跳转方式 |
open-type 有效值
值 | 说明 | 平台差异说明 |
---|---|---|
navigate | 对应 uni.navigateTo 的功能 | |
redirect | 对应 uni.redirectTo 的功能 | |
switchTab | 对应 uni.switchTab 的功能 | |
reLaunch | 对应 uni.reLaunch 的功能 | 字节跳动小程序不支持 |
navigateBack | 对应 uni.navigateBack 的功能 |
注意
- 跳转tabbar页面,必须设置open-type="switchTab"
案例:
传参的话,在路径后面通过键值对的方式传参
<view>
<navigator url="../demo01/demo01?id=2">
跳转到新页面
</navigator>
<navigator url="../demo02/demo02?num=10" open-type="redirect">
当前页面打开
</navigator>
<navigator url="../swiperdemo/swiperdemo" open-type="switchTab">
跳转到tabBar页面
</navigator>
</view>
// navigate.vue页面接受参数
export default {
onLoad: function (option) { //option为object类型,会序列化上个页面传递的参数
console.log(option); //打印出上个页面传递的参数。
}
}
# 2.3:模板语法
# 数据绑定
数据绑定最常见的形式就是使用“Mustache”语法 (双大括号) 的文本插值:
<view>{{num}}</view>
这里双大括号语法还可以写 js 的原生代码
{{ number + 1 }}
{{ ok ? 'YES' : 'NO' }}
{{ message.split('') }}
# 指令
指令是带有 v-
前缀的特殊 attribute。指令 attribute 的值预期是单个 JavaScript 表达式 。指令的职责是,当表达式的值改变时,将其产生的连带影响,响应式地作用于 DOM。
# 常用指令
# v-html
将数据渲染到所在的元素中,支持html标签
<template>
<view>
<view v-html="aa"></view>
<view v-html="bb"></view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
aa:'插入的内容',
bb:"<h1>插入的标签</h1>"
};
}
}
</script>
# v-model
可以用来实现双向数据绑定
**注意:**这个指令只能给表单进行使用
v-model是根据表单的 value 值去改变data中属性的值
**作用:**如果表单上面加了 v-model,那么 data 中于表单绑定的那个属性就会随着表单的改变而改变
案例1:
<template>
<view>
<!-- v-model -->
<view>
<input v-model="modelVal" type="text" />
{{modelVal}}
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
modelVal:''
};
}
}
</script>
# v-bind
将数据绑定到元素的属性当中
v-bind 可以简写 使用 冒号 :
<template>
<view>
<!-- v-bind -->
<view>
<input type="text" v-bind:value="bindVal" />
<!-- 简写 -->
<input type="text" :value="bindVal" />
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
bindVal:'默认值'
};
}
}
</script>
# v-show
用于对指定的内容显示与隐藏,也算是一种条件渲染
<template>
<view>
<!-- v-show -->
<view>
<text v-show="showV">显示与隐藏</text>
<text v-show="showV ? true : false">显示与隐藏</text>
<button size="mini" v-on:click="showV=!showV">控制</button>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
showV:true
};
}
}
</script>
# 条件渲染
# v-if
v-if
指令用于条件性地渲染一块内容。根据表达式的值的真假条件渲染元素,值是布尔值。跟JavaScript 中的 if 判断一样的作用
<template>
<view>
<!-- v-if -->
<view>
<view v-if="ifV === false">v-if显示与隐藏</view>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
ifV:false
};
}
}
</script>
# v-else-if
当v-if条件不满足时,执行判断,也是布尔值。他可以连续使用
<div v-if="type === 'A'">
A
</div>
<div v-else-if="type === 'B'">
B
</div>
<div v-else-if="type === 'C'">
C
</div>
# v-else
当v-if与v-else-if都不满足时,会执行
<template>
<view>
<!-- v-else-if -->
<view>
<view v-if="ifelseV === 12">v-if显示与隐藏</view>
<view v-else-if="ifelseV === 13">v-else-if显示与隐藏</view>
<view v-else>v-else显示与隐藏</view>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
ifelseV:123
};
}
}
</script>
# v-if vs v-show
**相同点:**v-show和v-if都能控制元素的显示和隐藏。
不同点:
- 实现本质方法不同
- v-show本质就是通过设置css中的display设置为none,控制隐藏
- v-if是动态的向DOM树内添加或者删除DOM元素
- 编译的区别
- v-show其实就是在控制css
- v-if切换有一个局部编译/卸载的过程,切换过程中合适地销毁和重建内部的事件监听和子组件
- 编译的条件不同
- v-show都会编译,初始值为false,只是将display设为none,但它也编译了
- v-if初始值为false,就不会编译了
# 列表渲染
# v-for
遍历指令,相当于JavaScript中的 for 循环
我们可以用 v-for
指令对一个数组来进行遍历。v-for
指令需要使用 item in items
形式的特殊语法,其中 items
是源数据数组,而 item
则是被迭代的数组元素的别名。
<template>
<view>
<!-- 列表渲染 v-for -->
<view>
<view v-for="item in arr">
{{item}}
</view>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
arr:[1,2,3]
};
}
}
</script>
结果:
- 1
- 2
- 3
v-for
还支持一个可选的第二个参数,即当前项的索引。
<template>
<view>
<!-- 列表渲染 v-for -->
<view>
<view v-for="(item,index) in arr">
{{index}} | {{item}}
</view>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
arr:[1,2,3]
};
}
}
</script>
结果:前面是下标,后面是值
- 0 | 1
- 1 | 2
- 2 | 3
v-for
还可以遍历对象
<template>
<view>
<!-- 列表渲染 v-for -->
<view>
<view v-for="(item,index) in obj">
{{index}} | {{item}}
</view>
</view>
</view>
</template>
<script>
export default {
name:"directives",
data() {
return {
obj:{
name:'webchubby',
age:18,
sex:'男'
}
};
}
}
</script>
结果:
- name : webchubby
- age : 18
- sex : 男
# 2.4:自定义组件的创建
首先需要在项目根目录创建一个 components 文件夹,以后自己创建的组件都要放到 components 这个文件夹当中。
在uni-app中,可以通过创建一个后缀名为vue的文件,即创建一个组件成功,其他组件可以将该组件通过 import 的方式导入,在通过components进行注册即可
组件当中有三大模块:template
、script
、style
,与页面规范是一致的。
- 创建一个 login 自定义组件,在 components 文件夹下新建一个 login.vue 文件。这里需要注意,如果自定义组件很多,则需要在 components 文件夹下再创建目录
<template>
<view>
这是一个 login 自定义组件
</view>
</template>
<script>
</script>
<style>
</style>
- 在其他组件中导入该组件通过 es6 的 import 方式导入
import login from "@/components/login.vue"
- 注册组件
注册组件需要通过 components 来进行注册
<script>
import login from "@/components/login.vue"
export default{
data(){
return{
}
},
components:{
login
}
}
</script>
- 使用组件
组件使用的时候,只需要将名字当作标签来使用就可以了
<login></login>
# 2.5:uni-app中的事件
# methods 与 事件
事件绑定
在uni中事件绑定和vue中是一样的,通过v-on进行事件的绑定,也可以简写为@
<button @click="tapHandle">点我啊</button>
事件函数定义在methods中
export default {
methods: {
tapHandle () {
console.log('你还真点啊')
}
}
}
# 2.6:组件的生命周期
uni-app
组件支持的生命周期,与vue标准组件的生命周期相同。这里没有页面级的onLoad等生命周期。详解见vue官方文档 (opens new window)
函数名 | 说明 | 平台差异说明 | 最低版本 |
---|---|---|---|
beforeCreate | 在实例初始化之后被调用。详见 (opens new window) | ||
created | 在实例创建完成后被立即调用。详见 (opens new window) | ||
beforeMount | 在挂载开始之前被调用。详见 (opens new window) | ||
mounted | 挂载到实例上去之后调用。详见 (opens new window) 注意:此处并不能确定子组件被全部挂载,如果需要子组件完全挂载之后在执行操作可以使用$nextTick Vue官方文档 (opens new window) | ||
beforeUpdate | 数据更新时调用,发生在虚拟 DOM 打补丁之前。详见 (opens new window) | 仅H5平台支持 | |
updated | 由于数据更改导致的虚拟 DOM 重新渲染和打补丁,在这之后会调用该钩子。详见 (opens new window) | 仅H5平台支持 | |
beforeDestroy | 实例销毁之前调用。在这一步,实例仍然完全可用。详见 (opens new window) | ||
destroyed | Vue 实例销毁后调用。调用后,Vue 实例指示的所有东西都会解绑定,所有的事件监听器会被移除,所有的子实例也会被销毁。详见 (opens new window) |
# 2.7:组件的通讯
这里总结了一句话给大家:父子属性,子父事件,非父子公共
# 父子传值
父组件通过属性的方式传递数据给子组件,子组件接收的时候通过 props
来接收
子组件通过 props
接收的方式有俩种:
- 通过数组接收
- 通过对象接收
这里通常用第二种对象方式来进行接收,因为对象接收还可以检验数据类型与设置默认值。
注意:
- 子组件不能直接修改父组件传过来的属性值
- 子组件接收的值不要与组件data内的返回对象属性同名
父组件
<template>
<view>
father1
<child :aa="text"></child>
</view>
</template>
<script>
import child from "./child.vue"
export default {
data(){
return{
text:'父组件内容'
}
},
components:{
child
}
}
</script>
子组件
<template>
<view>
child
<view v-html="aa"></view>
</view>
</template>
<script>
export default {
//第一种 数组方式
props:["aa"]
//第二种 对象方式
props:{
aa:String,
default:"正在加载"//默认值
}
}
</script>
# 子父传值
子父传值的话,子组件通过 $emit
发送一个事件给父组件来进行传值,父组件通过自定义事件来监听子组件传过来的这个事件来进行接收。
子组件:
<template>
<view>
child
<button type="button" @click="fn">给父组件发送数据</button>
</view>
</template>
<script>
export default {
data(){
return{
childs:'子组件数据'
}
},
methods:{
fn(){
this.$emit('child',this.childs)
}
}
}
</script>
父组件:
<template>
<view>
father2
<child @child="fafn"></child>
</view>
</template>
<script>
import child from "./child.vue"
export default {
components:{
child
},
methods:{
fafn(val){
console.log(val)
}
}
}
</script>
# 非父子传值
非父子组件传值首先需要先创建一个公共的 Vue
实例,然后通过这个公共实例再来进行传值。
传值方通过 $emit
发送一个事件来进行传值
接收方通过 $on
来监听这个事件进行接收
首先要创建一个公共的vue
实例,这里在 main.js 文件中创建
Vue.prototype.$bus = new Vue()
father1组件
<template>
<view>
father1
<button type="button" @click="fath1">发送给非父子组件数据</button>
</view>
</template>
<script>
export default {
methods:{
fath1(){
this.$bus.$emit('fath1','one')
}
}
}
</script>
father2组件
<template>
<view>
father2
</view>
</template>
<script>
export default {
mounted(){
this.$bus.$on('fath1',function(val){
console.log(val)
})
}
}
</script>
# 第三章:uni 的 API
# 3.1:网络请求
在uni中可以调用uni.request方法进行请求网络请求
在各个小程序平台运行时,网络相关的 API 在使用前需要配置域名白名单。
常用参数说明
参数名 | 类型 | 必填 | 默认值 | 说明 |
---|---|---|---|---|
url | String | 是 | 开发者服务器接口地址 | |
data | Object/String/ArrayBuffer | 否 | 请求的参数 | |
header | Object | 否 | 设置请求的 header | |
method | String | 否 | GET | 有效值:GET、POST、PUT、DELETE、CONNECT、HEAD、OPTIONS、TRACE |
success | Function | 否 | 收到开发者服务器成功返回的回调函数 |
案例:
# get请求
<script>
export default {
onLoad() {
uni.request({
method:'GET',
url:"http://iwenwiki.com/api/blueberrypai/getIndexBanner.php",
success:(data)=>{
console.log(data)
}
})
}
}
</script>
# post请求
post请求需要配置请求头 header
'content-type':'application/x-www-form-urlencoded'
uni.request({
method:'POST',
url:"http://localhost:3000/api/login",//仅为测试接口,实际以真实接口为准
header:{'content-type':'application/x-www-form-urlencoded'},
data:{
username:'admin',
password:'123'
},
success: (data) => {
console.log(data)
}
})
# 封装uni.request
通过 promise
来进行封装
// 域名地址
const BASE_URL = 'http://iwenwiki.com';
export default (options)=>{
return new Promise((resolve,reject)=>{
uni.request({
method:options.method || 'GET',
url:BASE_URL+options.url,
data:options.data || {},
success:(res)=>{
if(res.statusCode === 200){
resolve(res)
}
},
fail:(err)=>{
reject(err)
}
})
})
}
调用:
首先在全局挂载使用,然后再去请求
main.js 中引用并全局挂载
import request from "utils/request.js"
Vue.prototype.$api = request
使用
this.$api({
method:'GET',
url:'/api/blueberrypai/getIndexBanner.php',
}).then(res=>{
uni.showToast({
title:'获取成功'
})
console.log(res)
})
# 3.2:路由与页面跳转与传参
与 navigator
组件不同的是,他是通过事件来进行页面的跳转
# uni.navigateTo
保留当前页面,跳转到应用内的某个页面
<template>
<view>
<button @click="newpage">api跳转到新页面</button>
</view>
</template>
<script>
export default {
methods: {
newpage(){
uni.navigateTo({
url:'../demo01/demo01?id=2'
})
}
}
}
</script>
# uni.redirectTo
关闭当前页面,跳转到应用内的某个页面。
<template>
<view>
<button @click="currentpage">api当前页面打开</button>
</view>
</template>
<script>
export default {
methods: {
currentpage(){
uni.redirectTo({
url:'../demo02/demo02?num=10'
})
}
}
}
</script>
# uni.switchTab
跳转到 tabBar 页面,并关闭其他所有非 tabBar 页面。
<template>
<view>
<button @click="tabpage">api跳转到tabBar页面</button>
</view>
</template>
<script>
export default {
methods: {
tabpage(){
uni.switchTab({
url:'../swiperdemo/swiperdemo'
})
}
}
}
</script>
# 接收参数
通过 onLoad 生命周期来接收参数
<script>
export default {
onLoad: function (option) { //option为object类型,会序列化上个页面传递的参数
console.log(option);
}
}
</script>
# 3.3:图片及预览
# uni.chooseImage
从本地相册选择图片或使用相机拍照。
案例:
<template>
<view>
<button type="primary" @click="chooseImg">选择图片</button>
<view v-for="item in chooseImageArr">
<image :src="item" mode=""></image>
</view>
</view>
</template>
<script>
export default {
name:"choseimg",
data() {
return {
chooseImageArr:[]
};
},
methods:{
chooseImg(){
uni.chooseImage({
count:5,
success: (res) => {
console.log(res)
this.chooseImageArr = res.tempFilePaths
}
})
}
}
}
</script>
# uni.previewImage
图片预览
常用属性:
参数名 | 类型 | 必填 | 说明 | 平台差异说明 |
---|---|---|---|---|
urls | Array | 是 | 需要预览的图片链接列表 | |
indicator | String | 否 | 图片指示器样式,可取值:"default" - 底部圆点指示器; "number" - 顶部数字指示器; "none" - 不显示指示器。 | App |
loop | Boolean | 否 | 是否可循环预览,默认值为 false | App |
longPressActions | Object | 否 | 长按图片显示操作菜单,如不填默认为保存相册 | App 1.9.5+ |
success | Function | 否 | 接口调用成功的回调函数 | |
fail | Function | 否 | 接口调用失败的回调函数 | |
complete | Function | 否 | 接口调用结束的回调函数(调用成功、失败都会执行) |
longPressActions 参数说明
参数 | 类型 | 必填 | 说明 |
---|---|---|---|
itemList | Array | 是 | 按钮的文字数组 |
itemColor | String | 否 | 按钮的文字颜色,字符串格式,默认为"#000000" |
success | Function | 否 | 接口调用成功的回调函数,详见返回参数说明 |
fail | Function | 否 | 接口调用失败的回调函数 |
案例:本案需要配合整机调试查看效果
<template>
<view>
<button type="primary" @click="chooseImg">选择图片</button>
</view>
</template>
<script>
export default {
name:"choseimg",
data() {
return {
chooseImageArr:[]
};
},
methods:{
chooseImg() {
uni.chooseImage({
count: 5,
success: res => {
console.log(res)
uni.previewImage({
urls: res.tempFilePaths,
indicator: "default",
longPressActions: {
itemList: ['发送给朋友', '保存图片', '收藏'],
success: function(data) {
console.log('选中了第' + (data.tapIndex + 1) + '个按钮,第' + (data.index + 1) + '张图片');
}
}
})
}
})
}
}
}
</script>
# 3.4:数据缓存
# 设置
# uni.setStorage
将数据存储在本地缓存中指定的 key 中,会覆盖掉原来该 key 对应的内容,这是一个异步接口。
参数说明:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
key | String | 是 | 本地缓存中的指定的 key |
data | Any | 是 | 需要存储的内容,只支持原生类型、及能够通过 JSON.stringify 序列化的对象 |
success | Function | 否 | 接口调用成功的回调函数 |
fail | Function | 否 | 接口调用失败的回调函数 |
uni.setStorage({
key:'name',
data:'张三',
success:()=>{
console.log('存储成功')
}
})
# uni.setStorageSync
将 data 存储在本地缓存中指定的 key 中,会覆盖掉原来该 key 对应的内容,这是一个同步接口。
参数说明
参数 | 类型 | 必填 | 说明 |
---|---|---|---|
key | String | 是 | 本地缓存中的指定的 key |
data | Any | 是 | 需要存储的内容,只支持原生类型、及能够通过 JSON.stringify 序列化的对象 |
try {
uni.setStorageSync('storage_key', 'hello');
} catch (e) {
// error
}
# 获取
# uni.getStorage
从本地缓存中异步获取指定 key 对应的内容。
OBJECT 参数说明
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
key | String | 是 | 本地缓存中的指定的 key |
success | Function | 是 | 接口调用的回调函数,res = {data: key对应的内容} |
fail | Function | 否 | 接口调用失败的回调函数 |
uni.getStorage({
key:"name",
success:res=>{
console.log(res)
}
})
# uni.getStorageSync
从本地缓存中同步获取指定 key 对应的内容。
try {
const value = uni.getStorageSync('age');
console.log(value,'getStorageSync');
} catch (e) {
// error
}
# 删除
# uni.removeStorage
从本地缓存中异步移除指定 key。
OBJECT 参数说明
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
key | String | 是 | 本地缓存中的指定的 key |
success | Function | 是 | 接口调用的回调函数 |
fail | Function | 否 | 接口调用失败的回调函数 |
uni.removeStorage({
key:'name',
success: () => {
console.log('删除成功')
}
})
# uni.removeStorageSync
从本地缓存中同步移除指定 key。
try {
uni.removeStorageSync('name');
} catch (e) {
// error
}
# 清除
# uni.clearStorage()
清理本地数据缓存。
uni.clearStorage();
# uni.clearStorageSync()
同步清理本地数据缓存。
try {
uni.clearStorageSync();
} catch (e) {
// error
}
# 3.5:交互反馈
# uni.showToast
显示消息提示框。
常用参数说明
参数 | 类型 | 必填 | 说明 | 平台差异说明 |
---|---|---|---|---|
title | String | 是 | 提示的内容,长度与 icon 取值有关。 | |
icon | String | 否 | 图标,有效值详见下方说明。 | |
mask | Boolean | 否 | 是否显示透明蒙层,防止触摸穿透,默认:false | App、微信小程序 |
duration | Number | 否 | 提示的延迟时间,单位毫秒,默认:1500 | |
position | String | 否 | 纯文本轻提示显示位置,填写有效值后只有 title 属性生效, 有效值详见下方说明。 | App |
success | Function | 否 | 接口调用成功的回调函数 | |
fail | Function | 否 | 接口调用失败的回调函数 | |
complete | Function | 否 | 接口调用结束的回调函数(调用成功、失败都会执行) |
icon 值说明
值 | 说明 | 平台差异说明 |
---|---|---|
success | 显示成功图标,此时 title 文本最多显示 7 个汉字长度。默认值 | |
error | 显示错误图标,此时 title 文本最多显示 7 个汉字长度。 | |
loading | 显示加载图标,此时 title 文本最多显示 7 个汉字长度。 | 支付宝小程序不支持 |
none | 不显示图标,此时 title 文本在小程序 最多可显示两行,App 仅支持单行显示。 |
position 值说明(仅App生效)
值 | 说明 |
---|---|
top | 居上显示 |
center | 居中显示 |
bottom | 居底显示 |
uni.showToast({
title: '标题',
duration: 2000
});
# uni.hideToast
隐藏消息提示框。
uni.hideToast();
案例:
uni.showLoading({
title:'showLoading',
mask:true
})
setTimeout(function(){
uni.hideLoading();
},2000)
# uni.showLoading
显示 loading 提示框
OBJECT参数说明
参数 | 类型 | 必填 | 说明 | 平台差异说明 |
---|---|---|---|---|
title | String | 是 | 提示的文字内容,显示在loading的下方 | |
mask | Boolean | 否 | 是否显示透明蒙层,防止触摸穿透,默认:false | App、微信小程序、百度小程序 |
success | Function | 否 | 接口调用成功的回调函数 | |
fail | Function | 否 | 接口调用失败的回调函数 | |
complete | Function | 否 | 接口调用结束的回调函数(调用成功、失败都会执行) |
uni.showLoading({
title:'showLoading'
})
# uni.hideLoading
隐藏 loading 提示框。
uni.showLoading({
title:'showLoading',
mask:true
})
setTimeout(function(){
uni.hideLoading();
},2000)
# uni.showModal
显示模态弹窗,可以只有一个确定按钮,也可以同时有确定和取消按钮。
常用参数说明
参数 | 类型 | 必填 | 说明 | 平台差异说明 |
---|---|---|---|---|
title | String | 否 | 提示的标题 | |
content | String | 否 | 提示的内容 | |
showCancel | Boolean | 否 | 是否显示取消按钮,默认为 true | |
cancelText | String | 否 | 取消按钮的文字,默认为"取消",最多 4 个字符 | |
confirmText | String | 否 | 确定按钮的文字,默认为"确定",最多 4 个字符 | |
success | Function | 否 | 接口调用成功的回调函数 | |
fail | Function | 否 | 接口调用失败的回调函数 | |
complete | Function | 否 | 接口调用结束的回调函数(调用成功、失败都会执行) |
success返回参数说明
参数 | 类型 | 说明 |
---|---|---|
confirm | Boolean | 为 true 时,表示用户点击了确定按钮 |
cancel | Boolean | 为 true 时,表示用户点击了取消(用于 Android 系统区分点击蒙层关闭还是点击取消按钮关闭) |
uni.showModal({
title: '提示',
content: '这是一个模态弹窗',
success: function (res) {
if (res.confirm) {
console.log('用户点击确定');
} else if (res.cancel) {
console.log('用户点击取消');
}
}
});
# uni.showActionSheet
从底部向上弹出操作菜单
OBJECT参数说明
参数 | 类型 | 必填 | 说明 | 平台差异说明 |
---|---|---|---|---|
itemList | Array | 是 | 按钮的文字数组 | 微信、百度、字节跳动小程序数组长度最大为6个 |
success | Function | 否 | 接口调用成功的回调函数,详见返回参数说明 | |
fail | Function | 否 | 接口调用失败的回调函数 | |
complete | Function | 否 | 接口调用结束的回调函数(调用成功、失败都会执行) |
success返回参数说明
参数 | 类型 | 说明 |
---|---|---|
tapIndex | Number | 用户点击的按钮,从上到下的顺序,从0开始 |
uni.showActionSheet({
itemList: ['A', 'B', 'C'],
success: function (res) {
console.log('选中了第' + (res.tapIndex + 1) + '个按钮');
},
fail: function (res) {
console.log(res.errMsg);
}
});
# 3.6:设备相关
# uni.getSystemInfo
获取系统信息。
uni.getSystemInfo({
success: (res) => {
console.log(res)
}
})
# uni.getNetworkType
获取网络类型。
uni.getNetworkType({
success: function (res) {
console.log(res.networkType);
}
});
# uni.onNetworkStatusChange
监听网络状态变化。
uni.onNetworkStatusChange(function (res) {
console.log(res);
});
# 3.7:下拉刷新与上拉加载
# 下拉刷新
在uni-app中有两种方式开启下拉刷新
- 第一种:
pages.json
文件中配置下拉刷新 - 第二种:通过
uni.startPullDownRefresh()
api 来开启
关闭下拉刷新:
uni.stopPullDownRefresh()
# 第一种:通过配置下拉刷新(推荐)
- 首先在需要刷新的页面配置
enablePullDownRefresh
,值为布尔值
{
"path": "pages/downrefresh/downrefresh",
"style": {
"enablePullDownRefresh": true
}
}
- 去对应页面定义
onPullDownRefresh
处理函数(和onLoad等生命周期函数同级),监听该页面用户下拉刷新事件。
案例:
<template>
<view>
<text>下拉刷新</text><br/>
----------------------
<view v-for="(item,index) in reflist" :key="index">
{{item}}
</view>
</view>
</template>
<script>
export default {
data() {
return {
reflist:['松树','樟树','桃树','苹果树','杨树']
}
},
onPullDownRefresh(){
console.log(111)
setTimeout(()=>{
this.reflist = ['苹果','桃子','香蕉','哈密瓜','荔枝'];
uni.stopPullDownRefresh();
},1000)
},
methods: {
}
}
</script>
# 第二种:通过uni.startPullDownRefresh()
api 来开启
- 首先也需要配置
enablePullDownRefresh
,如果不配置没有刷新效果,会直接修改
案例:
<template>
<view>
<text>下拉刷新</text><br />
----------------------
<view v-for="(item,index) in reflist" :key="index">
{{item}}
</view>
<button @click="refbuttom">点击刷新</button>
</view>
</template>
<script>
export default {
data() {
return {
reflist: ['松树', '樟树', '桃树', '苹果树', '杨树']
}
},
methods: {
refbuttom() {
uni.startPullDownRefresh({
success: () => {
setTimeout(() => {
this.reflist = ['苹果', '桃子', '香蕉', '哈密瓜', '荔枝'];
uni.stopPullDownRefresh();
}, 1000)
}
})
}
}
}
</script>
# 上拉加载
通过onReachBottom
监听触底行为
onReachBottom
使用注意 可在pages.json里定义具体页面底部的触发距离onReachBottomDistance,比如设为50,那么滚动页面到距离底部50px时,就会触发onReachBottom事件。
案例:
<template>
<view>
<text>上拉加载</text><br />
----------------------
<view class="refbottom" v-for="(item,index) in reflist" :key="index">
{{item}}
</view>
</view>
</template>
<script>
export default {
data() {
return {
reflist: ['松树', '樟树', '桃树', '苹果树', '杨树']
}
},
onReachBottom() {
console.log('触底了')
let refarr = ['苹果', '桃子', '香蕉', '哈密瓜', '荔枝']
this.reflist.push(...refarr)
},
methods: {
}
}
</script>
<style scoped>
.refbottom{
height: 702.57rpx;
line-height: 702.57rpx;
}
</style>
# 第四章:跨端兼容
# 4.1:条件编译
跨端兼容
uni-app 已将常用的组件、JS API 封装到框架中,开发者按照 uni-app 规范开发即可保证多平台兼容,大部分业务均可直接满足。
但每个平台有自己的一些特性,因此会存在一些无法跨平台的情况。
- 大量写 if else,会造成代码执行性能低下和管理混乱。
- 编译到不同的工程后二次修改,会让后续升级变的很麻烦。
条件编译是用特殊的注释作为标记,在编译时根据这些特殊的注释,将注释里面的代码编译到不同平台。
**写法:**以 #ifdef 加平台标识 开头,以 #endif 结尾。
常用平台标识:
值 | 平台 | 参考文档 |
---|---|---|
APP-PLUS | 5+App | HTML5+ 规范 (opens new window) |
H5 | H5 | |
MP-WEIXIN | 微信小程序 | 微信小程序 (opens new window) |
MP-ALIPAY | 支付宝小程序 | 支付宝小程序 (opens new window) |
MP-BAIDU | 百度小程序 | 百度小程序 (opens new window) |
MP-TOUTIAO | 头条小程序 | 头条小程序 (opens new window) |
MP-QQ | QQ小程序 | (目前仅cli版支持) |
MP | 微信小程序/支付宝小程序/百度小程序/头条小程序/QQ小程序 |
# 组件的条件注释
<!-- #ifdef H5 -->
<view>
h5页面会显示
</view>
<!-- #endif -->
<!-- #ifdef MP-WEIXIN -->
<view>
微信小程序会显示
</view>
<!-- #endif -->
<!-- #ifdef APP-PLUS -->
<view>
app会显示
</view>
<!-- #endif -->
# api的条件编译
onLoad () {
//#ifdef MP-WEIXIN
console.log('微信小程序')
//#endif
//#ifdef H5
console.log('h5页面')
//#endif
}
# 样式的条件编译
/* #ifdef H5 */
view{
height: 100px;
line-height: 100px;
background: red;
}
/* #endif */
/* #ifdef MP-WEIXIN */
view{
height: 100px;
line-height: 100px;
background: green;
}
/* #endif */
# 第五章:uni ui
# 5.1:扩展组件 uni ui 的使用
uni-ui是DCloud提供的一个跨端ui库,它是基于vue组件的、flex布局的、无dom的跨全端ui框架。
uni-ui不包括基础组件,它是基础组件的补充。
有俩种使用方式:
- 使用 uni_modules 安装(推荐),也就是编辑器直接导入下载
- 使用 npm安装
使用步骤:
- 进入你想要使用的组件
- 使用 HBuilderX 导入该组件
- 自定义组件的使用流程
# 第一种编辑器导入方式(推荐)
用 uni_modules
方式安装组件库,可以直接通过插件市场导入,通过右键菜单快速更新组件,不需要引用、注册,直接在页面中使用 uni-ui
组件
以日历组件为例:
- HBuilderX 导入该组件
导入后会在项目根目录生成一个 uni_modules
文件夹
- 使用组件
用HBuilderX 导入的组件不需要引入,直接使用就行
<template>
<view>
<uni-calendar
:insert="true"
:lunar="true"
:start-date="'2019-3-2'"
:end-date="'2019-5-20'"
@change="change"
/>
</view>
</template>
<script>
export default {
methods:{
change(e){
console.log(e)
}
}
}
</script>
也可以通过方法来打开日历
- 需要设置
insert
为false
<template>
<view>
<text>通过方法打开日历</text>
<uni-calendar
ref="calendar"
:insert="false"
:lunar="true"
@confirm="confirm"
/>
<button @click="open">打开日历</button>
</view>
</template>
<script>
export default {
methods:{
open(){
this.$refs.calendar.open();
},
confirm(e){
console.log(e)
}
}
}
</script>
# 第二种npm方式
- 在终端输入命令
npm i @dcloudio/uni-ui
下载uni-ui - 配置
easycom
规则,让npm
安装的组件支持easycom
- 打开项目根目录下的
pages.json
并添加easycom
节点配置
- 打开项目根目录下的
// pages.json
{
"easycom": {
"autoscan": true,
"custom": {
// uni-ui 规则如下配置
"^uni-(.*)": "@dcloudio/uni-ui/lib/uni-$1/uni-$1.vue"
}
}
}
- 使用组件(同上)
# 5.2:uView框架的讲解与使用
uni-app
出现发展到现在以来,一直蓬勃发展。随着一直在发展,相应的 ui 框架就会应用而生,其中uView 框架就是uni-app众多框架中的一款。
uView也是使用easycom
模式,无需引入组件即可直接使用
# 安装与使用步骤
安装使用的方式有俩种:
- 在uni-app插件市场右上角选择
使用HBuilder X 导入插件
或者下载插件ZIP
- 直接创建 uView 框架项目
# 使用步骤:
安装 uView ,同上
引入uView主JS库
在项目根目录中的main.js
中,引入并使用uView的JS库,注意这两行要放在import Vue
之后。
// main.js
import uView from "uview-ui";
Vue.use(uView);
- 引入uView的全局SCSS主题文件
在项目根目录的uni.scss
中引入此文件。
/* uni.scss */
@import 'uview-ui/theme.scss';
- 引入uView基础样式
注意:在App.vue
中首行的位置引入,注意给style标签加入lang="scss"属性
<style lang="scss">
/* 注意要写在第一行,同时给style标签加入lang="scss"属性 */
@import "uview-ui/index.scss";
</style>
- 配置easycom组件模式
在 pages.json 文件中配置
// pages.json
{
"easycom": {
"autoscan": true,
"custom": {
// uView 规则如下配置
"^u-(.*)": "@/uview-ui/components/u-$1/u-$1.vue"
}
},
// 此为本身已有的内容
"pages": [
// ......
]
}
# uView案例
# button 按钮
type
值可选的有default
(默认)、primary
、success
、info
、warning
、error
<u-button >默认按钮</u-button>
<u-button type="primary">主要按钮</u-button>
<u-button type="success">成功按钮</u-button>
<u-button type="info">信息按钮</u-button>
<u-button type="warning">警告按钮</u-button>
<u-button type="error">危险按钮</u-button>
还可以设置为圆角按钮,添加 shape="circle" 属性
<u-button shape="circle">圆角按钮</u-button>
设置点击按钮的水波纹效果
<!-- 水波纹效果 -->
<u-button :ripple="true">水波纹效果</u-button>
<!-- 通过rippleBgColor设置水波纹的背景颜色 -->
<u-button :ripple="true" ripple-bg-color="#55aaff">水波纹效果</u-button>
# 下拉菜单案例
- 该组件必须结合
u-dorpdown
和u-dropdown-item
一起使用,展开的内容由u-dropdown-item
通过传递参数或者slot
提供 - 组件的菜单栏标题由
u-dropdown-item
通过title
参数提供 u-dropdown-item
带有默认的单选展示功能,通过options
(见下方说明)配置,传入slot
则会覆盖默认功能,通过v-model
双向绑定options
选中项的value
值
<template>
<view class="">
<u-dropdown>
<u-dropdown-item v-model="value1" title="距离" :options="options1"></u-dropdown-item>
<u-dropdown-item v-model="value2" title="温度" :options="options2"></u-dropdown-item>
</u-dropdown>
</view>
</template>
<script>
export default {
data() {
return {
value1: 1,
value2: 2,
options1: [{
label: '默认排序',
value: 1,
},
{
label: '距离优先',
value: 2,
},
{
label: '价格优先',
value: 3,
}
],
options2: [{
label: '去冰',
value: 1,
},
{
label: '加冰',
value: 2,
},
],
}
},
}
</script>
# 自定义菜单栏
自定义菜单栏不再是通过options
来传递值,而是通过 slot
来自定义需要展示的内容。
如果想实现点击其中按钮关闭菜单栏,在u-dropdown
中,有一个close()
方法,可以通过ref
获取实例,并调用方法进行关闭即可。
<template>
<view class="">
<u-dropdown ref="uDropdown">
<u-dropdown-item title="属性">
<view class="slot-content">
<view class="u-text-center u-content-color u-m-t-20 u-m-b-20">
其他自定义内容
</view>
<u-button type="primary" @click="closeDropdown">确定</u-button>
</view>
</u-dropdown-item>
</u-dropdown>
</view>
</template>
<script>
export default {
methods: {
closeDropdown() {
this.$refs.uDropdown.close();
}
}
}
</script>
案例:
<template>
<view class="">
<u-dropdown ref="uDropdown">
<u-dropdown-item title="属性">
<view class="item-list">
<view
@click="actives(index)"
:class="activeindex == index ? 'u-text-center u-content-color butcolor active' : 'u-text-center u-content-color butcolor'"
v-for="(item,index) in itemarr" :key="index"
>
{{item.writer}}
</view>
</view>
<u-button type="primary" @click="closeDropdown">确定</u-button>
</u-dropdown-item>
</u-dropdown>
</view>
</template>
<script>
export default {
data(){
return {
itemarr:[],
activeindex:''
}
},
onLoad(){
uni.request({
method:"GET",
url:'http://iwenwiki.com/api/blueberrypai/getListeningInfo.php',
success: res => {
this.itemarr = res.data.listening
}
})
},
methods: {
closeDropdown() {
this.$refs.uDropdown.close();
},
actives(index){
this.activeindex = index
console.log(index)
}
}
}
</script>
<style scoped>
.item-list{
background: #FFFFFF;
padding-bottom: 46.83rpx;
display: flex;
flex-wrap: wrap;
justify-content: space-between;
}
.butcolor {
padding: 7.02rpx 37.47rpx;
color: #2979FF;
border: 2.34rpx solid #2979FF;
border-radius: 96.01rpx;
margin: 23.41rpx 23.41rpx 0;
}
.active{
color: #FFFFFF;
background: #2979FF;
}
</style>