Merge branch 'main' of http://192.168.0.251:3000/localhost/localhost-front
This commit is contained in:
commit
58cbb8f534
BIN
public/img/icons/sunny-custom.png
Normal file
BIN
public/img/icons/sunny-custom.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 20 KiB |
@ -11,9 +11,9 @@
|
|||||||
<div class="d-flex align-items-center weather-box">
|
<div class="d-flex align-items-center weather-box">
|
||||||
<img
|
<img
|
||||||
v-if="weather.icon"
|
v-if="weather.icon"
|
||||||
:src="`https://openweathermap.org/img/wn/${weather.icon}@2x.png`"
|
:src="customIconUrl"
|
||||||
:alt="weather.description"
|
:alt="weather.description"
|
||||||
class="weather-icon"
|
:class="customIconClass"
|
||||||
/>
|
/>
|
||||||
<div class="d-flex flex-column">
|
<div class="d-flex flex-column">
|
||||||
<span class="weather-desc">{{ weather.description }}</span>
|
<span class="weather-desc">{{ weather.description }}</span>
|
||||||
@ -269,6 +269,7 @@
|
|||||||
import { useRouter } from 'vue-router';
|
import { useRouter } from 'vue-router';
|
||||||
import { useThemeStore } from '@s/darkmode';
|
import { useThemeStore } from '@s/darkmode';
|
||||||
import { computed, onMounted, ref, watch } from 'vue';
|
import { computed, onMounted, ref, watch } from 'vue';
|
||||||
|
import axios from '@api';
|
||||||
|
|
||||||
const baseUrl = import.meta.env.VITE_SERVER;
|
const baseUrl = import.meta.env.VITE_SERVER;
|
||||||
|
|
||||||
@ -350,44 +351,59 @@
|
|||||||
tempMax: null,
|
tempMax: null,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const customIconUrl = computed(() => {
|
||||||
|
if (weather.value.icon === "01d" || weather.value.icon === "01n") {
|
||||||
|
return "/img/icons/sunny-custom.png";
|
||||||
|
}
|
||||||
|
return `https://openweathermap.org/img/wn/${weather.value.icon}@2x.png`;
|
||||||
|
});
|
||||||
|
|
||||||
|
const customIconClass = computed(() => {
|
||||||
|
if (weather.value.icon === "01d" || weather.value.icon === "01n") {
|
||||||
|
return "weather-icon custom-sunny-icon";
|
||||||
|
}
|
||||||
|
return "weather-icon";
|
||||||
|
});
|
||||||
|
|
||||||
const weatherKorean = computed(() => weather.value.description || '날씨 정보 없음');
|
const weatherKorean = computed(() => weather.value.description || '날씨 정보 없음');
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
navigator.geolocation.getCurrentPosition(async (position) => {
|
navigator.geolocation.getCurrentPosition(async (position) => {
|
||||||
const lat = position.coords.latitude;
|
const lat = position.coords.latitude;
|
||||||
const lon = position.coords.longitude;
|
const lon = position.coords.longitude;
|
||||||
const apiKey = '3505b3500aacf34c4497bf449996ea09';
|
|
||||||
const url = `https://api.openweathermap.org/data/2.5/forecast?lat=${lat}&lon=${lon}&appid=${apiKey}&units=metric&lang=kr`;
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const res = await fetch(url);
|
const res = await axios.get(`/weather`, {
|
||||||
const data = await res.json();
|
params: { lat, lon },
|
||||||
|
withCredentials: true,
|
||||||
|
});
|
||||||
|
|
||||||
const now = new Date();
|
const raw = res.data;
|
||||||
|
const data = JSON.parse(raw.data);
|
||||||
|
|
||||||
// 가장 가까운 데이터
|
if (!data || !Array.isArray(data.list) || data.list.length === 0) {
|
||||||
const closest = data.list.reduce((prev, curr) => {
|
console.error('날씨 데이터 형식 오류 또는 없음:', data);
|
||||||
const prevTime = new Date(prev.dt_txt).getTime();
|
return;
|
||||||
const currTime = new Date(curr.dt_txt).getTime();
|
}
|
||||||
const nowTime = now.getTime();
|
|
||||||
|
|
||||||
const prevDiff = Math.abs(prevTime - nowTime);
|
const now = new Date();
|
||||||
const currDiff = Math.abs(currTime - nowTime);
|
const closest = data.list.reduce((prev, curr) => {
|
||||||
|
const prevTime = new Date(prev.dt_txt).getTime();
|
||||||
|
const currTime = new Date(curr.dt_txt).getTime();
|
||||||
|
const nowTime = now.getTime();
|
||||||
|
const prevDiff = Math.abs(prevTime - nowTime);
|
||||||
|
const currDiff = Math.abs(currTime - nowTime);
|
||||||
|
return prevDiff < currDiff ? prev : curr;
|
||||||
|
});
|
||||||
|
|
||||||
if (prevDiff < currDiff) return prev;
|
weather.value.icon = closest.weather[0].icon.replace(/n$/, 'd');
|
||||||
if (prevDiff > currDiff) return curr;
|
weather.value.description = closest.weather[0].description;
|
||||||
|
weather.value.tempMin = Math.round(closest.main.temp_min);
|
||||||
return prevTime < currTime ? prev : curr;
|
weather.value.tempMax = Math.round(closest.main.temp_max);
|
||||||
|
} catch (e) {
|
||||||
|
console.error('날씨 정보 가져오기 실패:', e);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
weather.value.icon = closest.weather[0].icon.replace(/n$/, 'd');
|
|
||||||
weather.value.description = closest.weather[0].description;
|
|
||||||
weather.value.tempMin = Math.round(closest.main.temp_min);
|
|
||||||
weather.value.tempMax = Math.round(closest.main.temp_max);
|
|
||||||
} catch (e) {
|
|
||||||
console.error('날씨 정보 가져오기 실패:', e);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
const handleLogout = async () => {
|
const handleLogout = async () => {
|
||||||
@ -408,10 +424,10 @@
|
|||||||
.weather-desc {
|
.weather-desc {
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
line-height: 1.2;
|
line-height: 1.6;
|
||||||
}
|
}
|
||||||
.weather-temp {
|
.weather-temp {
|
||||||
font-size: 12px;
|
font-size: 13px;
|
||||||
color: #888;
|
color: #888;
|
||||||
line-height: 1.2;
|
line-height: 1.2;
|
||||||
}
|
}
|
||||||
@ -423,4 +439,8 @@
|
|||||||
white-space: nowrap;
|
white-space: nowrap;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
.custom-sunny-icon {
|
||||||
|
width: 5% !important;
|
||||||
|
height: 5% !important;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user