diff --git a/src/renderer/index.js b/src/renderer/index.js
index 1ebc458d..93716a3f 100644
--- a/src/renderer/index.js
+++ b/src/renderer/index.js
@@ -239,23 +239,60 @@ const app = new Vue({
hangtimer: null,
selectedMediaItems: [],
routes: ["browse", "listen_now", "radio"],
- musicBaseUrl: "https://api.music.apple.com/"
+ musicBaseUrl: "https://api.music.apple.com/",
+ modals: {
+ addToPlaylist: false
+ },
},
watch: {
page: () => {
document.getElementById("app-content").scrollTo(0, 0);
- app.selectedMediaItems = [];
+ app.resetState()
},
showingPlaylist: () => {
document.getElementById("app-content").scrollTo(0, 0);
- app.selectedMediaItems = [];
+ app.resetState()
},
artistPage: () => {
document.getElementById("app-content").scrollTo(0, 0);
- app.selectedMediaItems = [];
+ app.resetState()
},
},
methods: {
+ resetState() {
+ app.selectedMediaItems = [];
+ for (let key in app.modals) {
+ app.modals[key] = false;
+ }
+ },
+ promptAddToPlaylist() {
+ app.modals.addToPlaylist = true;
+ },
+ addSelectedToPlaylist(playlist_id) {
+ let self = this
+ let pl_items = []
+ for (let i = 0; i < self.selectedMediaItems.length; i++) {
+ if(self.selectedMediaItems[i].kind == "song") {
+ self.selectedMediaItems[i].kind = "songs"
+ }else if(self.selectedMediaItems[i].kind == "album") {
+ self.selectedMediaItems[i].kind = "albums"
+ } else if(self.selectedMediaItems[i].kind == "library-song") {
+ self.selectedMediaItems[i].kind = "library-songs"
+ } else if(self.selectedMediaItems[i].kind == "library-album") {
+ self.selectedMediaItems[i].kind = "library-albums"
+ }
+ pl_items.push({
+ id: self.selectedMediaItems[i].id,
+ type: self.selectedMediaItems[i].kind
+ })
+ }
+ this.modals.addToPlaylist = false
+ this.mk.api.library.appendTracksToPlaylist(playlist_id, pl_items).then(()=>{
+ if(this.page == 'playlist_' + this.showingPlaylist.id) {
+ this.getPlaylistFromID(this.showingPlaylist.id)
+ }
+ })
+ },
async init() {
let self = this
clearTimeout(this.hangtimer)
@@ -326,7 +363,7 @@ const app = new Vue({
let type = (self.mk.nowPlayingItem != null) ? self.mk.nowPlayingItem["type"] ?? '' : '';
- if (type.includes("musicVideo") || type.includes("uploadedVideo") || type.includes("music-movie")) {
+ if (type.includes("musicVideo") || type.includes("uploadedVideo") || type.includes("music-movie")) {
document.getElementById("apple-music-video-container").style.display = "block";
// app.chrome.topChromeVisible = false
} else {
@@ -366,7 +403,6 @@ const app = new Vue({
this.appRoute(window.location.hash)
}
-
setTimeout(() =>{
this.getBrowsePage();
this.$forceUpdate()}, 500)
@@ -401,13 +437,14 @@ const app = new Vue({
return false
}
},
- select_selectMediaItem(id, kind, index, guid) {
+ select_selectMediaItem(id, kind, index, guid, library) {
if (!this.select_hasMediaItem(guid)) {
this.selectedMediaItems.push({
id: id,
kind: kind,
index: index,
- guid: guid
+ guid: guid,
+ isLibrary: library
})
}
},
@@ -466,10 +503,11 @@ const app = new Vue({
let playlistId = response.id
this.playlists.loadingState = 0
this.showingPlaylist = response
- if(!response.relationships.tracks.next) {
+ if (!response.relationships.tracks.next) {
this.playlists.loadingState = 1
return
}
+
function getPlaylistTracks(next) {
app.apiCall(app.musicBaseUrl + next, res => {
if (self.showingPlaylist.id != playlistId) {
@@ -669,7 +707,6 @@ const app = new Vue({
window.location.hash = `${kind}/${id}`
document.querySelector("#app-content").scrollTop = 0
} else if (!kind.toString().includes("radioStation") && !kind.toString().includes("song") && !kind.toString().includes("musicVideo") && !kind.toString().includes("uploadedVideo") && !kind.toString().includes("music-movie")) {
- if (kind.toString().includes("music-movie")){kind = "musicMovie"}
app.page = (kind) + "_" + (id);
app.getTypeFromID((kind), (id), (isLibrary), {extend: "editorialVideo"});
window.location.hash = `${kind}/${id}`
diff --git a/src/renderer/style.less b/src/renderer/style.less
index f3b2fba3..9f3605a4 100644
--- a/src/renderer/style.less
+++ b/src/renderer/style.less
@@ -1520,6 +1520,49 @@ input[type="range"].web-slider.display--small::-webkit-slider-thumb {
/* Cider */
+.modal-fullscreen {
+ display:flex;
+ justify-content: center;
+ align-items: center;
+ position: fixed;
+ top: 0;
+ left: 0;
+ width: 100%;
+ height: 100%;
+ background: rgba(0, 0, 0, 0.5);
+ z-index: 9999;
+ .modal-window {
+ background: #333;
+ border-radius: var(--mediaItemRadius);
+ box-shadow: var(--mediaItemShadow-Shadow);
+ display:flex;
+ flex-flow: column;
+ .modal-header {
+ width:100%;
+ padding: 6px;
+ }
+ .modal-content {
+ width:100%;
+ height:100%;
+ overflow: hidden;
+ overflow-y: scroll;
+ }
+ .modal-footer {
+
+ }
+ }
+}
+
+.addtoplaylist-panel {
+ .modal-header {
+ padding: 16px;
+ }
+ .modal-window {
+ max-height: 500px;
+ max-width: 300px;
+ }
+}
+
#navigation-bar {
width: 100%;
background: rgba(0, 0, 0, 0.25);
diff --git a/src/renderer/views/components/add-to-playlist.ejs b/src/renderer/views/components/add-to-playlist.ejs
new file mode 100644
index 00000000..08ee7b31
--- /dev/null
+++ b/src/renderer/views/components/add-to-playlist.ejs
@@ -0,0 +1,36 @@
+
+
+
\ No newline at end of file
diff --git a/src/renderer/views/components/mediaitem-list-item.ejs b/src/renderer/views/components/mediaitem-list-item.ejs
index 7b832b4f..23b93c97 100644
--- a/src/renderer/views/components/mediaitem-list-item.ejs
+++ b/src/renderer/views/components/mediaitem-list-item.ejs
@@ -4,9 +4,10 @@
@contextmenu="contextMenu"
@click="select"
:data-id="item.attributes.playParams.id ?? item.id"
- :data-type="item.type ?? item.attributes.playParams.kind"
+ :data-type="getDataType()"
:data-index="index"
:data-guid="guid"
+ :data-islibrary="this.item.attributes.playParams.isLibrary ?? false"
class="cd-mediaitem-list-item"
:class="{'mediaitem-selected': app.select_hasMediaItem(guid)}">
@@ -84,11 +85,23 @@
'contextExt': {type: Object, required: false},
},
methods: {
+ getDataType() {
+ if(this.item.attributes.playParams.isLibrary) {
+ return this.item.type
+ }else{
+ return this.item.attributes.playParams.kind
+ }
+ },
select(e) {
+ let data_type = this.getDataType()
+ let item_id = this.item.attributes.playParams.id ?? this.item.id
+ let isLibrary = this.item.attributes.playParams.isLibrary ?? false
+
if (e.shiftKey) {
if (this.index != -1) {
+
if(app.selectedMediaItems.length == 0) {
- app.select_selectMediaItem(this.item.attributes.playParams.id ?? this.item.id, this.item.attributes.playParams.kind ?? this.item.type, this.index, this.guid)
+ app.select_selectMediaItem(item_id, this.getDataType(), this.index, this.guid, isLibrary)
}
let allMediaItems = document.querySelectorAll(".cd-mediaitem-list-item[data-index]")
let startIndex = Math.min(...app.selectedMediaItems.map(item => item.index))
@@ -100,7 +113,8 @@
app.select_selectMediaItem(item.getAttribute("data-id"),
item.getAttribute("data-type"),
item.getAttribute("data-index"),
- item.getAttribute("data-guid"))
+ item.getAttribute("data-guid")),
+ item.getAttribute("data-islibrary")
}
}
} else if (this.index > endIndex) {
@@ -110,7 +124,8 @@
app.select_selectMediaItem(item.getAttribute("data-id"),
item.getAttribute("data-type"),
item.getAttribute("data-index"),
- item.getAttribute("data-guid"))
+ item.getAttribute("data-guid")),
+ item.getAttribute("data-islibrary")
}
}
} else {
@@ -120,7 +135,8 @@
app.select_selectMediaItem(item.getAttribute("data-id"),
item.getAttribute("data-type"),
item.getAttribute("data-index"),
- item.getAttribute("data-guid"))
+ item.getAttribute("data-guid")),
+ item.getAttribute("data-islibrary")
}
}
}
@@ -129,29 +145,39 @@
if (app.select_hasMediaItem(this.guid)) {
app.select_removeMediaItem(this.guid)
} else {
- app.select_selectMediaItem(this.item.attributes.playParams.id ?? this.item.id, this.item.attributes.playParams.kind ?? this.item.type, this.index, this.guid)
+ app.select_selectMediaItem(item_id, this.getDataType(), this.index, this.guid, isLibrary)
}
} else {
if (app.select_hasMediaItem(this.guid)) {
app.selectedMediaItems = []
} else {
app.selectedMediaItems = []
- app.select_selectMediaItem(this.item.attributes.playParams.id ?? this.item.id, this.item.attributes.playParams.kind ?? this.item.type, this.index, this.guid)
+ app.select_selectMediaItem(item_id, this.getDataType(), this.index, this.guid, isLibrary)
}
}
},
contextMenu(event) {
let self = this
+ let data_type = this.getDataType()
+ let item_id = this.item.attributes.playParams.id ?? this.item.id
+ let isLibrary = this.item.attributes.playParams.isLibrary ?? false
+
let useMenu = "normal"
if (app.selectedMediaItems.length <= 1) {
app.selectedMediaItems = []
- app.select_selectMediaItem(this.item.attributes.playParams.id ?? this.item.id, this.item.attributes.playParams.kind ?? this.item.type, this.index, this.guid)
+ app.select_selectMediaItem(item_id, data_type, this.index, this.guid, isLibrary)
} else {
useMenu = "multiple"
}
let menus = {
multiple: {
items: [
+ {
+ "name": "Add to Playlist...",
+ "action": function () {
+ app.promptAddToPlaylist()
+ }
+ },
{
name: `Play ${app.selectedMediaItems.length} tracks next`,
action: () => {
@@ -197,6 +223,12 @@
},
normal: {
items: [
+ {
+ "name": "Add to Playlist...",
+ "action": function () {
+ app.promptAddToPlaylist()
+ }
+ },
{
"name": "Start Radio",
"action": function () {
diff --git a/src/renderer/views/main.ejs b/src/renderer/views/main.ejs
index f5e6d37a..468ed243 100644
--- a/src/renderer/views/main.ejs
+++ b/src/renderer/views/main.ejs
@@ -173,6 +173,7 @@
Playlists