前言
做小程序开发有段时间了,开发中遇到各种各样的UI需求,很多都是类似甚至重复。虽然可以使用template
和include
来实现代码复用,但是它们都没有逻辑处理能力,有时一些简单的逻辑,我们更加希望可以直接被模板内部实现掉,所以更好的方法是直接封装成组件,最大程度的实现代码复用。
本文及后续一系列文章将会介绍常用UI组件的封装,方便今后开发中使用,所有样式源码及示例将提交至开源项目wx-abui
搜索框组件:ab-search-bar
搜索框是常用组件之一,也是本文封装的对象。在封装时我主张对外暴露出常用的属性和方法,以便在项目中重复使用时减少对源码的修改。
github传送门:https://github.com/albert-lii/wx-abui/tree/master/widgets/ab-search-bar
demo传送门:https://github.com/albert-lii/wx-abui/tree/master/pages/mainex
样式示例
搜索框样式搜索框样式
自定义属性和方法
自定义属性 | 描述 |
---|---|
placeholder | 搜索框中的提示字 |
value | 搜索框的内容 |
自定义方法 | 描述 |
---|---|
bindinput | 输入监听 |
bindclear | 清除内容按钮点击监听 |
bindback | 返回按钮点击监听 |
bindsearch | 搜索按钮点击监听 |
使用示例
<view class="container">
<!-- 搜索框 -->
<ab-search-bar placeholder="请输入关键字" value="{{searchValue}}" bindinput="searchInput" bindsearch="searchTab" bindclear="searchClear" />
</view>
const LABEL_SOURCE = require('../../utils/label_flow_source.js');
Page({
data: {
searchValue: ''
},
/*=========================================================
* 搜索框相关
*=========================================================*/
/**
* 搜索框输入监听
*/
searchInput: function (e) {
console.log('searchInput >>> ' + e.detail.value);
},
/**
* 搜索框清除监听
*/
searchClear: function (e) {
console.log('searchClear');
},
/**
* 搜索框右侧按钮点击监听
*/
searchTab: function (e) {
let _key = e.detail.key;
let _value = e.detail.value;
if (_key === 'search') {
console.log('searchTab >>> search');
console.log(e.detail);
} else if (_key === 'back') {
console.log('searchTab >>> back');
console.log(e.detail);
}
}
})
{
"navigationBarTitleText": "abui",
"usingComponents": {
"ab-search-bar": "../../abui/widgets/ab-search-bar/ab-search-bar"
}
}
源码
- ab-search-bar.wxml
<view class="ab-search-bar">
<view class="ab-search-bar__box">
<icon class="ab-search-bar__icon" type="search" size="{{iconSize}}" />
<view class="ab-search-bar__divider" />
<input class="ab-search-bar__input" type="text" placeholder="{{placeholder}}" value="{{value}}" bindinput="_searchInput" bindconfirm="_searchConfirm" confirm-type="search" />
<view class="ab-search-bar__icon-clear" wx:if="{{value.length > 0}}" bindtap="_searchClear">
<icon type="clear" size="{{iconSize}}" />
</view>
</view>
<view class="ab-search-bar__search-btn" bindtap="_searchConfirm" data-key="{{value.length > 0?'search':'back'}}">{{value.length > 0?'搜索':'返回'}}
</view>
</view>
- ab-search-bar.wxss
.ab-search-bar {
position: relative;
display: flex;
width: 100%;
padding: 9rpx 15rpx;
box-sizing: border-box;
border-top: 1rpx solid #d7d6dc;
border-bottom: 1rpx solid #d7d6dc;
background-color: #ececec;
}
.ab-search-bar__box {
position: relative;
display: flex;
flex-direction: row;
align-items: center;
width: 100%;
padding-left: 15rpx;
padding-right: 15rpx;
box-sizing: border-box;
border-radius: 4px;
border: 1rpx solid #e6e6ea;
background: #fff;
}
.ab-search-bar__icon {
position: relative;
margin-right: 15rpx;
font-size: 0;
}
.ab-search-bar__divider {
position: relative;
width: 1px;
height: calc(100% - 20rpx);
margin-right: 15rpx;
background-color: #aaa;
}
.ab-search-bar__input {
width: 100%;
height: 50rpx;
font-size: 25rpx;
line-height: 50rpx;
color: #2e2e2e;
}
.ab-search-bar__icon-clear {
position: relative;
display: flex;
align-items: center;
height: 100%;
top: 0;
left: 0;
right: 0;
bottom: 0;
padding-left: 15rpx;
box-sizing: content-box;
}
.ab-search-bar__search-btn {
font-size: 32rpx;
line-height: 64rpx;
text-align: center;
margin-left: 15rpx;
color: #2e2e2e;
white-space: nowrap;
}
- ab-search-bar.json
{
"component": true,
"usingComponents": {}
}
- ab-search-bar.js
Component({
properties: {
// 搜索框的提示字
placeholder: {
type: String,
value: '请输入搜索内容',
},
// 搜索框的初始内容
value: {
type: String,
value: ''
}
},
data: {
// icon 的大小
iconSize: 15
},
attached() {
try {
let _screenWidth = wx.getSystemInfoSync().screenWidth;
this.setData({
iconSize: Math.round(_screenWidth / 750 * 25)
});
} catch (e) {
console.error(e);
}
},
methods: {
/**
* 输入事件
*/
_searchInput: function(e) {
// 输入的内容
let _value = e.detail.value;
this.setData({
value: _value
});
this.triggerEvent('input', {
value: _value
});
},
/**
* 清除输入内容事件
*/
_searchClear: function(e) {
this.setData({
value: ''
});
this.triggerEvent('clear', {});
},
/**
* 搜索/返回 事件
*/
_searchConfirm: function(e) {
let _key = e.target.dataset.key;
if (_key === 'back') {
this.setData({
value: ''
});
}
this.triggerEvent('search', {
key: _key,
value: this.data.value
});
}
}
})
网友评论