릴리스: v0.1.45 토스트와 즐겨찾기 상호작용 보정

This commit is contained in:
2026-03-27 10:46:29 +09:00
parent 7de5e96c4c
commit 282e89b738
8 changed files with 79 additions and 44 deletions

View File

@@ -1,5 +1,5 @@
<script setup>
import { onMounted, ref } from 'vue'
import { computed, onMounted, ref } from 'vue'
import { useRouter } from 'vue-router'
import { api } from '../lib/api'
import { toApiUrl } from '../lib/runtime'
@@ -11,6 +11,9 @@ const toast = useToast()
const favorites = ref([])
const query = ref('')
const sort = ref('favorited')
const sortLabel = computed(() =>
sort.value === 'favorited' ? '즐겨찾기한 날짜' : sort.value === 'updated' ? '최종 업데이트' : '즐겨찾기 수'
)
function fmt(ts) {
return new Date(ts).toLocaleString(undefined, {
@@ -52,16 +55,6 @@ function openTierList(tierList) {
router.push(`/editor/${tierList.gameId}/${tierList.id}`)
}
async function unfavorite(tierList) {
try {
await api.unfavoriteTierList(tierList.id)
favorites.value = favorites.value.filter((entry) => entry.id !== tierList.id)
toast.success('즐겨찾기를 해제했어요.')
} catch (e) {
toast.error('즐겨찾기 해제에 실패했어요.')
}
}
onMounted(loadFavorites)
</script>
@@ -103,9 +96,9 @@ onMounted(loadFavorites)
<div class="row__foot">
<div class="row__meta">
<div>{{ tierList.gameName || tierList.gameId }}</div>
<div>{{ fmt(sort === 'favorited' ? tierList.favoritedAt : tierList.updatedAt) }}</div>
<div>{{ sortLabel }}: {{ fmt(sort === 'favorited' ? tierList.favoritedAt : tierList.updatedAt) }}</div>
</div>
<button class="favoriteBtn" @click="unfavorite(tierList)"> {{ tierList.favoriteCount || 0 }}</button>
<div class="favoriteStat"> {{ tierList.favoriteCount || 0 }}</div>
</div>
</article>
</div>
@@ -239,13 +232,12 @@ onMounted(loadFavorites)
opacity: 0.78;
font-size: 13px;
}
.favoriteBtn {
.favoriteStat {
border: 1px solid rgba(255, 255, 255, 0.12);
background: rgba(255, 255, 255, 0.05);
color: rgba(255, 255, 255, 0.92);
border-radius: 999px;
padding: 7px 10px;
cursor: pointer;
font-weight: 800;
}
@media (max-width: 1100px) {

View File

@@ -4,12 +4,10 @@ import { useRoute, useRouter } from 'vue-router'
import { api } from '../lib/api'
import { toApiUrl } from '../lib/runtime'
import { useAuthStore } from '../stores/auth'
import { useToast } from '../composables/useToast'
const route = useRoute()
const router = useRouter()
const auth = useAuthStore()
const toast = useToast()
const gameId = computed(() => route.params.gameId)
@@ -73,21 +71,6 @@ function openTierList(id) {
router.push(`/editor/${gameId.value}/${id}`)
}
async function toggleFavorite(tierList) {
if (!auth.user) {
router.push(`/login?redirect=/games/${gameId.value}`)
return
}
try {
const data = tierList.isFavorited ? await api.unfavoriteTierList(tierList.id) : await api.favoriteTierList(tierList.id)
tierLists.value = tierLists.value.map((entry) => (entry.id === tierList.id ? { ...entry, ...data.tierList } : entry))
toast.success(tierList.isFavorited ? '즐겨찾기를 해제했어요.' : '즐겨찾기에 추가했어요.')
} catch (e) {
toast.error('즐겨찾기 처리에 실패했어요.')
}
}
function submitSearch() {
loadTierLists()
}
@@ -133,9 +116,9 @@ function submitSearch() {
</button>
<div class="row__foot">
<div class="row__meta">{{ fmt(t.updatedAt) }}</div>
<button class="favoriteBtn" @click="toggleFavorite(t)">
<div class="favoriteStat" :title="t.isFavorited ? '이미 즐겨찾기한 티어표' : '즐겨찾기 수'">
{{ t.isFavorited ? '★' : '☆' }} {{ t.favoriteCount || 0 }}
</button>
</div>
</div>
</article>
</div>
@@ -319,18 +302,14 @@ function submitSearch() {
justify-content: space-between;
margin-top: auto;
}
.favoriteBtn {
.favoriteStat {
border: 1px solid rgba(255, 255, 255, 0.12);
background: rgba(255, 255, 255, 0.05);
color: rgba(255, 255, 255, 0.92);
border-radius: 999px;
padding: 7px 10px;
cursor: pointer;
font-weight: 800;
}
.favoriteBtn:hover {
background: rgba(255, 255, 255, 0.09);
}
@media (max-width: 1100px) {
.list {
grid-template-columns: repeat(2, minmax(0, 1fr));