feat(music): 添加音乐状态获取功能并优化音乐列表展示
- 新增 getMusicStatus API 接口,用于获取音乐的收藏和点赞状态 - 在音乐列表、歌单详情、搜索结果等页面中集成音乐状态获取功能 - 优化音乐播放器,主动获取并更新音乐状态 - 为每首歌曲添加收藏和点赞状态字段
This commit is contained in:
@@ -2,12 +2,14 @@
|
||||
import { ref, onMounted } from 'vue'
|
||||
import { useRouter } from 'vue-router'
|
||||
import { Search } from '@element-plus/icons-vue'
|
||||
import { getMusicList, getHotMusic, getLatestMusic, processMusicUrl } from '../api/music'
|
||||
import { getMusicList, getHotMusic, getLatestMusic, processMusicUrl, getMusicStatus } from '../api/music'
|
||||
import { getMusicTypeList } from '../api/musicType'
|
||||
import MusicList from '../components/MusicList.vue'
|
||||
import { ElMessage } from 'element-plus'
|
||||
import { useUserStore } from '../stores/user'
|
||||
|
||||
const router = useRouter()
|
||||
const userStore = useUserStore()
|
||||
|
||||
// 音乐列表数据
|
||||
const musicList = ref([])
|
||||
@@ -43,13 +45,8 @@ const fetchMusicList = async (params = {}) => {
|
||||
|
||||
console.log('音乐列表数据:', res.data)
|
||||
|
||||
// 处理收藏状态
|
||||
// 确保音乐URL和封面URL正确处理
|
||||
musicList.value.forEach(music => {
|
||||
if (music.collected === undefined) {
|
||||
music.collected = false
|
||||
}
|
||||
|
||||
// 确保音乐URL和封面URL正确处理
|
||||
if (music.url) {
|
||||
music.url = processMusicUrl(music.url)
|
||||
}
|
||||
@@ -57,6 +54,9 @@ const fetchMusicList = async (params = {}) => {
|
||||
music.cover = processMusicUrl(music.cover)
|
||||
}
|
||||
})
|
||||
|
||||
// 更新音乐状态
|
||||
updateMusicStatuses(musicList.value)
|
||||
} else {
|
||||
ElMessage.error(res.message || '获取音乐列表失败')
|
||||
}
|
||||
@@ -98,6 +98,27 @@ const handleCollectChange = (music) => {
|
||||
console.log('收藏状态变化:', music)
|
||||
}
|
||||
|
||||
// 更新音乐状态
|
||||
const updateMusicStatuses = async (list) => {
|
||||
if (!userStore.isLoggedIn || !list || list.length === 0) {
|
||||
return
|
||||
}
|
||||
|
||||
// 为列表中的每首歌曲获取状态
|
||||
const promises = list.map(music => getMusicStatus(music.id))
|
||||
try {
|
||||
const results = await Promise.all(promises)
|
||||
results.forEach((res, index) => {
|
||||
if (res.code === 200 && res.data) {
|
||||
list[index].collected = res.data.collected
|
||||
list[index].liked = res.data.liked
|
||||
}
|
||||
})
|
||||
} catch (error) {
|
||||
console.error('批量获取音乐状态失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// 获取热门音乐
|
||||
const fetchHotMusic = async (params = {}) => {
|
||||
loadingHot.value = true
|
||||
@@ -108,13 +129,15 @@ const fetchHotMusic = async (params = {}) => {
|
||||
const allHotMusic = res.data || []
|
||||
total.value = allHotMusic.length // 总数是50
|
||||
|
||||
// 处理URL和收藏状态
|
||||
// 处理URL
|
||||
allHotMusic.forEach(music => {
|
||||
if (music.url) music.url = processMusicUrl(music.url)
|
||||
if (music.cover) music.cover = processMusicUrl(music.cover)
|
||||
if (music.collected === undefined) music.collected = false
|
||||
})
|
||||
|
||||
// 更新状态
|
||||
updateMusicStatuses(allHotMusic)
|
||||
|
||||
// 根据当前页码和每页数量进行前端分页
|
||||
const page = params.page || currentPage.value
|
||||
const size = params.size || pageSize.value
|
||||
@@ -149,10 +172,10 @@ const fetchLatestMusic = async () => {
|
||||
if (music.cover) {
|
||||
music.cover = processMusicUrl(music.cover)
|
||||
}
|
||||
if (music.collected === undefined) {
|
||||
music.collected = false
|
||||
}
|
||||
})
|
||||
|
||||
// 更新状态
|
||||
updateMusicStatuses(latestMusicList.value)
|
||||
} else {
|
||||
ElMessage.error(res.message || '获取最新音乐失败')
|
||||
}
|
||||
|
||||
@@ -78,7 +78,7 @@
|
||||
@click="toggleLike"
|
||||
>
|
||||
<el-icon><component :is="music.liked ? 'Check' : 'Pointer'" /></el-icon>
|
||||
{{ music.liked ? '已点赞' : '点赞' }} ({{ music.likeCount || 0 }})
|
||||
{{ music.liked ? '已点赞' : '点赞' }}
|
||||
</el-button>
|
||||
|
||||
<el-button
|
||||
@@ -202,7 +202,7 @@ import { ref, computed, onMounted, watch, onUnmounted } from 'vue'
|
||||
import { useRoute, useRouter } from 'vue-router'
|
||||
import { usePlayerStore } from '../stores/player'
|
||||
import { useUserStore } from '../stores/user'
|
||||
import { getMusicById, toggleCollectMusic, getHotMusic, toggleLikeMusic } from '../api/music'
|
||||
import { getMusicById, toggleCollectMusic, getHotMusic, toggleLikeMusic, getMusicStatus } from '../api/music'
|
||||
import { getCommentList, addComment, deleteComment as apiDeleteComment } from '../api/comment'
|
||||
import { connect, subscribe, unsubscribe, disconnect } from '../utils/websocket'
|
||||
import { ElMessage, ElMessageBox } from 'element-plus'
|
||||
@@ -246,6 +246,8 @@ const fetchMusicDetail = async () => {
|
||||
if (res.code === 200) {
|
||||
if (res.data) {
|
||||
music.value = res.data
|
||||
// 获取音乐状态
|
||||
fetchMusicStatus()
|
||||
} else {
|
||||
// 如果音乐不存在,显示提示并返回音乐列表页
|
||||
ElMessage.warning('音乐不存在或已被删除')
|
||||
@@ -264,6 +266,22 @@ const fetchMusicDetail = async () => {
|
||||
}
|
||||
}
|
||||
|
||||
// 获取音乐状态
|
||||
const fetchMusicStatus = async () => {
|
||||
if (!music.value || !userStore.isLoggedIn) {
|
||||
return
|
||||
}
|
||||
try {
|
||||
const res = await getMusicStatus(music.value.id)
|
||||
if (res.code === 200 && res.data) {
|
||||
music.value.collected = res.data.collected
|
||||
music.value.liked = res.data.liked
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('获取音乐状态失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// 获取相关音乐
|
||||
const fetchRelatedMusic = async () => {
|
||||
try {
|
||||
|
||||
@@ -5,6 +5,7 @@ import { usePlayerStore } from '../stores/player'
|
||||
import { useUserStore } from '../stores/user'
|
||||
import { ElMessage, ElMessageBox } from 'element-plus'
|
||||
import { getPlaylistById, toggleCollectPlaylist, deletePlaylist as apiDeletePlaylist } from '../api/playlist'
|
||||
import { getMusicStatus } from '../api/music'
|
||||
import { getCommentList, addComment, deleteComment as apiDeleteComment } from '../api/comment'
|
||||
import { connect, subscribe, unsubscribe, disconnect } from '../utils/websocket' // 导入 WebSocket 工具
|
||||
import { processImageUrl } from '../utils/imageUtils'
|
||||
@@ -67,6 +68,9 @@ const fetchPlaylistDetail = async () => {
|
||||
|
||||
// 获取收藏状态
|
||||
isCollected.value = playlist.value.collected === true
|
||||
|
||||
// 更新歌单内歌曲的状态
|
||||
updateMusicStatuses(playlist.value.songs)
|
||||
} else {
|
||||
ElMessage.error(res.message || '获取歌单详情失败')
|
||||
}
|
||||
@@ -202,6 +206,27 @@ const cancelReply = () => {
|
||||
replyContent.value = ''
|
||||
}
|
||||
|
||||
// 更新音乐状态
|
||||
const updateMusicStatuses = async (list) => {
|
||||
if (!userStore.isLoggedIn || !list || list.length === 0) {
|
||||
return
|
||||
}
|
||||
|
||||
// 为列表中的每首歌曲获取状态
|
||||
const promises = list.map(music => getMusicStatus(music.id))
|
||||
try {
|
||||
const results = await Promise.all(promises)
|
||||
results.forEach((res, index) => {
|
||||
if (res.code === 200 && res.data) {
|
||||
list[index].collected = res.data.collected
|
||||
list[index].liked = res.data.liked
|
||||
}
|
||||
})
|
||||
} catch (error) {
|
||||
console.error('批量获取音乐状态失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// 提交评论
|
||||
const submitComment = async (isReply = false) => {
|
||||
if (!userStore.isLoggedIn) {
|
||||
|
||||
@@ -153,7 +153,7 @@ import { useRoute, useRouter } from 'vue-router'
|
||||
import { useUserStore } from '../stores/user'
|
||||
import { ElMessage } from 'element-plus'
|
||||
import { Search } from '@element-plus/icons-vue'
|
||||
import { searchMusic, toggleCollectMusic } from '../api/music'
|
||||
import { searchMusic, toggleCollectMusic, getMusicStatus } from '../api/music'
|
||||
import { searchPlaylist, toggleCollectPlaylist } from '../api/playlist'
|
||||
import { searchSinger, toggleCollectSinger } from '../api/singer'
|
||||
import { processImageUrl } from '../utils/imageUtils'
|
||||
@@ -222,6 +222,9 @@ const fetchMusicList = async () => {
|
||||
cover: processMusicUrl(item.cover),
|
||||
url: processMusicUrl(item.url)
|
||||
}))
|
||||
|
||||
// 更新音乐状态
|
||||
updateMusicStatuses(musicList.value)
|
||||
} else {
|
||||
ElMessage.error(res.message || '搜索音乐失败')
|
||||
}
|
||||
@@ -448,6 +451,27 @@ const formatFans = (count) => {
|
||||
}
|
||||
}
|
||||
|
||||
// 更新音乐状态
|
||||
const updateMusicStatuses = async (list) => {
|
||||
if (!userStore.isLoggedIn || !list || list.length === 0) {
|
||||
return
|
||||
}
|
||||
|
||||
// 为列表中的每首歌曲获取状态
|
||||
const promises = list.map(music => getMusicStatus(music.id))
|
||||
try {
|
||||
const results = await Promise.all(promises)
|
||||
results.forEach((res, index) => {
|
||||
if (res.code === 200 && res.data) {
|
||||
list[index].collected = res.data.collected
|
||||
list[index].liked = res.data.liked
|
||||
}
|
||||
})
|
||||
} catch (error) {
|
||||
console.error('批量获取音乐状态失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// 监听关键词变化
|
||||
watch(() => route.query.keyword, (newKeyword) => {
|
||||
searchKeyword.value = newKeyword
|
||||
|
||||
@@ -7,7 +7,7 @@ import { ElMessage, ElMessageBox } from 'element-plus'
|
||||
import { getSingerById, toggleCollectSinger } from '../api/singer'
|
||||
import { getCommentList, addComment, deleteComment as apiDeleteComment } from '../api/comment'
|
||||
import { processImageUrl } from '../utils/imageUtils'
|
||||
import { processMusicUrl, getMusicBySinger } from '../api/music'
|
||||
import { processMusicUrl, getMusicBySinger, getMusicStatus } from '../api/music'
|
||||
import { connect, subscribe, unsubscribe, disconnect } from '../utils/websocket' // 导入 WebSocket 工具
|
||||
|
||||
const route = useRoute()
|
||||
@@ -92,6 +92,9 @@ const fetchSingerMusic = async () => {
|
||||
cover: processMusicUrl(song.cover),
|
||||
url: processMusicUrl(song.url)
|
||||
}))
|
||||
|
||||
// 更新歌曲状态
|
||||
updateMusicStatuses(songs.value)
|
||||
} else {
|
||||
ElMessage.error(res.message || '获取歌手音乐失败')
|
||||
}
|
||||
@@ -221,6 +224,27 @@ const cancelReply = () => {
|
||||
replyContent.value = ''
|
||||
}
|
||||
|
||||
// 更新音乐状态
|
||||
const updateMusicStatuses = async (list) => {
|
||||
if (!userStore.isLoggedIn || !list || list.length === 0) {
|
||||
return
|
||||
}
|
||||
|
||||
// 为列表中的每首歌曲获取状态
|
||||
const promises = list.map(music => getMusicStatus(music.id))
|
||||
try {
|
||||
const results = await Promise.all(promises)
|
||||
results.forEach((res, index) => {
|
||||
if (res.code === 200 && res.data) {
|
||||
list[index].collected = res.data.collected
|
||||
list[index].liked = res.data.liked
|
||||
}
|
||||
})
|
||||
} catch (error) {
|
||||
console.error('批量获取音乐状态失败:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// 提交评论
|
||||
const submitComment = async (isReply = false) => {
|
||||
if (!userStore.isLoggedIn) {
|
||||
|
||||
Reference in New Issue
Block a user