新增下载的歌曲按列表名分组的功能(#2145)
This commit is contained in:
@@ -23,6 +23,10 @@ export default {
|
||||
type: [Object, null],
|
||||
required: true,
|
||||
},
|
||||
listId: {
|
||||
type: String,
|
||||
default: '',
|
||||
},
|
||||
bgClose: {
|
||||
type: Boolean,
|
||||
default: true,
|
||||
@@ -51,7 +55,7 @@ export default {
|
||||
},
|
||||
methods: {
|
||||
handleClick(quality) {
|
||||
void createDownloadTasks([this.musicInfo], quality)
|
||||
void createDownloadTasks([this.musicInfo], quality, this.listId)
|
||||
this.handleClose()
|
||||
},
|
||||
handleClose() {
|
||||
|
||||
@@ -23,6 +23,10 @@ export default {
|
||||
type: Boolean,
|
||||
default: true,
|
||||
},
|
||||
listId: {
|
||||
type: String,
|
||||
default: '',
|
||||
},
|
||||
list: {
|
||||
type: Array,
|
||||
default() {
|
||||
@@ -37,7 +41,7 @@ export default {
|
||||
emits: ['update:show', 'confirm'],
|
||||
methods: {
|
||||
handleClick(quality) {
|
||||
void createDownloadTasks(this.list.filter(item => item.source != 'local'), quality)
|
||||
void createDownloadTasks(this.list.filter(item => item.source != 'local'), quality, this.listId)
|
||||
this.handleClose()
|
||||
this.$emit('confirm')
|
||||
},
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import { appSetting } from '@renderer/store/setting'
|
||||
import { getDownloadFilePath } from '@renderer/utils/music'
|
||||
|
||||
import {
|
||||
@@ -7,6 +6,7 @@ import {
|
||||
getLyricInfo as getOnlineLyricInfo,
|
||||
} from './online'
|
||||
import { buildLyricInfo, getCachedLyricInfo } from './utils'
|
||||
import { buildSavePath } from '@renderer/store/download/utils'
|
||||
|
||||
export const getMusicUrl = async({ musicInfo, isRefresh, allowToggleSource = true, onToggleSource = () => {} }: {
|
||||
musicInfo: LX.Download.ListItem
|
||||
@@ -15,7 +15,7 @@ export const getMusicUrl = async({ musicInfo, isRefresh, allowToggleSource = tru
|
||||
allowToggleSource?: boolean
|
||||
}): Promise<string> => {
|
||||
if (!isRefresh) {
|
||||
const path = await getDownloadFilePath(musicInfo, appSetting['download.savePath'])
|
||||
const path = await getDownloadFilePath(musicInfo, buildSavePath(musicInfo))
|
||||
if (path) return path
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ export const getPicUrl = async({ musicInfo, isRefresh, listId, onToggleSource =
|
||||
onToggleSource?: (musicInfo?: LX.Music.MusicInfoOnline) => void
|
||||
}): Promise<string> => {
|
||||
if (!isRefresh) {
|
||||
const path = await getDownloadFilePath(musicInfo, appSetting['download.savePath'])
|
||||
const path = await getDownloadFilePath(musicInfo, buildSavePath(musicInfo))
|
||||
if (path) {
|
||||
const pic = await window.lx.worker.main.getMusicFilePic(path)
|
||||
if (pic) return pic
|
||||
@@ -62,7 +62,7 @@ export const getLyricInfo = async({ musicInfo, isRefresh, onToggleSource = () =>
|
||||
onToggleSource,
|
||||
}).catch(async() => {
|
||||
// 尝试读取文件内歌词
|
||||
const path = await getDownloadFilePath(musicInfo, appSetting['download.savePath'])
|
||||
const path = await getDownloadFilePath(musicInfo, buildSavePath(musicInfo))
|
||||
if (path) {
|
||||
const rawlrcInfo = await window.lx.worker.main.getMusicFileLyric(path)
|
||||
if (rawlrcInfo) return buildLyricInfo(rawlrcInfo)
|
||||
|
||||
@@ -29,7 +29,7 @@ export const filterList = async({ playedList, listId, list, playerMusicInfo, isN
|
||||
listId,
|
||||
list: list.map(m => toRaw(m)),
|
||||
playedList: toRaw(playedList),
|
||||
savePath: appSetting['download.savePath'],
|
||||
// savePath: appSetting['download.savePath'],
|
||||
playerMusicInfo: toRaw(playerMusicInfo),
|
||||
dislikeInfo: { names: toRaw(dislikeInfo.names), musicNames: toRaw(dislikeInfo.musicNames), singerNames: toRaw(dislikeInfo.singerNames) },
|
||||
isNext,
|
||||
|
||||
@@ -16,6 +16,7 @@ import { proxyCallback } from '@renderer/worker/utils'
|
||||
import { arrPush, arrUnshift, joinPath } from '@renderer/utils'
|
||||
import { DOWNLOAD_STATUS } from '@common/constants'
|
||||
import { proxy } from '../index'
|
||||
import { buildSavePath } from './utils'
|
||||
|
||||
const waitingUpdateTasks = new Map<string, LX.Download.ListItem>()
|
||||
let timer: NodeJS.Timeout | null = null
|
||||
@@ -271,12 +272,13 @@ const handleStartTask = async(downloadInfo: LX.Download.ListItem) => {
|
||||
if (downloadInfo.status != DOWNLOAD_STATUS.RUN) return
|
||||
}
|
||||
|
||||
const filePath = joinPath(appSetting['download.savePath'], downloadInfo.metadata.fileName)
|
||||
const savePath = buildSavePath(downloadInfo)
|
||||
const filePath = joinPath(savePath, downloadInfo.metadata.fileName)
|
||||
if (downloadInfo.metadata.filePath != filePath) updateFilePath(downloadInfo, filePath)
|
||||
|
||||
setStatusText(downloadInfo, window.i18n.t('download_status_start'))
|
||||
|
||||
await window.lx.worker.download.startTask(toRaw(downloadInfo), appSetting['download.savePath'], appSetting['download.skipExistFile'], proxyCallback((event: LX.Download.DownloadTaskActions) => {
|
||||
await window.lx.worker.download.startTask(toRaw(downloadInfo), savePath, appSetting['download.skipExistFile'], proxyCallback((event: LX.Download.DownloadTaskActions) => {
|
||||
// console.log(event)
|
||||
switch (event.action) {
|
||||
case 'start':
|
||||
@@ -357,12 +359,11 @@ const filterTask = (list: LX.Download.ListItem[]) => {
|
||||
* @param list 要下载的歌曲
|
||||
* @param quality 下载音质
|
||||
*/
|
||||
export const createDownloadTasks = async(list: LX.Music.MusicInfoOnline[], quality: LX.Quality) => {
|
||||
export const createDownloadTasks = async(list: LX.Music.MusicInfoOnline[], quality: LX.Quality, listId?: string) => {
|
||||
if (!list.length) return
|
||||
const tasks = filterTask(await window.lx.worker.download.createDownloadTasks(list, quality,
|
||||
appSetting['download.savePath'],
|
||||
appSetting['download.fileName'],
|
||||
toRaw(qualityList.value)),
|
||||
toRaw(qualityList.value), listId),
|
||||
)
|
||||
|
||||
if (tasks.length) await addTasks(tasks)
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
import { appSetting } from '@renderer/store/setting'
|
||||
import { defaultList, loveList, userLists } from '@renderer/store/list/listManage'
|
||||
import { filterFileName } from '@common/utils/common'
|
||||
import { clipFileNameLength } from '@common/utils/tools'
|
||||
import { joinPath } from '@common/utils/nodejs'
|
||||
|
||||
export const buildSavePath = (musicInfo: LX.Download.ListItem) => {
|
||||
let savePath = appSetting['download.savePath']
|
||||
if (appSetting['download.isSavePathGroupByListName']) {
|
||||
let dirName: string | undefined
|
||||
const listId = musicInfo.metadata.listId
|
||||
switch (listId) {
|
||||
case defaultList.id:
|
||||
dirName = window.i18n.t(defaultList.name)
|
||||
break
|
||||
case loveList.id:
|
||||
dirName = window.i18n.t(loveList.name)
|
||||
break
|
||||
default:
|
||||
dirName = userLists.find(list => list.id === listId)?.name
|
||||
break
|
||||
}
|
||||
if (dirName) dirName = filterFileName(dirName)
|
||||
savePath = joinPath(savePath, clipFileNameLength(dirName ?? window.i18n.t(defaultList.name)))
|
||||
}
|
||||
return savePath
|
||||
}
|
||||
@@ -94,8 +94,8 @@
|
||||
v-model:show="isShowListAddMultiple" :from-list-id="listId"
|
||||
:is-move="isMoveMultiple" :music-list="selectedList" :exclude-list-id="excludeListIds" teleport="#view" @confirm="removeAllSelect"
|
||||
/>
|
||||
<common-download-modal v-model:show="isShowDownload" :music-info="selectedDownloadMusicInfo" teleport="#view" />
|
||||
<common-download-multiple-modal v-model:show="isShowDownloadMultiple" :list="selectedList" teleport="#view" @confirm="removeAllSelect" />
|
||||
<common-download-modal v-model:show="isShowDownload" :music-info="selectedDownloadMusicInfo" teleport="#view" :list-id="listId" />
|
||||
<common-download-multiple-modal v-model:show="isShowDownloadMultiple" :list="selectedList" teleport="#view" :list-id="listId" @confirm="removeAllSelect" />
|
||||
<search-list :list="list" :visible="isShowSearchBar" @action="handleMusicSearchAction" />
|
||||
<music-sort-modal v-model:show="isShowMusicSortModal" :music-info="selectedSortMusicInfo" :selected-num="selectedNum" @confirm="sortMusic" />
|
||||
<music-toggle-modal v-model:show="isShowMusicToggleModal" :music-info="selectedToggleMusicInfo" @toggle="toggleSource" />
|
||||
|
||||
@@ -5,6 +5,8 @@ dd
|
||||
base-checkbox(id="setting_download_enable" :model-value="appSetting['download.enable']" :label="$t('setting__download_enable')" @update:model-value="updateSetting({'download.enable': $event})")
|
||||
.gap-top
|
||||
base-checkbox(id="setting_download_skip_exist_file" :model-value="appSetting['download.skipExistFile']" :label="$t('setting__download_skip_exist_file')" @update:model-value="updateSetting({'download.skipExistFile': $event})")
|
||||
.gap-top
|
||||
base-checkbox(id="setting_download_save_group_list_name" :model-value="appSetting['download.isSavePathGroupByListName']" :label="$t('setting_download_save_group_list_name')" @update:model-value="updateSetting({'download.isSavePathGroupByListName': $event})")
|
||||
dd(:aria-label="$t('setting__download_path_title')")
|
||||
h3#download_path {{ $t('setting__download_path') }}
|
||||
div
|
||||
|
||||
@@ -8,7 +8,7 @@ import { createDownloadInfo } from './utils'
|
||||
// assertApiSupport,
|
||||
// getExt,
|
||||
// } from '..'
|
||||
import { checkPath, getFileStats, removeFile } from '@common/utils/nodejs'
|
||||
import { checkAndCreateDir, checkPath, getFileStats, removeFile } from '@common/utils/nodejs'
|
||||
import { DOWNLOAD_STATUS } from '@common/constants'
|
||||
// import { download as eventDownloadNames } from '@renderer/event/names'
|
||||
|
||||
@@ -40,12 +40,12 @@ const sendAction = (id: string, action: LX.Download.DownloadTaskActions) => {
|
||||
export const createDownloadTasks = (
|
||||
list: LX.Music.MusicInfoOnline[],
|
||||
quality: LX.Quality,
|
||||
savePath: string,
|
||||
fileNameFormat: string,
|
||||
qualityList: LX.QualityList,
|
||||
listId?: string,
|
||||
): LX.Download.ListItem[] => {
|
||||
return list.map(musicInfo => {
|
||||
return createDownloadInfo(musicInfo, quality, fileNameFormat, savePath, qualityList)
|
||||
return createDownloadInfo(musicInfo, quality, fileNameFormat, qualityList, listId)
|
||||
}).filter(task => task)
|
||||
// commit('addTasks', { list: taskList, addMusicLocationType: rootState.setting.list.addMusicLocationType })
|
||||
// let result = getStartTask(downloadList, DOWNLOAD_STATUS, rootState.setting.download.maxDownloadNum)
|
||||
@@ -60,7 +60,7 @@ const createTask = async(downloadInfo: LX.Download.ListItem, savePath: string, s
|
||||
// 开始任务
|
||||
/* commit('onStart', downloadInfo)
|
||||
commit('setStatusText', { downloadInfo, text: '任务初始化中' }) */
|
||||
if (!await checkPath(savePath)) {
|
||||
if (!await checkAndCreateDir(savePath)) {
|
||||
sendAction(downloadInfo.id, {
|
||||
action: 'error',
|
||||
data: {
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import { DOWNLOAD_STATUS, QUALITYS } from '@common/constants'
|
||||
import { filterFileName } from '@common/utils/common'
|
||||
import { joinPath } from '@common/utils/nodejs'
|
||||
import { mergeLyrics } from './lrcTool'
|
||||
import fs from 'fs'
|
||||
import { clipFileNameLength, clipNameLength } from '@common/utils/tools'
|
||||
|
||||
/**
|
||||
* 保存歌词文件
|
||||
@@ -65,22 +65,8 @@ export const getMusicType = (musicInfo: LX.Music.MusicInfoOnline, type: LX.Quali
|
||||
// const checkExistList = (list: LX.Download.ListItem[], musicInfo: LX.Music.MusicInfo, type: LX.Quality, ext: string): boolean => {
|
||||
// return list.some(s => s.id === musicInfo.id && (s.metadata.type === type || s.metadata.ext === ext))
|
||||
// }
|
||||
const MAX_NAME_LENGTH = 80
|
||||
const MAX_FILE_NAME_LENGTH = 150
|
||||
const clipNameLength = (name: string) => {
|
||||
if (name.length <= MAX_NAME_LENGTH || !name.includes('、')) return name
|
||||
const names = name.split('、')
|
||||
let newName = names.shift()!
|
||||
for (const name of names) {
|
||||
if (newName.length + name.length > MAX_NAME_LENGTH) break
|
||||
newName = newName + '、' + name
|
||||
}
|
||||
return newName
|
||||
}
|
||||
const clipFileNameLength = (name: string) => {
|
||||
return name.length > MAX_FILE_NAME_LENGTH ? name.substring(0, MAX_FILE_NAME_LENGTH) : name
|
||||
}
|
||||
export const createDownloadInfo = (musicInfo: LX.Music.MusicInfoOnline, type: LX.Quality, fileName: string, savePath: string, qualityList: LX.QualityList) => {
|
||||
|
||||
export const createDownloadInfo = (musicInfo: LX.Music.MusicInfoOnline, type: LX.Quality, fileName: string, qualityList: LX.QualityList, listId?: string) => {
|
||||
type = getMusicType(musicInfo, type, qualityList)
|
||||
let ext = getExt(type)
|
||||
const key = `${musicInfo.id}_${type}_${ext}`
|
||||
@@ -101,12 +87,13 @@ export const createDownloadInfo = (musicInfo: LX.Music.MusicInfoOnline, type: LX
|
||||
quality: type,
|
||||
ext,
|
||||
filePath: '',
|
||||
listId,
|
||||
fileName: filterFileName(`${clipFileNameLength(fileName
|
||||
.replace('歌名', musicInfo.name)
|
||||
.replace('歌手', clipNameLength(musicInfo.singer)))}.${ext}`),
|
||||
},
|
||||
}
|
||||
downloadInfo.metadata.filePath = joinPath(savePath, downloadInfo.metadata.fileName)
|
||||
// downloadInfo.metadata.filePath = joinPath(savePath, downloadInfo.metadata.fileName)
|
||||
// commit('addTask', downloadInfo)
|
||||
|
||||
// 删除同路径下的同名文件
|
||||
|
||||
@@ -9,7 +9,7 @@ import { createLocalMusicInfo } from '@renderer/utils/music'
|
||||
/**
|
||||
* 过滤列表中已播放的歌曲
|
||||
*/
|
||||
export const filterMusicList = async({ playedList, listId, list, savePath, playerMusicInfo, dislikeInfo, isNext }: {
|
||||
export const filterMusicList = async({ playedList, listId, list, playerMusicInfo, dislikeInfo, isNext }: {
|
||||
/**
|
||||
* 已播放列表
|
||||
*/
|
||||
@@ -25,7 +25,7 @@ export const filterMusicList = async({ playedList, listId, list, savePath, playe
|
||||
/**
|
||||
* 下载目录
|
||||
*/
|
||||
savePath: string
|
||||
// savePath: string
|
||||
/**
|
||||
* 播放器内当前歌曲(`playInfo.playerPlayIndex`指向的歌曲)
|
||||
*/
|
||||
|
||||
Reference in New Issue
Block a user