Uni-app
页面生命周期
每个 Vue 实例在被创建时都要经过一系列的初始化过程——例如,需要设置数据监听、编译模板、将实例挂载到 DOM 并在数据变化时更新 DOM 等。同时在这个过程中也会运行一些叫做生命周期钩子的函数。
mounted
在组件的 DOM 元素被挂载到文档 DOM 中之后被调用。下面代码中如果发现token则直接跳转页面。
mounted () { // mounted 钩子在组件的DOM元素被挂载(即插入到文档DOM中)之后被调用。
this.getToken(); // 获取本地缓存token
if (this.token != '' && this.token != null) {
// 跳转主页
uni.switchTab({
url: '/pages/tabBar/home/index'
});
} else {
this.getCode();
this.getAccount();
}
},
onShow、onHide、onUnload
注意页面显示,是一个会重复触发的事件。
a页面刚进入时,会触发a页面的onShow。
当a跳转到b页面时,a会触发onHide,而b会触发onShow。
但当b被关闭时,b会触发onUnload,此时a再次显示出现,会再次触发onShow。
在tabbar页面(指pages.json里配置的tabbar),不同tab页面互相切换时,会触发各自的onShow和onHide。
create
在实例创建完成后被立即调用。
onReady
监听页面初次渲染完成并执行所编写的代码,此时组件已挂载完成,DOM 树已可用。
uni-app框架,首先根据pages.json的配置,创建页面。根据页面中的template组件创建dom。之后,触发onload。
Tabbar的设置
uni-app底部导航栏tabBar的显示和使用步骤_uni-app 判断是否为tabbar界面-CSDN博客
tabBar 中的 list 是一个数组,只能配置最少2个、最多5个 tab,tab 按数组的顺序排序。Tabbar的设置位于page.js
文件中。Tabbar页面要加入文档中的pages数组中。
删除顶部导航栏
uni-app开发-顶部导航栏 - 掘金 (juejin.cn)
属性 | 类型 | 默认值 | 描述 |
---|---|---|---|
navigationStyle | String | default | 导航栏样式,仅支持 default/custom。custom即取消默认的原生导航栏,需看使用注意 |
通过在manifest.json
中设置如下参数可以避免app与手机顶部状态栏或是水滴屏等遮挡的问题。也可以在顶部添加视觉块填充顶部状态栏区域解决该问题。
"app-plus" : {
"statusbar": {
"immersed": false
}
}
uni.setStorageSync
和 Vuex store 存储异同
uni.setStorageSync
是 uni-app 提供的一个本地存储 API,用于在客户端存储数据。它类似于 Web Storage API 中的 localStorage
和 sessionStorage
。Vuex 是 Vue.js
的官方状态管理模式,用于集中管理应用的所有组件的状态。本地存储是在客户端存储数据的一种方式,而状态管理是一种模式,用于集中管理应用程序的状态。
- 存储位置:
uni.setStorageSync
存储数据在客户端本地存储中;Vuex store 存储数据在内存中。 - 持久化:
uni.setStorageSync
中的数据是持久化的;Vuex store 中的数据在页面刷新后会丢失。 - 响应式: Vuex store 中的数据是响应式的;
uni.setStorageSync
中的数据不是响应式的。 - 状态管理: Vuex store 提供了复杂的状态管理功能;
uni.setStorageSync
主要用于简单的数据存储。 - 安全性:
uni.setStorageSync
中的数据更容易受到攻击;Vuex store 中的数据更受保护,因为数据在内存中而不是客户端本地存储。
uni.setStorage(OBJECT) @setstorage | uni-app官网 (dcloud.net.cn)
使用 uni-app 的全局数据管理
客户端存储 - 学习 Web 开发 | MDN (mozilla.org)
在 main.js
或 App.vue
中初始化:
使用全局变量或 store
在store文件夹下的JS文件夹中可以看到所存储的全局变量。
缓存
一文读懂Uniapp的setStorage、setStorageSync、getStorage以及getStorageSync(附Demo)_uni.getstorage-CSDN博客
通过缓存数据以在其他页面使用。
uni.setStorage({key, data, success, fail, complete})
:将数据异步存储到本地缓存中,可提供成功、失败和完成时的回调函数uni.getStorage({key, success, fail, complete})
:从本地缓存中异步获取数据,可提供成功、失败和完成时的回调函数uni.setStorageSync(key, data)
:将数据同步存储到本地缓存中,即时执行,没有回调函数uni.getStorageSync(key)
:从本地缓存中同步获取数据,即时执行,没有回调函数
// 异步方法
uni.setStorage({
key: 'key',
data: 'value',
success: function () {
console.log('数据存储成功');
},
fail: function (error) {
console.log('数据存储失败:', error);
}
});
// 获取数据
uni.getStorage({
key: 'key',
success: function (res) {
console.log('获取数据成功:', res.data);
},
fail: function (error) {
console.log('获取数据失败:', error);
}
});
// 同步方法
uni.setStorageSync('projectId', this.projectId); // 缓存数据
let x = uni.getStorageSync('projectId'); // 提取数据
下拉单选框组件的使用
选择使用uniapp社区的select-lay - DCloud 插件市场 插件。该插件可以实现自定义数据索引对象,对于一些传入复杂的数据结构单选展示具有很好的效果。
<select-lay :value="tval" name="name" :options="datalist" @selectitem="selectitem"></select-lay>
自定义数据结构的写法为:
<select-lay :zindex="998" :value="choicedID" name='Name' placeholder="请选择拓扑名称"
slabel="t_name" svalue="t_id"
:options="project" @selectitem="choicet_Name"></select-lay>
value要与选择框最终传给的变量值相同,否则选择之后在UI上面无法显示选择后的结果。
组件层级设置
在UI中不同组件显示过程中,通过参数设置不同的层可以使一部分组件显示在另一部分组建的上方。
uniapp中部分组件可以通过z-index
参数来设置组件的层级。z-index 属性设置元素在渲染时的z轴顺序。在同一个层叠上下文下z-index较大的元素会覆盖在z-index较小的元素上面。简单来说,就是当该参数设置的值越大,则会显示在更上层。
app端z-index默认值为0,web端默认值为auto。
z-index | uni-app-x (dcloud.net.cn)
props参数的使用
props
可以是数组或对象,用于接收来自父组件的数据。props
可以是简单的数组,或者使用对象作为替代,对象允许配置高级选项,如类型检测、自定义验证和设置默认值。
表单检查与校验
.some方法
.some()
方法是 JavaScript 数组的一个方法,用于测试数组中的元素是否至少有一个满足提供的测试函数。如果至少有一个元素让测试函数返回 true
,那么 .some()
方法就会返回 true
;否则返回 false
。
// 是否有任何数字大于 10
const numbers = [1, 5, 10, 15, 20];
const hasNumberGreaterThanTen = numbers.some(number => number > 10);
console.log(hasNumberGreaterThanTen); // 输出: tr
检查对应两组变量之间是否相同
// 检查哪些属性发生了改变
const changedProperties = ['email', 'nickname', 'phone'].some(prop => {
return this.accountForm[prop] !== this.profile[prop];
});
弹窗的实现
Popup 弹出层 | uView 2.0 - 全面兼容 nvue 的 uni-app 生态框架 - uni-app UI 框架 (uviewui.com)
通过uview中u-popup组件实现
<u-popup :show="popShow" mode="center">
<view >
<text>确认取消?</text>
<u-button type="primary" style="margin-top: 5rpx;" text="返回" @click="popShow = false"></u-button>
<u-button type="error" style="margin-top: 5rpx;" text="确认" @click="cancelAppoint(cancelId)"></u-button>
</view>
</u-popup>
弹出消息后延时跳转
uni.showToast({
title: ' 预约成功!',
duration: 1000
});
setTimeout(function() {
uni.reLaunch({
url: '/pages/tabBar/home/index'
});
}, 1000);
post传递query形式数据
问题
使用post携带query数据发送请求。
背景
使用uview发送请求,默认是可以提前对请求进行设置。下面是uview官网提供的配置。通过定义并导出配置即可实现在对所有请求的全局配置。在不配置headers中datatype的情况下,uview默认post发送的是body的请求。如果要使用post请求发送数据则需要修改headers中Content-Type的值。
const install = (Vue, vm) => {
baseURL: '',
header: {},
method: 'GET',
dataType: 'json',
// #ifndef MP-ALIPAY
responseType: 'text',
// #endif
// 注:如果局部custom与全局custom有同名属性,则后面的属性会覆盖前面的属性,相当于Object.assign(全局,局部)
custom: {}, // 全局自定义参数默认值
// #ifdef H5 || APP-PLUS || MP-ALIPAY || MP-WEIXIN
timeout: 60000,
// #endif
// #ifdef APP-PLUS
sslVerify: true,
// #endif
// #ifdef H5
// 跨域请求时是否携带凭证(cookies)仅H5支持(HBuilderX 2.6.15+)
withCredentials: false,
// #endif
// #ifdef APP-PLUS
firstIpv4: false, // DNS解析时优先使用ipv4 仅 App-Android 支持 (HBuilderX 2.8.0+)
// #endif
// 局部优先级高于全局,返回当前请求的task,options。请勿在此处修改options。非必填
// getTask: (task, options) => {
// 相当于设置了请求超时时间500ms
// setTimeout(() => {
// task.abort()
// }, 500)
// },
// 全局自定义验证器。参数为statusCode 且必存在,不用判断空情况。
validateStatus: (statusCode) => { // statusCode 必存在。此处示例为全局默认配置
return statusCode >= 200 && statusCode < 300
}
}
解决方法
post发送query请求时headers中Content-Type的值为application/x-www-form-urlencoded
,而发送body请求时值为application/json
。由于上述为全局设置,而项目中使用post发送query形式的数据较少,因此,可以在发送query请求时单独设置headers中Content-Type的值。
// query形式的http传参
export function http_a_post_query(path,params){
let formBody = Object.keys(params).map(key => key + '=' + params[key]).join('&');
console.log('http_a_post=', projectConfig.baseUrl_a + path);
return http.post(projectConfig.baseUrl + path, params,{header:{'content-type': 'application/x-www-form-urlencoded'}});
}
图片上传
-
使用uni.chooseImage从文件中选择图片,并使用uni.uploadFile上传图片。选择图片结束后。
获取文件路径后,以
content-type=multipart/form-data
的形式,使用post协议上传至服务器。同时,接收服务器返回的图片地址。
uploadPic() {
uni.chooseImage({
count: 1,
sizeType: ['original', 'compressed'],
success: res => {
console.log(projectConfig.baseUrl + '/v1/dms/upload/picture/local');
uni.uploadFile({
url: projectConfig.baseUrl + '/v1/dms/upload/picture/local',
filePath: res.tempFilePaths[0],
name: 'files',
header: {
'Authorization': 'Bearer ' + uni.getStorageSync('token'),
},
complete: (res) => {
console.log('res:', JSON.parse(res.data)[0]);
this.form.device_image = JSON.parse(res.data)[0];
this.$u.toast('图片上传完毕!');
this.upPicMsg = '重新上传'
}
})
}
})
},
统计图实现
思路:对后端返回的数据格式化成组件所接受的数据格式,通过图表组件实现。
HTML部分
<qiun-data-charts :ontouch="true" type="line" :opts="line_opts2" :localdata="trendData" />
:ontouch="true"
表示组件是否应该响应触摸事件。type="line"
指定了图表的类型为折线图。:opts="line_opts2"
是一个包含图表配置的对象,在本地的js中设定,例如轴的标签、网格线等。:localdata="trendData"
是一个包含要显示的数据集的对象
数据格式
第一种格式
let res = {
categories: ["2016","2017","2018","2019","2020","2021"], // 横坐标的标签
series: [
{
name: "目标值",
data: [35,36,31,33,13,34] // 第一条数据
},
{
name: "完成量",
data: [18,27,21,24,6,28] // 第二条数据
}
]
};
第二种格式
localdata:[
{value:35, text:"2016", group:"目标值"},
{value:18, text:"2016", group:"完成量"},
{value:36, text:"2017", group:"目标值"},
{value:27, text:"2017", group:"完成量"},
{value:31, text:"2018", group:"目标值"},
{value:21, text:"2018", group:"完成量"},
{value:33, text:"2019", group:"目标值"},
{value:24, text:"2019", group:"完成量"},
{value:13, text:"2020", group:"目标值"}, // 根据group类确定两类或是多类数据
{value:6, text:"2020", group:"完成量"},
{value:34, text:"2021", group:"目标值"},
{value:28, text:"2021", group:"完成量"}
]
表格的实现
问题
uniapp自带的表格无法完成合并单元格等操作,直接使用 rowspan
和 colspan
会在不同端中产生兼容性问题。
uniapp uni-table表格组件 合并单元格_uni-table合并单元格-CSDN博客
方法
直接使用HTML中的table、tr、td
标签来实现。需要注意的是:v-for不能在以下标签里使用:
thead
tbody
tfoot
th
td
在实际使用中如果希望使用循环来显示后端返回的不同长度的数据,可以在外侧再嵌套一层。
<template v-for="(type, typeIndex) in deviceParam">
<tr :key="typeIndex">
<!-- 类型标题行,使用rowspan属性来合并单元格 -->
<th :rowspan="type.deviceParamInfoVos.length + 1">
{{ type.device_param_type_name }}
</th>
<!-- 使用v-for遍历每个参数 -->
<tr v-for="param in type.deviceParamInfoVos" :key="param.device_param">
<td>{{ param.device_param_name }}</td>
<td>{{ param.device_param_value + param.device_param_unit }}</td>
</tr>
</tr>
</template>