城市选择页面
城市选择页面即点击出现一个城市列表,需要实现点击相应的城市后,跳转到首页获取所选择城市的天气数据。这里城市数据是格式无序的列表:{“letter”:“B”,“name”:“北京市“}
代码组成
-
.js后缀的JS脚本逻辑文件 citychoose.js
-
.json后缀的JSON配置文件 citychoose.json
-
.wxml后缀的WXML模板文件 citychoose.wxml
-
.wxss后缀的WXSS样式文件 citychoose.wxss
具体实现
1. 创建项目和目录文件结构
和其他页面差不多,在创建空的citychoose文件夹后,在其中添加四个文件,分别是citychoose. wxml, citychoose. wxss, citychoose.js, citychoose. json,并在.json中添加大括号,防止报错。
2. 页面配置
citychoose中的一些关键代码
- 如果按照字母顺序进行排序,则需要排序再遍历。代码如下:
// 按照字母顺序生成需要的数据格式
getSortedAreaObj(areas) {
// let areas = staticData.area
areas = areas.sort((a, b) => {
if (a.letter > b.letter) {
return 1
}
if (a.letter < b.letter) {
return -1
}
return 0
})
let obj = {}
for (let i = 0, len = areas.length; i < len; i++) {
let item = areas[i]
delete item.districts
let letter = item.letter
if (!obj[letter]) {
obj[letter] = []
}
obj[letter].push(item)
}
// 返回一个对象,直接用 wx:for 来遍历对象,index 为 key,item 为 value,item 是一个数组
return obj
},
- 点击城市后,我们使用getCurrentPages()获取页面堆栈,修改首页数据。代码如下:
choose(e) {
let name = e.currentTarget.dataset.name
let pages = getCurrentPages()
let len = pages.length
let indexPage = pages[len - 2]
if (name) {
indexPage.search(name, () => {
wx.navigateBack({})
})
} else {
indexPage.init({}, () => {
wx.navigateBack({})
})
}
},
- 在citychoose.json中添加”navigationBarTitleText”:”选择城市”
- 在citychoose.wxml中添加信息以描述当前页面的结构
① 页面顶部设置搜索框,达到自主输入城市名查询天气的效果
② 给予用户推荐信息,进行城市定位以查询天气
③ 按首字母排序的城市名称
代码如下:
<view class='container'>
<view class="wrapper">
<view class='search'>
<view class="inner">
<image class='icon' src='/img/search_grey.png'></image>
<input value='{{inputText}}' placeholder='请输入城市名,快速查询天气信息' maxlength='20' confirm-type='搜索' bindinput='inputFilter' bindconfirm='inputFilter' bindfocus='inputFilter'></input>
</view>
<text class='cancel' catchtap='cancel'>清空</text>
</view>
</view>
<!-- <view class='top'
wx:if='{{hotCities.length}}'>
<view class='title'>热门城市</view>
<view class='items'>
<view class='item'
hover-class='hover-ddd' catchtap='choose' data-item='{{item}}'
wx:key='{{index}}' wx:for='{{hotCities}}'>{{item.name}}</view>
</view>
</view> -->
<view class='hot'>
<view class='title'>猜你想找</view>
<view class='cities'>
<view class='item active' catchtap='choose'>
<image class='icon' src='/img/location_s_w.png'></image>
<view>定位</view>
</view>
<view class='item' hover-class='active' catchtap='choose' wx:for='{{hotCities}}' wx:key='{{index}}' data-name='{{item.name}}'>{{item.name}}</view>
</view>
</view>
<view class='bottom'>
<view wx:key='{{index}}' wx:for='{{showItems}}'>
<view class='key'>{{index}}</view>
<view class='values'>
<view wx:key='{{index}}' class='value' hover-class='hover' wx:for='{{item}}' catchtap='choose' data-name='{{item.name}}'>{{item.name}}</view>
</view>
</view>
</view>
<view class='empty' wx:if='{{!showItems}}'>暂无城市可以选择</view>
</view>
- 在citychoose.wxss中添加代码用来设置自己喜欢的城市选择页面样式。这里不再赘述。
.container {
min-height: 100vh;
display: flex;
flex-direction: column;
margin-bottom: 20rpx;
}
.wrapper {
font-size: 0;
background: #fff;
padding: 30rpx;
position: relative;
height: 128rpx;
box-sizing: border-box;
}
.wrapper .search {
display: flex;
justify-content: flex-start;
align-items: center;
}
.inner {
background: #f4f6f9;
font-size: 30rpx;
padding: 16rpx 0 16rpx 20rpx;
box-sizing: border-box;
border-radius: 8rpx;
flex: 1;
display: flex;
align-items: center;
}
.inner input {
background: #f4f6f9;
font-size: 30rpx;
height: 38rpx;
/* 覆盖默认样式 min-height */
min-height: 38rpx;
line-height: 38rpx;
width: 100%;
box-sizing: border-box;
}
.icon {
width: 28rpx;
height: 28rpx;
margin-right: 10rpx;
}
.cancel {
font-size: 30rpx;
display: inline-block;
color: #666;
width: 2.5em;
text-align: right;
}
.items {
display: flex;
flex-direction: row;
justify-content: flex-start;
flex-wrap: wrap;
}
.items .item {
border: 1rpx solid rgb(242, 242, 242);
background: #efefef;
border-radius: 10rpx;
padding: 8rpx 40rpx;
margin-right: 30rpx;
margin-bottom: 36rpx;
}
.top .title {
margin-bottom: 30rpx;
}
.top {
padding: 30rpx 96rpx 20rpx 30rpx;}
.top,
.bottom {
font-size: 32rpx;
color: #333;
background: #fff;
}
.hot {
background: #fff;
margin-top: 10rpx;
padding: 30rpx 30rpx 20rpx;
}
.hot .title {
font-size: 32rpx;
}
.hot .cities {
display: flex;
align-items: center;
flex-wrap: wrap;
}
.hot .item {
display: flex;
justify-content: center;
align-items: center;
width: 30%;
height: 60rpx;
background: #f4f6f9;
border-radius: 8rpx;
color: #333;
font-size: 28rpx;
margin-top: 20rpx;
margin-left: 2.5%;
margin-right: 2.5%;
}
.hot .item .icon {
width: 24rpx;
height: 24rpx;
margin-right: 8rpx;
}
.hot .item.active {
background: #40a7e7;
color: #fff;
}
.hot .item:nth-child(3n+1) {
margin-left: 0;
}
.hot .item:nth-child(3n) {
margin-right: 0;
}
.bottom .key {
background: #f4f6f9;
height: 50rpx;
display: flex;
align-items: center;
padding: 0 30rpx;
}
.bottom .values .value {
border-bottom: 1rpx solid #efefef;
height: 104rpx;
display: flex;
align-items: center;
padding: 0 30rpx;
}
.bottom .values .value:last-child {
border-bottom: none;
}
.hover {
background: #f4f6f9;
}
.empty {
margin-top: 100rpx;
font-size: 30rpx;
text-align: center;
color: #666;
}