商业微信小程序开发:小白轻松接单(外卖-点餐页(搜索功能))(2)

接上文继续实现点餐页面。回看前一篇文章,发现搜索框样式布局已经实现,但是逻辑部分忘记写了,所以本篇文章就以搜索框逻辑开篇。

首先看一下搜索页面的示意图

1、搜索页面布局与功能实现

首先需要注意的一点是,点餐页面最上方的搜索框是一个"死框",即仅仅是一个点击跳转至搜索页面的"装饰",并没有搜索功能。

同样,样式布局就不过多解释,直接放源码,有需要的自己复制

<view style="padding-bottom: 10rpx;">
	<view class="search-input">
		<image src="https://7761-waimai-user-6g2zcvhp46ac02a8-1326568420.tcb.qcloud.la/static/diandan/sousuo.png?sign=fd87793ca3d569294b92116ce843fb1b&t=1719890621" mode="aspectFill"></image>
		<view @click="search" class="custom-button">搜索</view>
		<!-- @confirm="search"是可以实现点击键盘的搜索也能进行商品检索 -->
		<input type="text" @confirm="search" :focus="true" v-model="keyword.data" placeholder="" 
			confirm-type="search"/>
	</view>
</view>
.search-input{
	background: #FFFFFF;
	font-size: 28rpx;
	display: flex;
	flex-direction: row;
	flex: 1;
	position: relative;
	align-items: center;
	height: 90rpx;
	width: 100%;
}
.search-input image:nth-child(1){
	border-radius: 50upx;
	width: 35rpx;
	height: 35rpx;
	position: absolute;
	left: 50rpx;
	align-self: center;
}
.search-input input{
	background-color: #f4f4f4;
	width: 100%;
	color: #b2b2b2;
	padding-left: 80upx;
	padding-right: 75px;
	border-radius: 50rpx;
	height: 60rpx;
	margin-left: 20rpx;
}
.custom-button{
	/* 48*27 */
	position: absolute;
	top: 50%;
	right: 0;
	font-size: 25rpx;
	transform: translateY(-50%);
	background-color: #81614A; /* 红色背景 */
	color: #fff;
	padding: 4px 10px;
	border-radius: 15px; /* 边框弧度 */
	cursor: pointer;
	user-select: none;
	margin-right: 5px; /* 设置按钮与输入框的间距 */
	display: flex;
	align-items: center;
	justify-content: center;
	cursor: pointer;
	-webkit-tap-highlight-color: transparent;
	outline: none;
}

1.1、搜索功能实现

先放代码:

// 触发搜索
	async function search(){
		// 本地缓存搜索历史
		if(keyword.data==''){
			const res = await db.collection('goods').get()
			card.value = res.data
		}
		let search_arr = wx.getStorageSync('search_key') || []  //取出本地缓存记录
		var specialCharacters = /[!@#$%^&*(),.?":{}|<> ]/
		if(keyword.data!=''&& !specialCharacters.test(keyword.data)){
			search_arr.unshift(keyword.data)  //unshift()函数是将值插入到数组的前端
			wx.setStorageSync('search_key',search_arr)
		}
		card.value=[]
		data_search()
	}
	// 数据库模糊查询
	async function data_search(){
		wx.showLoading({title:'加载中...',mask:true})
		// load_data.loaded=false
		// 设置模糊字段匹配
		let query = _.or([
			{
				category:db.RegExp({
					regexp:keyword.data,
					options:'i'
				})
			},
			{
				goods_title:db.RegExp({
					regexp:keyword.data,
					options:'i'
				})
			}
		])
		const res = await db.collection('goods').where(query).get()
		show_history.value = false
		card.value = res.data
		if(card.value.length===0){
			show_1.value = true
		}else{
			show_1.value = false
		}
		wx.hideLoading()
	}

说一下思路:在输入关键字后点击搜索,是根据搜索的关键字在数据库"goods"中提取"分类"、"商品标题"中含有关键字的商品,具体实现如方法data_search()。搜索过的关键字会存储在本地,以便在"历史记录"中展示。(复制完无法直接使用,需要创建对应的响应式变量,例如card、show_history、show_1。)

如何创建本地存储:

wx.setStorageSync('search_key',search_arr)

1.2、商品列表布局

同样,直接放代码,就不过多解释

<view class="goods_view" v-for="(item,index) in card" :key="index" @click="show_details(item._id)">
	<view class="goods_before">
		<view class="goods_image">
			<image :src="item.goods_cover" mode="aspectFill"></image>
		</view>
		<view class="goods_title overflow">{{item.goods_title}}</view>
	</view>
	<view class="goods_price">
		<view class="price_view">
			<text>¥ </text>
			<text>{{getInt(item.goods_price)}}</text>
			<text>.{{getDec(item.goods_price)}}</text>
		</view>
	</view>
</view>
<view style="height: 100rpx;"></view>
<view class="centered-container" v-if="card.length==0 && show_history == false && show_1">
	<image class="img" src="https://7761-waimai-user-6g2zcvhp46ac02a8-1326568420.tcb.qcloud.la/static/other/none_data.png?sign=e6636bc868bfbebec9d33cb1081baa23&t=1723096179" mode="aspectFill"></image>
	<view class="text">
		没找到对应商品,再看看~
	</view>
</view>

对应的css样式:

.goods_view{
	background-color: #FFFFFF;
	padding: 10rpx 20rpx;
	margin: 10rpx 15rpx;
	border-radius: 10rpx;
	display: flex;
	justify-content: space-between;
}
.goods_before{
	display: flex;
}
.goods_image{
	width: 100rpx;
	height: 100rpx;
	padding: 5rpx;
}
.goods_image image{
	width: 100rpx;
	height: 100rpx;
	border-radius: 10rpx;
}
.goods_title{
	font-size: 28rpx;
	font-family: "黑体";
	margin-left: 20rpx;
	display: flex;
	align-items: center;
}
.overflow{
	overflow: hidden;
	text-overflow: ellipsis;
	display: -webkit-box;
	-webkit-line-clamp: 1;
	-webkit-box-orient: vertical;
}
.goods_price{
	display: flex;
	align-items: center;
}
.price_view{
	display: flex;
	font-size: 28rpx;
	margin-right: 10rpx;
	font-weight: bold;
}
.centered-container{
	position: absolute;
	top: 50%;
	left: 50%;
	transform: translate(-50%, -50%);
	text-align: center;
	width: 200px; 
	height: 200px;
	margin-top: -50px;
}
.img {
	width: 200px;
	height: 200px;
	display: block;
}
.text {
	margin-top: 20px;
	text-align: center;
	color: #999;
}

2、历史记录布局与功能实现

2.1、历史记录布局

直接放代码

<block v-if="history.length>0 && show_history">
	<view class="history">
		<text>历史记录</text>
		<image src="../../static/search/shanchu.svg" mode="aspectFill" @click="del"></image>
	</view>
	<view class="history-text">
		<text v-for="(item,index) in history" :key="index" @click="history_search(item)">{{item}}</text>
	</view>
</block>

注意,上面有些响应式变量需要自己创建,同时有一些静态文件,自己在网上找一下对应的图标进行替换。

推荐一个图标网站: iconfont-阿里巴巴矢量图标库

对应的CSS样式:

.history image{
	display: block;
	width: 30rpx;
	height: 30rpx;
}
.history{
	display: flex;
	align-items: center;
	justify-content: space-between;
	margin: 40rpx 20rpx;
	font-size: 30rpx;
	font-weight: bold;
	font-family: "黑体";
}
.history-text{
	display: flex;
	flex-wrap: wrap;
	margin: 0 20rpx;
}
.history-text text{
	background-color: #FFFFFF;
	margin: 0 20rpx 20rpx 0;
	border-radius: 7rpx;
	padding: 10rpx 20rpx;
	font-size: 28rpx;
	font-family: "黑体";
}

2.2、历史记录功能实现

// 点击搜索历史记录触发搜索
	function history_search(item){
		keyword.data = item
		card.value=[]
		data_search()
	}
	// 清空搜索历史
	function del(){
		wx.showModal({
			title:'提示',
			content:'确定要删除吗?',
			success:function(sm){
				if(sm.confirm){
					wx.removeStorageSync('search_key')
					history.value=[]
				}else if(sm.cancel){
					console.log('用户取消')
				}
			}
		})
	}

上面代码应该没什么需要讲解的,比较简单,若不明白的可以留言,看到就会回。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值