2025-02-10- JavaScript 系列八:第6課 ── 天氣查詢應用程式-步驟04

2025-02-10- JavaScript 系列八:第6課 ── 天氣查詢應用程式-步驟04


✅ 你要的功能一覽:

  1. RWD 響應式版面
    → 使用 CSS Flexbox + Media Queries 或 Tailwind CSS 實作

  2. 背景隨天氣變化

    • ☀️ 晴天:漸層藍色背景
    • ☁️ 陰天:漸層灰色背景
    • 🌩️ 雷雨:黑色背景 + 閃電動畫
  3. 對應的天氣圖示顯示
    → 可使用 weather-iconsFont Awesome、或你選的 SVG 圖片


🔧 建議的改進步驟

我會先幫你 改寫 WeatherQuery.vue 的背景變化邏輯,並附上基本 RWD 設計。完成後,我們再加上圖示部分(SVG 或 Icon Font)。


🧩 改進版 WeatherQuery.vue(含背景切換與 RWD)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
<script setup>
import { ref, watch, computed } from 'vue'

const cities = ['臺北市', '新北市', '桃園市', '臺中市', '臺南市', '高雄市']
const selectedCity = ref('臺北市')
const weatherInfo = ref(null)

const fetchWeather = async () => {
const apiKey = '你的 API KEY'
const url = `https://opendata.cwa.gov.tw/api/v1/rest/datastore/F-C0032-001?Authorization=${apiKey}&locationName=${selectedCity.value}`

try {
const res = await fetch(url)
const data = await res.json()
const location = data.records.location[0]
const elements = location.weatherElement

weatherInfo.value = {
description: elements[0].time[0].parameter.parameterName,
minTemp: elements[2].time[0].parameter.parameterName,
maxTemp: elements[4].time[0].parameter.parameterName,
rain: elements[1].time[0].parameter.parameterName
}
} catch (error) {
console.error('API 錯誤:', error)
}
}

// 監聽縣市變化
watch(selectedCity, fetchWeather)
fetchWeather()

// 根據天氣現象設定背景類別
const backgroundClass = computed(() => {
if (!weatherInfo.value) return 'bg-default'

const desc = weatherInfo.value.description
if (desc.includes('雷') || desc.includes('雨')) return 'bg-thunder'
if (desc.includes('陰')) return 'bg-cloudy'
if (desc.includes('晴')) return 'bg-sunny'
return 'bg-default'
})
</script>

<template>
<div :class="['weather-container', backgroundClass]">
<div class="weather-card">
<h2>天氣查詢</h2>
<label>
縣市:
<select v-model="selectedCity">
<option v-for="city in cities" :key="city" :value="city">{{ city }}</option>
</select>
</label>

<div v-if="weatherInfo" class="weather-data">
<p>🌦️ 現象:{{ weatherInfo.description }}</p>
<p>🔺 最高溫:{{ weatherInfo.maxTemp }}°C</p>
<p>🔻 最低溫:{{ weatherInfo.minTemp }}°C</p>
<p>🌧️ 降雨率:{{ weatherInfo.rain }}%</p>
</div>
</div>
</div>
</template>

<style scoped>
.weather-container {
min-height: 100vh;
display: flex;
justify-content: center;
align-items: center;
transition: background 0.5s ease-in-out;
padding: 1rem;
}

/* 背景樣式 */
.bg-sunny {
background: linear-gradient(to bottom, #87CEFA, #ffffff);
}
.bg-cloudy {
background: linear-gradient(to bottom, #999, #ccc);
}
.bg-thunder {
background: linear-gradient(to bottom, #111, #444);
animation: flash 2s infinite;
}
.bg-default {
background: #eee;
}

/* 閃電效果 */
@keyframes flash {
0%, 100% { background-color: #111; }
50% { background-color: #222; }
}

.weather-card {
background: white;
padding: 2rem;
border-radius: 1rem;
box-shadow: 0 4px 10px rgba(0, 0, 0, 0.2);
max-width: 400px;
width: 100%;
text-align: center;
}

/* RWD 響應式設計 */
@media (max-width: 600px) {
.weather-card {
padding: 1rem;
}
h2 {
font-size: 1.4rem;
}
}
</style>

✅ 下一步(你選)

  1. 加入天氣圖示: 例如晴天 ☀️、陰天 ☁️、雷雨 🌩️(SVG 或 Icon 套件)
  2. 加入 loading 動畫 / 錯誤提示
  3. 加強卡片動畫或轉場效果
  4. 匯入 Tailwind CSS 做進一步美化