本文已参与「新人创作礼」活动,一起开启掘金创作之路。
前言
该组件除了具备展示实时温度、风力、湿度等常用功能外,还借助高德API添加了自动定位的功能,以达成更加便利的用户体验
另,最近想学习一下微信小程序,想看看uni-app,应该怎么学啊 :<
注意!使用时需要在高德地图中申请一个key来完成功能,key的目的应该是为了记录请求次数以在该key请求过多时限流。我已经在下列源码中标注 #在这里填入你申请来的key# ,申请教程在如下链接中
效果图
运行解释
该卡片为一个.vue组件,为了更加轻量没有使用天气预报,而是直接展示当前实时天气,为方便讲解,我以中间分割线为界,将该组件分为:下方展示框,上方查询框
展示框
组件挂载时,若为第一次运行,则将向高德地图申请ip地址并接收返回值中的adcode与城市名,adcode的变动触发watch函数以查询一次天气信息,此次查询到的位置信息将会被上方自动定位使用
若不是第一次运行,则将获取localStorage中的地址信息并发送请求查询天气
在watch中,adcode每一次变动都会触发查询该地天气信息(很重要) ,查询所用的adcode将被存入localStorage以方便在下一次进入时直接查询该地天气
天气图标将会根据左侧天气信息计算应该呈现的图标
查询框
上方查询input框中,敲下回车以触发函数来根据该位置查询该地adcode并存入以触发watch
查询成功时仅更新展示框内容
当查询失败时,将会弹出警告框,以下为查询错误时弹框样式
函数解读
前提:adcode是高德开放平台下的用于记录地理位置的编码,将adcode发往某一接口中可返回所需要的信息
核心函数:众所周知,Vue中的watch将检测所配置上的变量,并在该变量发生变化时及时运行所配置的函数。在watch配置项中的adcode函数将会监视data中的adcode,每一次变化都将发送一次请求到restapi.amap.com/v3/weather/… ,该url接受两个必选参数:city、key并返回一串关于查询结果的json
useIp:当用户点击“使用该地区”时将会调用,将第一次挂载时或localStorage获取到的adcode(已被存入ipAdCode)填入data中的adcode
keyUp:当用户在上方查询框中敲下回车时触发,将会把input框中的内容存入city并触发getCityCode函数(根据city查询adcode的函数)
getIp:直接发送一次请求并返回该地的位置信息
getCityCode:根据城市名查询该地adcode
代码
<template lang="">
<el-card shadow="hover">
<h1>天气</h1>
<el-input v-model="input" placeholder="输入位置并按下回车以查询该地天气" @keyup.enter.native="keyUp"></el-input>
<p class="ipAddress"><i class="el-icon-location-outline"></i>{{ipAddress}} <el-link type="primary"
@click="useIp">使用该地区</el-link>
</p>
<el-divider></el-divider>
<div class="showBlock">
<p class="address">{{address}}</p>
<p class="temperature">{{temperature}}℃<span class="weather">{{weather}} <span><i class="mainWeather"
:class="getIcon"></i></span></span></p>
<div class="other">
<p class="wind"><i class="el-icon-wind-power"></i>
风向:<span>{{winddirection}}</span> <span>风力:{{windpower}}级</span></p>
<p class="humidity"><i class="el-icon-odometer"></i> 湿度:{{humidity}}</p>
<p id="reporttime">消息发布时间:{{reporttime}}</p>
</div>
</div>
</el-card>
</template>
<script>
export default {
name: 'Weather',
data() {
return {
input: '',
city: '',
adcode: '',
address: '',
ipAddress: '',
ipAdCode: '',
weather: '',
temperature: '',
winddirection: '',
windpower: '',
humidity: '',
reporttime: '',
icon: true
}
},
watch: {
adcode() { //当adcode发生变化时,重新请求该地天气
this.$axios.get('https://restapi.amap.com/v3/weather/weatherInfo?parameters', {
params: {
key: '#在这里填入你申请来的key#', //需要操作
city: this.adcode,
extensions: 'base'
}
}).then(
response => {
let lives = response.data.lives[0]
this.weather = lives.weather
this.temperature = lives.temperature
this.winddirection = lives.winddirection
this.windpower = lives.windpower
this.humidity = lives.humidity
this.reporttime = lives.reporttime
this.address = lives.city
localStorage.setItem('adcode', this.adcode) //将存储目前查询的天气
},
error => {
this.$notify.info({
title: '未知错误',
message: error.message
});
}
)
},
},
computed: {
getIcon() {
this.icon = false
if (this.weather == '晴') {
return 'el-icon-sunny'
} else if (this.weather == '多云') {
return 'el-icon-cloudy-and-sunny'
} else if (this.weather == '阴') {
return 'el-icon-partly-cloudy'
} else if (this.weather.indexOf('雨')) {
return 'el-icon-heavy-rain'
} else if (this.weather.indexOf('雪')) {
return 'el-icon-light-rain'
}
this.icon = true
}
},
methods: {
useIp() {
this.adcode = this.ipAdCode
},
keyUp() {
this.city = this.input
this.input = ''
this.getCityCode()
},
getIp() { //挂载时执行,获取ip地址
this.$axios.get('https://restapi.amap.com/v3/ip?parameters', {
params: {
key: '#在这里填入你申请来的key#' //需要操作
}
}).then(
response => {
this.ipAddress = `${response.data.province}${response.data.city}`
this.ipAdCode = response.data.adcode
if (!(localStorage.getItem('adcode'))) {
this.adcode = response.data.adcode
}
}
)
},
getCityCode() { //查询城市的adcode
this.$axios.get('https://restapi.amap.com/v3/geocode/geo?parameters', {
params: {
key: '#在这里填入你申请来的key#', //需要操作
address: this.city,
}
}).then(
response => {
if(response.data.status == '1'){
console.log(response);
this.adcode = response.data.geocodes[0].adcode
}
else if (response.data.status == '0') {
this.$notify.error({
title: '查询错误',
message: '请重新核对查询地址'
});
}
}
)
}
},
mounted() {
if (localStorage.getItem('adcode')) { //取出本地存储的地址,若不存在,则使用ip地址
this.adcode = localStorage.getItem('adcode')
}
this.getIp()
},
}
</script>
<style scoped>
.ipAddress {
margin-top: 10px;
}
.el-card {
background-color: rgba(255, 215, 55, 0.8);
height: 409px;
color: #000;
}
h1 {
margin: 0px 0px 10px 10px;
}
.showBlock {
margin-top: 10px;
}
.temperature {
font-size: 50px;
}
.weather {
margin-left: 20px;
font-size: 35px;
}
.address {
font-size: 20px;
}
.other {
margin-top: 10px;
}
.other p {
margin-top: 10px;
font-size: 18px;
}
#reporttime {
margin-top: 10px;
font-size: 14px;
}
.mainWeather {
float: right;
margin-top: 10px;
margin-right: 10%;
font-size: 120px;
}
.showBlock {
margin-left: 10px;
}
</style>