前端Vue项目:旅游App-(11)city:添加热门数据动态修改索引栏点击跳转显示城市
Posted karshey
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了前端Vue项目:旅游App-(11)city:添加热门数据动态修改索引栏点击跳转显示城市相关的知识,希望对你有一定的参考价值。
文章目录
目标
上一篇以indexBar的形式显示了数据:【前端】Vue项目:旅游App-(10)city:以indexBar的形式显示数据
本篇目标:
点击城市:
跳转的city页面:
把点击的城市显示在首页:
注意,city页面添加了热门城市,并修改其索引。
过程与代码
添加热门数据
效果:
数据详情:是hotCities中的每一个元素。
数据包含Id、name等:
代码:
<!-- 热门 -->
<van-index-anchor index="热门" />
<div class="hot">
<template v-for="(item,index) in currentGroup?.hotCities" :key="index">
<div class="hotItem">
item.cityName
</div>
</template>
</div>
效果:以国内数据为例。
热门数据样式
.hot
display: flex;
// 允许换行
flex-wrap: wrap;
padding: 18px 0;
margin-right: 20px;
.hotItem
height: 28px;
width: 60px;
line-height: 28px;
text-align: center;
background-color: #fff4ec;
border-radius: 15px;
margin: 8px 5px;
font-size: 13px;
效果:这样也挺好看的。不求跟之前那个一样(之前那个也是随便写的)
索引栏索引
关于索引栏的索引,有几个问题:
- 热门要添加对应的索引,否则会串,对应到A
- 默认的索引是A-Z,但可能不存在某些字母开头的城市,如V
- 索引的值应当是数据中的Group的值
文档索引indexList:
实际需要的索引数值:
html:
<van-index-bar :index-list="indexList">
js:
import computed from 'vue';
// 定义数据currentGroup:一个对象
const props = defineProps(
currentGroup:
type: Object,
default: () => ()
)
const indexList = computed(() =>
// cities是一个数组
const list = props.currentGroup.cities.map(item => item.group)
list.unshift('#')
return list
)
效果:索引对应正确。
监听点击、保存数据、回退
先试试能不能在组件中监听点击事件。若尝试后发现可以,我们就直接这么写;若不行,则使用组件提供的相关事件。
这里可以。
如何将点击的数据传到首页呢?答案是:store。
在store/modules/city的state中添加对象currentCity,用来表示当前点击的数据:要设置默认值,否则第一次城市显示为空
state: () =>
return
allCity: ,
currentCity:
// 默认值
cityName:'广州',
点击事件时修改currentCity:可以直接赋值item,而不是item.cityName。
因为在服务器中一般用id来代表数据,而页面又可能需要显示除了id之外的数据,所以我们赋值整个对象。
还要写回退。
点击事件cityClick
:
const cityStore=useCityStore()
const route=useRouter()
function cityClick(item)
cityStore.currentCity=item
// 回退
route.back()
首页跳转到city页、显示城市
跳转:router-link to
代码:
<div class="city">
<router-link to="/city"> cityStore.currentCity.cityName </router-link>
</div>
效果
总代码
修改的文件
city.js
state添加currentCity。
// city.vue页面所有的进行网络请求和数据都封装到这里
import getAllCity from "@/service";
import defineStore from "pinia";
const useCityStore = defineStore('city',
state: () =>
return
allCity: ,
currentCity:
// 默认值
cityName:'广州',
,
actions:
// 调用网络请求
async fetchAllCity()
const res = await getAllCity()
this.allCity = res.data
)
export default useCityStore
currentGroupCity.vue
添加热门,修改索引,新增点击事件:点击城市、保存数据、回退。
<template>
<van-index-bar :index-list="indexList">
<!-- 热门 -->
<van-index-anchor index="热门" />
<div class="hot">
<template v-for="(item, index) in currentGroup?.hotCities" :key="index">
<div class="hotItem" @click="cityClick(item)">
item.cityName
</div>
</template>
</div>
<template v-for="(item, index) in currentGroup?.cities" :key="index">
<van-index-anchor :index="item.group" />
<template v-for="(itemm, indexx) in item.cities" :key="indexx">
<van-cell :title="itemm.cityName" @click="cityClick(itemm)" />
</template>
</template>
</van-index-bar>
</template>
<script setup>
import computed from 'vue';
import useCityStore from '@/store/modules/city'
import useRouter from 'vue-router';
// 定义数据currentGroup:一个对象
const props = defineProps(
currentGroup:
type: Object,
default: () => ()
)
const indexList = computed(() =>
// cities是一个数组
const list = props.currentGroup.cities.map(item => item.group)
list.unshift('#')
return list
)
const cityStore=useCityStore()
const route=useRouter()
function cityClick(item)
cityStore.currentCity=item
// 回退
route.back()
</script>
<style lang="less" scoped>
.hot
display: flex;
// 允许换行
flex-wrap: wrap;
padding: 18px 0;
margin-right: 20px;
.hotItem
height: 28px;
width: 60px;
line-height: 28px;
text-align: center;
background-color: #fff4ec;
border-radius: 15px;
margin: 8px 5px;
font-size: 13px;
</style>
home.vue
点击跳转到city页,显示选中的城市。
<template>
<div class="home">
<div class="nav-bar">
<div class="title">旅游App</div>
<div class="banner">
<img src="@/assets/img/home/banner.webp" alt="">
</div>
<div class="location">
<div class="city">
<router-link to="/city"> cityStore.currentCity.cityName </router-link>
</div>
<div class="position">
<div class="text">我的位置</div>
<img src="@/assets/img/home/icon_location.png" alt="">
</div>
</div>
</div>
</div>
</template>
<script setup>
import useCityStore from '../../store/modules/city';
const cityStore = useCityStore()
</script>
<style lang="less" scoped>
.home
.nav-bar
.title
height: 46px;
// flex居中,以后左右有东西可以直接加
display: flex;
align-items: center;
justify-content: center;
color: var(--primary-color);
font-size: 16px;
font-weight: 700;
.banner
// 图片本身大很多,让它大小刚好
img
width: 100%;
.location
height: 44px;
display: flex;
align-items: center;
padding: 0 20px;
color: #53565c;
.city
// flex:1 === flex:1 1 auto 除了position之外的剩余部分都属于city
flex: 1;
.position
width: 74px;
display: flex;
align-items: center;
.text
font-size: 12px;
img
width: 20px;
margin-left: 5px;
</style>
以上是关于前端Vue项目:旅游App-(11)city:添加热门数据动态修改索引栏点击跳转显示城市的主要内容,如果未能解决你的问题,请参考以下文章
前端Vue项目:旅游App-(10)city:以indexBar的形式显示数据
前端Vue项目:旅游App-city:固定tab栏内容中显示数据
前端Vue项目:旅游App-city:隐藏TabBar的2种方法
前端Vue项目:旅游App-city:搜索框search和标签页Tabs
前端Vue项目:旅游App-city:标签页Tabs动态数据:网络请求axios与request数据管理store与pinia各种封装