Merge branch 'main' into router-implementation

This commit is contained in:
Roberto Tonino
2020-08-22 21:11:22 +02:00
44 changed files with 2773 additions and 1141 deletions

View File

@@ -7,6 +7,8 @@
<TheTrackPreview />
<TheQualityModal />
<TheContextMenu />
</div>
</template>
@@ -16,6 +18,7 @@ import TheMainContent from '@components/TheMainContent.vue'
import TheTrackPreview from '@components/TheTrackPreview.vue'
import TheQualityModal from '@components/TheQualityModal.vue'
import BaseLoadingPlaceholder from '@components/BaseLoadingPlaceholder.vue'
import TheContextMenu from '@components/TheContextMenu.vue'
export default {
components: {
@@ -23,10 +26,8 @@ export default {
TheMainContent,
TheTrackPreview,
TheQualityModal,
BaseLoadingPlaceholder
BaseLoadingPlaceholder,
TheContextMenu
}
}
</script>
<style>
</style>

View File

@@ -8,14 +8,7 @@
}"
>
<h1>{{ title }}</h1>
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="link"
class="fab right"
>
<div role="button" aria-label="download" @click.stop="addToQueue" :data-link="link" class="fab right">
<i class="material-icons" :title="$t('globals.download_hint')">get_app</i>
</div>
</header>
@@ -69,12 +62,8 @@
</i>
</td>
<td>{{ release.release_date }}</td>
<td
@click.stop="addToQueue"
@contextmenu.prevent="openQualityModal"
:data-link="release.link"
class="clickable"
>
<td>{{ release.nb_song }}</td>
<td @click.stop="addToQueue" :data-link="release.link" class="clickable">
<i class="material-icons" :title="$t('globals.download_hint')">
file_download
</i>
@@ -129,9 +118,6 @@ export default {
e.stopPropagation()
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
sortBy(key) {
if (key == this.sortKey) {
this.sortOrder = this.sortOrder == 'asc' ? 'desc' : 'asc'
@@ -172,6 +158,7 @@ export default {
this.head = [
{ title: this.$tc('globals.listTabs.title', 1), sortKey: 'title' },
{ title: this.$t('globals.listTabs.releaseDate'), sortKey: 'release_date' },
{ title: this.$tc('globals.listTabs.track', 2), sortKey: 'nb_song' },
{ title: '', width: '32px' }
]
if (isEmpty(releases)) {
@@ -183,8 +170,17 @@ export default {
},
computed: {
showTable() {
if (this.body) return orderBy(this.body[this.currentTab], this.sortKey, this.sortOrder)
else return []
if (this.body) {
if (this.sortKey == 'nb_song')
return orderBy(
this.body[this.currentTab],
function (o) {
return new Number(o.nb_song)
},
this.sortOrder
)
else return orderBy(this.body[this.currentTab], this.sortKey, this.sortOrder)
} else return []
}
},
mounted() {

View File

@@ -82,10 +82,6 @@
<strong>PayPal:</strong>
<a href="https://paypal.me/RemixDev" target="_blank">PayPal.me/RemixDev</a>
</li>
<li>
<i class="bitcoin" v-html="bitcoin" />
<strong>Bitcoin:</strong> 1sdNymSJrMBWyHM4u2m9uco5nv6uV4Qs1
</li>
<li>
<i class="ethereum" v-html="ethereum" />
<strong>Ethereum:</strong> 0x1d2aa67e671485CD4062289772B662e0A6Ff976c
@@ -123,10 +119,6 @@ i /deep/ svg {
width: 20px;
}
.bitcoin /deep/ svg {
fill: #ff9900;
}
.ethereum /deep/ svg {
fill: var(--foreground);
}
@@ -200,14 +192,12 @@ ul {
</style>
<script>
import paypal from '@/assets/paypal.svg'
import bitcoin from '@/assets/bitcoin.svg'
import ethereum from '@/assets/ethereum.svg'
export default {
data: () => ({
paypal,
ethereum,
bitcoin
ethereum
}),
mounted() {
console.log('about mounted')

View File

@@ -36,11 +36,7 @@
</div>
<div v-else id="charts_table">
<button @click="changeCountry">{{ $t('charts.changeCountry') }}</button>
<button
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="'https://www.deezer.com/playlist/' + id"
>
<button @click.stop="addToQueue" :data-link="'https://www.deezer.com/playlist/' + id">
{{ $t('charts.download') }}
</button>
<table class="table table--charts">
@@ -94,7 +90,6 @@
</td>
<td
class="table__cell--download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="track.link"
role="button"
@@ -144,9 +139,6 @@ export default {
e.stopPropagation()
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
getTrackList(event) {
document.getElementById('content').scrollTo(0, 0)

View File

@@ -0,0 +1,316 @@
<template>
<div class="context-menu" v-show="menuOpen" ref="contextMenu" :style="{ top: yPos, left: xPos }">
<button
class="menu-option"
v-for="option of sortedOptions"
:key="option.label"
v-show="option.show"
@click.prevent="option.action"
>
<span class="menu-option__text">{{ option.label }}</span>
</button>
</div>
</template>
<script>
import Downloads from '@/utils/downloads'
import downloadQualities from '@js/qualities'
import { generatePath, copyToClipboard } from '@/utils/utils'
export default {
data() {
return {
menuOpen: false,
xPos: 0,
yPos: 0,
deezerHref: '',
generalHref: '',
imgSrc: ''
}
},
computed: {
options() {
// In the action property:
// Use arrow functions to keep the Vue instance in 'this'
// Use normal functions to keep the object instance in 'this'
const options = {
cut: {
label: this.$t('globals.cut'),
show: false,
position: 1,
action: () => {
document.execCommand('Cut')
}
},
copy: {
label: this.$t('globals.copy'),
show: false,
position: 2,
action: () => {
document.execCommand('Copy')
}
},
copyLink: {
label: this.$t('globals.copyLink'),
show: false,
position: 3,
action: () => {
copyToClipboard(this.generalHref)
}
},
copyImageLink: {
label: this.$t('globals.copyImageLink'),
show: false,
position: 4,
action: () => {
copyToClipboard(this.imgSrc)
}
},
copyDeezerLink: {
label: this.$t('globals.copyDeezerLink'),
show: false,
position: 5,
action: () => {
copyToClipboard(this.deezerHref)
}
},
paste: {
label: this.$t('globals.paste'),
show: false,
position: 6,
action: () => {
// Paste does not always work
if (clipboard in navigator) {
navigator.clipboard.readText().then(text => {
document.execCommand('insertText', undefined, text)
})
} else {
document.execCommand('paste')
}
}
}
}
let nextValuePosition = Object.values(options).length + 1
downloadQualities.forEach((quality, index) => {
options[quality.objName] = {
label: `${this.$t('globals.download', [quality.label])}`,
show: false,
position: nextValuePosition + index,
action: this.tryToDownloadTrack.bind(null, quality.value)
}
})
return options
},
/**
* This computed property is used for rendering the options in the wanted order
* while keeping the options computed property an Object to make the properties
* accessible via property name (es this.options.copyLink)
*
* @return {object[]} Options in order according to position property
*/
sortedOptions() {
return Object.values(this.options).sort((first, second) => {
return first.position < second.position ? -1 : 1
})
}
},
mounted() {
document.body.addEventListener('contextmenu', this.showMenu)
document.body.addEventListener('click', this.hideMenu)
},
methods: {
showMenu(contextMenuEvent) {
// contextMenuEvent.preventDefault()
const { pageX, pageY, target: elementClicked } = contextMenuEvent
const path = generatePath(elementClicked)
let deezerLink = null
// Searching for the first element with a data-link attribute
// let deezerLink = this.searchForDataLink(...)
for (let i = 0; i < path.length; i++) {
if (path[i] == document) break
if (path[i].matches('[data-link]')) {
deezerLink = path[i].dataset.link
break
}
}
const isLink = elementClicked.matches('a')
const isImage = elementClicked.matches('img')
const hasDeezerLink = !!deezerLink
if (!isLink && !isImage && !hasDeezerLink) return
contextMenuEvent.preventDefault()
this.menuOpen = true
this.positionMenu(pageX, pageY)
if (isLink) {
// Show 'Copy Link' option
this.generalHref = elementClicked.href
this.options.copyLink.show = true
}
if (isImage) {
// Show 'Copy Image Link' option
this.imgSrc = elementClicked.src
this.options.copyImageLink.show = true
}
if (deezerLink) {
// Show 'Copy Deezer Link' option
this.deezerHref = deezerLink
this.showDeezerOptions()
}
},
hideMenu() {
if (!this.menuOpen) return
// Finish all operations before closing (may be not necessary)
this.$nextTick()
.then(() => {
this.menuOpen = false
this.options.copyLink.show = false
this.options.copyDeezerLink.show = false
this.options.copyImageLink.show = false
downloadQualities.forEach(quality => {
this.options[quality.objName].show = false
})
})
.catch(err => {
console.error(err)
})
},
positionMenu(newX, newY) {
this.xPos = `${newX}px`
this.yPos = `${newY}px`
this.$nextTick().then(() => {
const { innerHeight, innerWidth } = window
const menuXOffest = newX + this.$refs.contextMenu.getBoundingClientRect().width
const menuYOffest = newY + this.$refs.contextMenu.getBoundingClientRect().height
if (menuXOffest > innerWidth) {
const difference = menuXOffest - innerWidth + 15
this.xPos = `${newX - difference}px`
}
if (menuYOffest > innerHeight) {
const difference = menuYOffest - innerHeight + 15
this.yPos = `${newY - difference}px`
}
})
},
showDeezerOptions() {
this.options.copyDeezerLink.show = true
downloadQualities.forEach(quality => {
this.options[quality.objName].show = true
})
},
tryToDownloadTrack(qualityValue) {
Downloads.sendAddToQueue(this.deezerHref, qualityValue)
}
}
}
</script>
<style lang="scss" scoped>
.context-menu {
position: absolute;
top: 0;
left: 0;
min-width: 100px;
border-radius: 7px;
background: var(--foreground-inverted);
box-shadow: 4px 10px 18px 0px hsla(0, 0%, 0%, 0.15);
overflow: hidden;
z-index: 10000;
}
.menu-option {
display: flex;
align-items: center;
width: 100%;
height: 40px;
padding-left: 10px;
padding-right: 10px;
color: var(--foreground);
cursor: pointer;
&:hover {
background: var(--table-highlight);
filter: brightness(150%);
}
&__text {
text-transform: capitalize;
}
}
// Resetting buttons only for this component (because the style is scoped)
button {
color: var(--accent-text);
color: unset;
background-color: var(--accent-color);
background-color: unset;
min-width: unset;
position: unset;
border: unset;
border-radius: unset;
font-family: unset;
font-weight: unset;
font-size: unset;
padding: unset;
margin-right: unset;
height: unset;
text-transform: unset;
cursor: unset;
transition: unset;
&:focus {
outline: none;
}
&[disabled] {
background-color: unset;
color: unset;
opacity: unset;
}
&.selective {
background-color: unset;
color: unset;
&.active {
background-color: unset;
color: unset;
}
}
&.with_icon {
display: unset;
align-items: unset;
i {
margin-left: unset;
}
}
&:active {
background-color: unset;
transform: unset;
}
&:hover {
background: unset;
border: unset;
}
}
</style>

View File

@@ -15,9 +15,7 @@
:title="$t('globals.toggle_download_tab_hint')"
></i>
<div id="queue_buttons">
<i id="open_downloads_folder" class="material-icons download_bar_icon hide" @click="openDownloadsFolder">
folder_open
</i>
<i id="open_downloads_folder" class="material-icons download_bar_icon hide" :title="$t('globals.open_downloads_folder')" @click="openDownloadsFolder">folder_open</i>
<i id="clean_queue" class="material-icons download_bar_icon" @click="cleanQueue" :title="$t('globals.clean_queue_hint')">clear_all</i>
<i id="cancel_queue" class="material-icons download_bar_icon" @click="cancelQueue" :title="$t('globals.cancel_queue_hint')">delete_sweep</i>
</div>
@@ -42,6 +40,7 @@ export default {
}),
mounted() {
socket.on('startDownload', this.startDownload)
socket.on('startConversion', this.startConversion)
socket.on('init_downloadQueue', this.initQueue)
socket.on('addedToQueue', this.addToQueue)
socket.on('updateQueue', this.updateQueue)
@@ -97,26 +96,43 @@ export default {
}
},
initQueue(data) {
const { queue: initQueue, queueComplete: initQueueComplete, currentItem, queueList: initQueueList } = data
const { queue: initQueue, queueComplete: initQueueComplete, currentItem, queueList: initQueueList, restored } = data
if (initQueueComplete.length) {
initQueueComplete.forEach(item => {
initQueueList[item].init = true
initQueueList[item].silent = true
this.addToQueue(initQueueList[item])
})
}
if (currentItem) {
initQueueList[currentItem].init = true
initQueueList[currentItem].silent = true
this.addToQueue(initQueueList[currentItem], true)
}
initQueue.forEach(item => {
initQueueList[item].init = true
initQueueList[item].silent = true
this.addToQueue(initQueueList[item])
})
if (restored){
toast(this.$t('toasts.queueRestored'), 'done', true, 'restoring_queue')
socket.emit('queueRestored')
}
},
addToQueue(queueItem, current = false) {
if (Array.isArray(queueItem)){
if (queueItem.length > 1){
queueItem.forEach((item, i) => {
item.silent = true
this.addToQueue(item)
});
toast(this.$t('toasts.addedMoreToQueue', [queueItem.length]), 'playlist_add_check')
return
}else{
queueItem = queueItem[0]
}
}
this.queueList[queueItem.uuid] = queueItem
if (queueItem.downloaded + queueItem.failed == queueItem.size) {
@@ -188,13 +204,13 @@ export default {
}
}
if (!queueItem.init) {
if (!queueItem.silent) {
toast(this.$t('toasts.addedToQueue', [queueItem.title]), 'playlist_add_check')
}
},
updateQueue(update) {
// downloaded and failed default to false?
const { uuid, downloaded, failed, progress, error, data, errid } = update
const { uuid, downloaded, failed, progress, conversion, error, data, errid } = update
if (uuid && this.queue.indexOf(uuid) > -1) {
if (downloaded) {
@@ -224,6 +240,10 @@ export default {
this.queueList[uuid].progress = progress
$('#bar_' + uuid).css('width', progress + '%')
}
if (conversion) {
$('#bar_' + uuid).css('width', (100-conversion) + '%')
}
}
},
removeFromQueue(uuid) {
@@ -339,9 +359,17 @@ export default {
},
startDownload(uuid) {
$('#bar_' + uuid)
.removeClass('converting')
.removeClass('indeterminate')
.addClass('determinate')
},
startConversion(uuid) {
$('#bar_' + uuid)
.addClass('converting')
.removeClass('indeterminate')
.addClass('determinate')
.css('width', '100%')
},
showErrorsTab(clickEvent) {
this.$root.$emit('showTabErrors', clickEvent.data.item, clickEvent.target)
}

View File

@@ -38,7 +38,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -62,7 +61,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -88,7 +86,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -112,7 +109,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -178,7 +174,6 @@
</td>
<td
class="table__cell--download clickable"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="track.link"
role="button"
@@ -260,9 +255,6 @@ export default {
e.stopPropagation()
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
updated_userSpotifyPlaylists(data) {
this.spotifyPlaylists = data
},

View File

@@ -20,7 +20,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -50,7 +49,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -89,9 +87,6 @@ export default {
addToQueue(e) {
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
initHome(data) {
const {
playlists: { data: playlistData },

View File

@@ -118,6 +118,7 @@ import { socket } from '@/utils/socket'
import { showView } from '@js/tabs.js'
import Utils from '@/utils/utils'
import EventBus from '@/utils/EventBus'
import Downloads from '@/utils/downloads'
export default {
name: 'the-link-analyzer-tab',
@@ -184,6 +185,9 @@ export default {
},
notSupported() {
this.link = 'error'
},
addToQueue(e) {
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
}
},
mounted() {

View File

@@ -50,7 +50,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="results.allTab.TOP_RESULT[0].link"
class="download_overlay"
@@ -115,7 +114,6 @@
</td>
<td
class="table__cell--download table__cell--center clickable"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="'https://www.deezer.com/track/' + track.SNG_ID"
role="button"
@@ -149,7 +147,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="'https://deezer.com/artist/' + release.ART_ID"
class="download_overlay"
@@ -181,7 +178,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="'https://deezer.com/album/' + release.ALB_ID"
class="download_overlay"
@@ -224,7 +220,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="'https://deezer.com/playlist/' + release.PLAYLIST_ID"
class="download_overlay"
@@ -321,7 +316,6 @@
</td>
<td
class="table__cell--download table__cell--center clickable"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="track.link"
role="button"
@@ -353,7 +347,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -391,7 +384,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -422,7 +414,6 @@
<div
role="button"
aria-label="download"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="release.link"
class="download_overlay"
@@ -625,9 +616,6 @@ export default {
addToQueue(e) {
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
numberWithDots: Utils.numberWithDots,
convertDuration: Utils.convertDuration,
search(type) {

View File

@@ -53,7 +53,6 @@ export default {
}),
mounted() {
this.$root.$on('QualityModal:open', this.openModal)
this.$refs.modal.addEventListener('webkitAnimationEnd', this.handleAnimationEnd)
},
methods: {

View File

@@ -19,13 +19,16 @@
</h3>
<div class="inline-flex">
<input autocomplete="off" type="password" id="login_input_arl" ref="loginInput" placeholder="ARL" />
<button id="settings_btn_copyArl" @click="copyARLtoClipboard">
<button id="settings_btn_copyArl" class="only_icon" @click="copyARLtoClipboard">
<i class="material-icons">assignment</i>
</button>
</div>
<a href="https://codeberg.org/RemixDev/deemix/wiki/Getting-your-own-ARL" target="_blank">
{{ $t('settings.login.arl.question') }}
</a>
<a id="settings_btn_applogin" class="hide" href="#" @click="applogin">
Automated login
</a>
<button id="settings_btn_updateArl" @click="login" style="width: 100%;">
{{ $t('settings.login.arl.update') }}
</button>
@@ -62,7 +65,12 @@
<h3 class="settings-group__header settings-group__header--with-icon">
<i class="material-icons">folder</i>{{ $t('settings.downloadPath.title') }}
</h3>
<input type="text" v-model="settings.downloadLocation" />
<div class="inline-flex">
<input autocomplete="off" type="text" v-model="settings.downloadLocation" />
<button id="select_downloads_folder" class="only_icon hide" @click="selectDownloadFolder">
<i class="material-icons">folder</i>
</button>
</div>
</div>
<div class="settings-group">
@@ -186,6 +194,8 @@
<select v-model="settings.overwriteFile">
<option value="y">{{ $t('settings.downloads.overwriteFile.y') }}</option>
<option value="n">{{ $t('settings.downloads.overwriteFile.n') }}</option>
<option value="e">{{ $t('settings.downloads.overwriteFile.e') }}</option>
<option value="b">{{ $t('settings.downloads.overwriteFile.b') }}</option>
<option value="t">{{ $t('settings.downloads.overwriteFile.t') }}</option>
</select>
</div>
@@ -264,12 +274,14 @@
<div class="input_group">
<p class="input_group_text">{{ $t('settings.covers.localArtworkSize') }}</p>
<input type="number" min="100" max="1800" step="100" v-model.number="settings.localArtworkSize" />
<input type="number" min="100" max="10000" step="100" v-model.number="settings.localArtworkSize" />
<p v-if="settings.localArtworkSize > 1200" class="input_group_text" style="opacity: 0.75; color: #ffcc22;"> {{ $t('settings.covers.imageSizeWarning') }}</p>
</div>
<div class="input_group">
<p class="input_group_text">{{ $t('settings.covers.embeddedArtworkSize') }}</p>
<input type="number" min="100" max="1800" step="100" v-model.number="settings.embeddedArtworkSize" />
<input type="number" min="100" max="10000" step="100" v-model.number="settings.embeddedArtworkSize" />
<p v-if="settings.embeddedArtworkSize > 1200" class="input_group_text" style="opacity: 0.75; color: #ffcc22;"> {{ $t('settings.covers.imageSizeWarning') }}</p>
</div>
<div class="input_group">
@@ -281,6 +293,12 @@
</select>
</div>
<label class="with_checkbox">
<input type="checkbox" v-model="settings.embeddedArtworkPNG" />
<span class="checkbox_text">{{ $t('settings.covers.embeddedArtworkPNG') }}</span>
</label>
<p v-if="settings.embeddedArtworkPNG" style="opacity: 0.75; color: #ffcc22;"> {{ $t('settings.covers.embeddedPNGWarning') }}</p>
<div class="input_group">
<p class="input_group_text">{{ $t('settings.covers.jpegImageQuality') }}</p>
<input type="number" min="1" max="100" v-model.number="settings.jpegImageQuality" />
@@ -727,6 +745,8 @@ export default {
socket.on('updateSettings', this.updateSettings)
socket.on('accountChanged', this.accountChanged)
socket.on('familyAccounts', this.initAccounts)
socket.on('downloadFolderSelected', this.downloadFolderSelected)
socket.on('applogin_arl', this.setArl)
},
methods: {
revertSettings() {
@@ -768,6 +788,13 @@ export default {
socket.emit('saveSettings', this.lastSettings, this.lastCredentials, changed ? this.lastUser : false)
},
selectDownloadFolder() {
if (window.clientMode) socket.emit('selectDownloadFolder')
},
downloadFolderSelected(folder){
console.log(folder)
this.settings.downloadLocation = folder
},
loadSettings(settings, spotifyCredentials, defaults = null) {
if (defaults) {
this.defaultSettings = { ...defaults }
@@ -784,6 +811,14 @@ export default {
socket.emit('login', arl, true, this.accountNum)
}
},
applogin(e) {
e.preventDefault()
if (window.clientMode) socket.emit('applogin')
},
setArl(arl) {
this.$refs.loginInput.value = arl
this.login()
},
changeAccount() {
socket.emit('changeAccount', this.accountNum)
},

View File

@@ -9,11 +9,11 @@
<span class="main_tablinks_text">{{ $t('sidebar.search') }}</span>
</span>
<span id="main_charts_tablink" class="main_tablinks" role="link" aria-label="charts">
<i class="material-icons side_icon">bubble_chart</i>
<i class="material-icons side_icon">show_chart</i>
<span class="main_tablinks_text">{{ $t('sidebar.charts') }}</span>
</span>
<span id="main_favorites_tablink" class="main_tablinks" role="link" aria-label="favorites">
<i class="material-icons side_icon">album</i>
<i class="material-icons side_icon">star</i>
<span class="main_tablinks_text">{{ $t('sidebar.favorites') }}</span>
</span>
<span id="main_analyzer_tablink" class="main_tablinks" role="link" aria-label="link analyzer">
@@ -194,4 +194,3 @@ export default {
}
}
</script>

View File

@@ -30,7 +30,10 @@ export default {
onTimeUpdate() {
// Prevents first time entering in this function
if (isNaN(this.$refs.preview.duration)) return
if (this.$refs.preview.currentTime <= this.$refs.preview.duration - 1) return
let duration = this.$refs.preview.duration
if (!isFinite(duration)) duration = 30
if (duration - this.$refs.preview.currentTime >= 1) return
if (this.previewStopped) return
$(this.$refs.preview).animate({ volume: 0 }, 800)

View File

@@ -133,15 +133,10 @@
</table>
<span v-if="label" style="opacity: 0.4; margin-top: 8px; display: inline-block; font-size: 13px;">{{ label }}</span>
<footer>
<button @contextmenu.prevent="openQualityModal" @click.stop="addToQueue" :data-link="link">
<button @click.stop="addToQueue" :data-link="link">
{{ `${$t('globals.download', [$tc(`globals.listTabs.${type}`, 1)])}` }}
</button>
<button
class="with_icon"
@contextmenu.prevent="openQualityModal"
@click.stop="addToQueue"
:data-link="selectedLinks()"
>
<button class="with_icon" @click.stop="addToQueue" :data-link="selectedLinks()">
{{ $t('tracklist.downloadSelection') }}<i class="material-icons">file_download</i>
</button>
<button class="back-button" @click="backTab">{{ $t('globals.back') }}</button>
@@ -191,9 +186,6 @@ export default {
addToQueue(e) {
Downloads.sendAddToQueue(e.currentTarget.dataset.link)
},
openQualityModal(e) {
this.$root.$emit('QualityModal:open', e.currentTarget.dataset.link)
},
toggleAll(e) {
this.body.forEach(item => {
if (item.type == 'track') {