1
0
Fork 0
mirror of https://github.com/heyarne/airsonic-ui.git synced 2026-05-07 02:33:39 +02:00

Remove current song

This commit is contained in:
heyarne 2019-03-10 12:09:17 +01:00
commit 065b3a6647
7 changed files with 72 additions and 7 deletions

View file

@ -1,7 +1,12 @@
module.exports = function (config) {
const configuration = {
browsers: ['ChromeHeadless'],
autoWatchBatchDelay: 1000,
// The tests are sometimes run before the tests were completely written
// to disc; this is a known problem unfortunately. This is a hack to at
// least keep the browsers connected so the tests are compiled and run
// again even if a developer isn't aware of this
autoWatchBatchDelay: 100,
browserNoActivityTimeout: 60 * 1000 * 10,
// The directory where the output file lives
basePath: 'public/test',
// The file itself

View file

@ -53,7 +53,8 @@
(fn [_]
(when-let [audio @audio]
(.pause audio)
(set! (.-currentTime audio) 0))))
(set! (.-currentTime audio) 0)
(set! (.-src audio) ""))))
(rf/reg-fx
:audio/toggle-play-pause

View file

@ -22,7 +22,9 @@
(enqueue-next [this song])
(move-song [this from-idx to-idx]
"Allows you to move a song in a playlist"))
"Allows you to move a song in a playlist")
(remove-song [this song-idx]
"Removes a song from the playlist"))
;; helpers to manage creating playlists
@ -142,7 +144,15 @@
(= from-idx current-idx) (assoc result :current-idx to-idx)
(<= to-idx current-idx from-idx) (update result :current-idx inc)
(>= to-idx current-idx from-idx) (update result :current-idx dec)
:else result))))
:else result)))
(remove-song [this song-idx]
(cond-> (update this :items #(let [n-items (count %)]
(-> (reduce (fn [items idx]
(assoc items idx (get items (inc idx))))
% (range song-idx n-items))
(dissoc (dec n-items)))))
(= song-idx current-idx) (assoc :current-idx -1))))
;; constructor wrapper

View file

@ -66,6 +66,14 @@
(fn [_ _]
{:audio/toggle-play-pause nil}))
(defn remove-song [{:keys [db]} [_ song-idx]]
(let [song-removed (update-in db [:audio :current-playlist] #(playlist/remove-song % song-idx))]
(cond-> {:db song-removed}
(nil? (playlist/current-song (get-in song-removed [:audio :current-playlist])))
(assoc :audio/stop nil))))
(rf/reg-event-fx :audio-player/remove-song remove-song)
(defn audio-update
"Reacts to audio events fired by the HTML5 audio player and plays the next
track if necessary."

View file

@ -21,10 +21,10 @@
(r/as-element [:span.is-size-7.has-text-grey-lighter
[icon :elevator]]))))
(defn song-actions []
(defn song-actions [{:keys [song idx]}]
;; TODO: Implement both of these
[dropdown {:items [{:label "Remove from queue"
:event []}
:event [:audio-player/remove-song idx]}
{:label "Go to source"
:event []}]}])
@ -62,7 +62,8 @@
[:td.song-artist [artist-link song]]
[:td.song-title [song-link song idx]]
[:td.song-duration (helpers/format-duration (:duration song) :brief? true)]
[:td.song-actions.is-narrow [song-actions]]])
[:td.song-actions.is-narrow [song-actions {:song song
:idx idx}]]])
:on-sort-end
(fn [{:keys [old-idx new-idx]}]

View file

@ -309,3 +309,33 @@
(is (= 3 (-> (playlist/set-current-song playlist 3)
(playlist/move-song 4 7)
:current-idx))))))))
(deftest remove-song
(with-redefs [shuffle identity]
(testing "Should remove a single song from the playlist"
(doseq [playback-mode [:linear :shuffled]
repeat-mode [:repeat-none :repeat-all :repeat-single]]
(let [n-songs 10
queue (song-queue n-songs)
playlist (playlist/->playlist queue :repeat-mode repeat-mode :playback-mode playback-mode)
first-removed (playlist/remove-song playlist 0)
middle-removed (playlist/remove-song playlist 5)
last-removed (playlist/remove-song playlist 9)
song-not-in-list? (fn [song playlist]
(every? #(not (same-song? % song))
(vals (:items playlist))))]
(is (= 9 (count first-removed) (count middle-removed) (count last-removed)))
(is (song-not-in-list? (first queue) first-removed))
(is (same-song? (second queue) (get (:items first-removed) 0)))
(is (song-not-in-list? (nth queue 5) middle-removed))
(is (same-song? (nth queue 6) (get (:items middle-removed) 5)))
(is (song-not-in-list? (last queue) last-removed)))))
(testing "Should pause if the currently playing song is removed"
(doseq [playback-mode [:linear :shuffled]
repeat-mode [:repeat-none :repeat-all :repeat-single]]
(let [n-songs 10
queue (song-queue n-songs)]
(is (nil? (-> (playlist/->playlist queue :repeat-mode repeat-mode :playback-mode playback-mode)
(playlist/set-current-song 5)
(playlist/remove-song 5)
(playlist/current-song)))))))))

View file

@ -27,3 +27,13 @@
(:current-idx)))
(str "for playback-mode " playback-mode " and repeat-mode " repeat-mode))
(is (contains? effects :audio/play))))))
(deftest removing-currently-playing-song
(testing "Should stop all audio when removing the currently playing song"
(doseq [playback-mode [:linear :shuffled]
repeat-mode [:repeat-none :repeat-single :repeat-all]]
(let [n-songs 100
fixture {:db {:credentials fixtures/credentials
:audio {:current-playlist (playlist/->playlist (song-queue n-songs) :playback-mode playback-mode :repeat-mode repeat-mode)}}}]
(is (contains? (events/remove-song fixture [:audio/remove-song 0]) :audio/stop))
(is (not (contains? (events/remove-song fixture [:audio/remove-song 99]) :audio/stop)))))))