探讨uniapp的组件使用的问题
1 视图容器
1.1 view
Flex是Flexible Box的缩写,意为“弹性布局”,用来为盒状模型提供最大的灵活性。
当设置display: flex
后,继续给view等容器组件设置flex-direction:row或column
,就可以在该容器内按行或列排布子组件。uni-app推荐使用flex布局, 因为flex布局有利于跨更多平台,尤其是采用原生渲染的平台。
1.2 scroll-view
- scroll-view是区域滚动,不会触发页面滚动,无法触发pages.json配置的下拉刷新、页面触底onReachBottomDistance、titleNView的transparent透明渐变
- 可滚动视图区域。用于区域滚动。
- 需注意在webview渲染的页面中,区域滚动的性能不及页面滚动。
<template><view><page-head title="scroll-view,区域滚动视图"></page-head><view class="uni-padding-wrap uni-common-mt"><view class="uni-title uni-common-mt">Vertical Scroll<text>\n纵向滚动</text></view><view><!-- scroll-top Number/String 设置竖向滚动条位置 --><!-- scroll-y Boolean false 允许纵向滚动 --><!-- @scrolltoupper EventHandle 滚动到顶部/左边,会触发 scrolltoupper 事件 --><!-- @scrolltolower EventHandle 滚动到底部/右边,会触发 scrolltolower 事件 --><!-- @scroll EventHandle 滚动时触发,event.detail = {scrollLeft, scrollTop, scrollHeight, scrollWidth, deltaX, deltaY} --><scroll-view :scroll-top="scrollTop" scroll-y="true" class="scroll-Y" @scrolltoupper="upper" @scrolltolower="lower"@scroll="scroll"><view id="demo1" class="scroll-view-item uni-bg-red">A</view><view id="demo2" class="scroll-view-item uni-bg-green">B</view><view id="demo3" class="scroll-view-item uni-bg-blue">C</view></scroll-view></view><!-- @tap (event: MouseEvent) => void - 手指触摸后马上离开 --><!-- @longpress (event: Event) => void - 如果一个组件被绑定了 longpress 事件,那么当用户长按这个组件时,该事件将会被触发。 --><view @tap="goTop" class="uni-link uni-center uni-common-mt">点击这里返回顶部</view><view class="uni-title uni-common-mt">Horizontal Scroll<text>\n横向滚动</text></view><view><scroll-view class="scroll-view_H" scroll-x="true" @scroll="scroll" scroll-left="120"><view id="demo1" class="scroll-view-item_H uni-bg-red">A</view><view id="demo2" class="scroll-view-item_H uni-bg-green">B</view><view id="demo3" class="scroll-view-item_H uni-bg-blue">C</view></scroll-view></view><view class="uni-common-pb"></view></view></view>
</template>
自定义下拉刷新
- 注意,在webview渲染时,自定义下拉刷新的性能不及pages.json中配置的原生下拉刷新。
1.3 pages.json中配置的原生下拉刷新
实现思路:
第一步,在pages.json中配置该页面,允许进行下拉刷新
第二步,在下拉刷新的生命周期函数中,处理逻辑
- 在pages.json中配置该页面,允许进行下拉刷新
{"pages": [{"path": "pages/index/index","style": {"navigationBarTitleText": "首页",//设置页面标题文字"enablePullDownRefresh":true//开启下拉刷新}},...]
}
- 在下拉刷新的生命周期函数中,处理逻辑
onPullDownRefresh() {console.log('onPullDownRefresh');this.initData();
},
1.4swiper
滑块视图容器。一般用于左右滑动或上下滑动,比如banner轮播图。
注意滑动切换和滚动的区别,滑动切换是一屏一屏的切换。swiper下的每个swiper-item是一个滑动切换区域,不能停留在2个滑动区域之间。
<view class="uni-margin-wrap"><!-- circular Boolean false 是否采用衔接滑动,即播放到末尾后重新回到开头 --><!-- indicator-dots Boolean false 是否显示面板指示点 --><!-- autoplay Boolean false 是否自动切换 --><!-- interval Number 5000 自动切换时间间隔 --><!-- duration Number 500 滑动动画时长 --><swiper class="swiper" circular :indicator-dots="indicatorDots" :autoplay="autoplay" :interval="interval" :duration="duration"><swiper-item><view class="swiper-item uni-bg-red">A</view></swiper-item><swiper-item><view class="swiper-item uni-bg-green">B</view></swiper-item><swiper-item><view class="swiper-item uni-bg-blue">C</view></swiper-item></swiper></view>
2 基础内容
2.1 icon图标
uniapp中自带的icon很少,不管哪个UI框架都有这个问题,最好就是引用来自iconfont之类的自定义项目文件,我见过很多项目是将文件直接下载下来使用,弊端是操作麻烦,颜色不可修改,只能用已下载的颜色,最好的方式当然是使用字体文件来实现,这里就详细说下操作流程
方案步骤
步骤主要分两块,一块是iconfont上的项目管理,一块是本地uniapp项目中的配置
iconfont端
iconfont端主要分3步:
-
创建项目
-
选择图标
-
导出字体文件
项目端引用
项目端引用主要分3步:
4. 文件下载
- CSS引用
然后进入到App.vue中的style进行CSS引用
<style>@import '@/static/icon/iconfont.css';
</style>
- CSS引用路径修改
这里是个小坑,因为默认网页中css引用当前文件夹下的字体文件是没问题的,但是在uniapp中需要去修改iconfont.css中的引用字体的文件位置
@font-face {font-family: "iconfont"; /* Project id 3355581 */src: url(iconfont.woff2?t=1650891154292') format('woff2'),url('iconfont.woff?t=1650891154292') format('woff'),url('iconfont.ttf?t=1650891154292') format('truetype');
}
改为如下(记得按你自己的路径来修改)
@font-face {font-family: "iconfont"; /* Project id 3355581 */src: url('/static/icon/iconfont.woff2?t=1650891154292') format('woff2'),url('/static/icon/iconfont.woff?t=1650891154292') format('woff'),url('/static/icon/iconfont.ttf?t=1650891154292') format('truetype');
}
至此就可以在前端进行引用了,eg:
<view><view class="iconfont icon-huiju2" style="font-size: 100rpx; color: green;;"></view></view>
2.2 text组件
文本组件。用于包裹文本内容。
- 支持 \n 方式换行。
<view class="text-box"><text>{{text}}</text></view>
2.3 rich-text
富文本。支持默认事件,包括:click、touchstart、touchmove、touchcancel、touchend、longpress。
export default {data() {return {title: 'rich-text',nodes: [{// name 标签名 String 是 支持部分受信任的 HTML 节点name: 'div',// attrs 属性 Object 否 支持部分受信任的属性,遵循 Pascal 命名法attrs: {class: 'div-class',style: 'line-height: 60px; color: red; text-align:center;'},// children 子节点列表 Array 否 结构和 nodes 一致children: [{type: 'text',text: 'Hello uni-app!'}]}],strings: '<div style="text-align:center;"><img src="https://web-assets.dcloud.net.cn/unidoc/zh/uni@2x.png"/></div>'}}}
- nodes 不推荐使用 String 类型,性能会有所下降。
- rich-text 组件内屏蔽所有节点的事件。所以如果内容中有链接、图片需要点击,则不能使用rich-text
- attrs 属性不支持 id ,支持 class
2.4 progress
进度条。
<view class="uni-padding-wrap uni-common-mt"><view class="progress-box"><!-- 属性名 类型 默认值 说明 --><!-- percent Number 无 百分比0~100 --><!-- show-info Boolean false 在进度条右侧显示百分比 --><!-- stroke-width Number 6 进度条线的宽度,单位px --><progress :percent="pgList[0]" show-info stroke-width="3" /></view><view class="progress-box"><progress :percent="pgList[1]" stroke-width="3" /><uni-icons type="close" class="progress-cancel" color="#dd524d"></uni-icons></view><view class="progress-box"><progress :percent="pgList[2]" stroke-width="3" /></view><view class="progress-box"><!-- activeColor Color #09BB07(百度为#E6E6E6) 已选择的进度条的颜色 --><progress :percent="pgList[3]" activeColor="#10AEFF" stroke-width="3" /></view><view class="progress-control"><button type="primary" @click="setProgress">设置进度</button><button type="warn" @click="clearProgress">清除进度</button></view></view>
3 表单组件
3.1 button
button 组件的点击遵循 vue 标准的 @click事件。
button 组件没有 url 属性,如果要跳转页面,可以在@click中编写,也可以在button组件外面套一层 navigator 组件。举例,如需跳转到about页面,可按如下几种代码写法执行:
<template><view><navigator url="/pages/about/about"><button type="default">通过navigator组件跳转到about页面</button></navigator><button type="default" @click="goto('/pages/about/about')">通过方法跳转到about页面</button><button type="default" @click="navigateTo('/pages/about/about')">跳转到about页面</button><!-- 这种写法只有h5平台支持,不跨端,不推荐使用 --></view>
</template>
<script>export default {methods: {goto(url) {uni.navigateTo({url:url})}}}
</script>
3.2 checkbox-group
多项选择器,内部由多个 checkbox 组成。
<template><view><page-head :title="title"></page-head><view class="uni-padding-wrap uni-common-mt"><view class="uni-title uni-common-mt">默认样式</view><view><checkbox-group><label><!-- checked Boolean false 当前是否选中,可用来设置默认选中 --><checkbox value="cb1" checked="true" />选中</label><label><checkbox value="cb" />未选中</label></checkbox-group></view><view class="uni-title uni-common-mt">不同颜色和尺寸的checkbox</view><view><checkbox-group><label><checkbox value="cb1" checked="true" color="#FFCC33" style="transform:scale(0.7)" />选中</label><label><!-- color Color checkbox的颜色,同css的color --><checkbox value="cb" color="#FFCC33" style="transform:scale(0.7)" />未选中</label></checkbox-group></view></view><view class="uni-padding-wrap"><view class="uni-title uni-common-mt">推荐展示样式<text>\n使用 uni-list 布局</text></view></view><!-- .uni-list {background-color: #FFFFFF;position: relative;width: 100%;display: flex;flex-direction: column;} --><view class="uni-list"><!-- @change EventHandle <checkbox-group>中选中项发生改变是触发 change 事件 --><checkbox-group @change="checkboxChange"><label class="uni-list-cell uni-list-cell-pd" v-for="item in items" :key="item.value"><view><checkbox :value="item.value" :checked="item.checked" /></view><view>{{item.name}}</view></label></checkbox-group></view></view>
</template>
<script>export default {data() {return {title: 'checkbox 复选框',items: [{value: 'USA',name: '美国'},{value: 'CHN',name: '中国',checked: 'true'},{value: 'BRA',name: '巴西'},{value: 'JPN',name: '日本'},{value: 'ENG',name: '英国'},{value: 'FRA',name: '法国'}]}},methods: {checkboxChange: function(e) {console.log('e = ', e);var items = this.items,values = e.detail.value;for (var i = 0, lenI = items.length; i < lenI; ++i) {const item = items[i]if (values.indexOf(item.value) >= 0) {this.$set(item, 'checked', true)} else {this.$set(item, 'checked', false)}}}}}
</script><style>/* justify-content是用于设置或检索弹性盒子元素在主轴(横轴)方向上的对齐方式。它常用于CSS的Flexbox布局。以下是justify-content的常用属性值:flex-start:默认值,项目位于容器的开头。flex-end:项目位于容器的结尾。center:项目位于容器的中心。space-between:项目位于各行之间留有空白的容器内,第一行在容器开头,最后一行在容器结尾。space-around:每个项目的左右撑开距离相等,项目与项目之间以及头尾的间距相等。space-evenly:每个间距,均匀分布为容器宽度的一半。需要注意的是,justify-content属性在Internet Explorer和Safari浏览器中不被支持。 */.uni-list-cell {justify-content: flex-start}
</style>
3.3 editor
富文本编辑器,可以对图片、文字格式进行编辑和混排。
3.4 form
表单,将组件内的用户输入的<switch> <input> <checkbox> <slider> <radio> <picker>
提交。
当点击 <form
> 表单中 formType 为 submit 的 <button>
组件时,会将表单组件中的 value 值进行提交,需要在表单组件中加上 name 来作为 key。
<template><view><page-head title="form"></page-head><view class="uni-padding-wrap uni-common-mt"><form @submit="formSubmit" @reset="formReset"><view class="uni-form-item uni-column"><view class="title">姓名</view><!-- .uni-input {height: 50rpx;padding: 15rpx 25rpx;line-height:50rpx;font-size:28rpx;background:#FFF;flex: 1;} --><!-- flex: 1表示项目的放大比例和缩小比例都为1,即当存在剩余空间时,该项目将自动放大以占据更多的空间,而在超出父容器时,超出部分将等分缩小的比例。这是一种常用的自适应布局方式,可以将父容器的空间自动分配给子元素,以达到自动调整布局的效果。 --><input class="uni-input" name="nickname" placeholder="请输入姓名" /></view><view class="uni-form-item uni-column"><view class="title">性别</view><radio-group name="gender"><label><radio value="男" /><text>男</text></label><label><radio value="女" /><text>女</text></label></radio-group></view><view class="uni-form-item uni-column"><view class="title">爱好</view><checkbox-group name="loves"><label><checkbox value="读书" /><text>读书</text></label><label><checkbox value="写字" /><text>写字</text></label></checkbox-group></view><view class="uni-form-item uni-column"><view class="title">年龄</view><slider value="20" name="age" show-value></slider></view><view class="uni-form-item uni-column"><view class="title">保留选项</view><view><switch name="switch" /></view></view><view class="uni-btn-v"><button form-type="submit">Submit</button><button type="default" form-type="reset">Reset</button></view></form></view></view>
</template>
<script>import graceChecker from "../../../common/graceChecker.js"export default {data() {return {}},methods: {formSubmit: function(e) {console.log('form发生了submit事件,携带数据为:' + JSON.stringify(e.detail.value))//定义表单规则var rule = [{name:"nickname", checkType : "string", checkRule:"1,3", errorMsg:"姓名应为1-3个字符"},{name:"gender", checkType : "in", checkRule:"男,女", errorMsg:"请选择性别"},{name:"loves", checkType : "notnull", checkRule:"", errorMsg:"请选择爱好"}];//进行表单检查var formData = e.detail.value;var checkRes = graceChecker.check(formData, rule);if(checkRes){uni.showToast({title:"验证通过!", icon:"none"});}else{uni.showToast({ title: graceChecker.error, icon: "none" });}},formReset: function(e) {console.log('清空数据')}}}
</script><style>.uni-form-item .title {padding: 20rpx 0;}
</style>
解读一下代码:
<form @submit="formSubmit" @reset="formReset">
formSubmit: function(e) {console.log('e = ', e);console.log('form发生了submit事件,携带数据为:' + JSON.stringify(e.detail.value))//定义表单规则var rule = [{name:"nickname", checkType : "string", checkRule:"1,3", errorMsg:"姓名应为1-3个字符"},{name:"gender", checkType : "in", checkRule:"男,女", errorMsg:"请选择性别"},{name:"loves", checkType : "notnull", checkRule:"", errorMsg:"请选择爱好"}];//进行表单检查var formData = e.detail.value;var checkRes = graceChecker.check(formData, rule);if(checkRes){uni.showToast({title:"验证通过!", icon:"none"});}else{uni.showToast({ title: graceChecker.error, icon: "none" });}}
为方便做表单验证,uni ui提供了组件,参考:https://ext.dcloud.net.cn/plugin?id=2773