| Add ability to load previous track
All checks were successful
SonarQube Code Quality Scan / SonarQube Scan (push) Successful in 26s

This commit is contained in:
2026-06-01 21:29:53 +03:00
parent 31ceb040ed
commit 363ee732b4
2 changed files with 85 additions and 4 deletions

59
gui.py
View File

@@ -972,7 +972,8 @@ class PlaybackBar(QWidget):
"QPushButton:hover { color: #ffffff; }"
),
}
btn_base = icon_style["normal"] + icon_style["hover"]
self._btn_base = icon_style["normal"] + icon_style["hover"]
btn_base = self._btn_base
self._loop_btn = QPushButton("")
self._loop_btn.setFixedSize(btn_size, btn_size)
@@ -986,13 +987,17 @@ class PlaybackBar(QWidget):
self._prev_btn = QPushButton("")
self._prev_btn.setFixedSize(btn_size, btn_size)
self._prev_btn.setToolTip("Restart / Previous")
self._prev_btn.setToolTip("Previous")
self._prev_btn.setStyleSheet(btn_base)
self._prev_btn.clicked.connect(self._restart)
self._prev_btn.setEnabled(False)
self._play_btn = QPushButton("")
self._play_btn.setFixedSize(40, 40)
self._play_btn.setToolTip("Play / Pause")
self._play_btn.setEnabled(False)
self._play_btn.setStyleSheet(
"QPushButton { background: #ffffff; border: none;"
" border-radius: 20px; color: #0a0814;"
@@ -1008,6 +1013,8 @@ class PlaybackBar(QWidget):
self._next_btn.setStyleSheet(btn_base)
self._next_btn.clicked.connect(self._next)
self._next_btn.setEnabled(False)
self._stop_btn = QPushButton("")
self._stop_btn.setFixedSize(btn_size, btn_size)
self._stop_btn.setToolTip("Stop")
@@ -1017,6 +1024,8 @@ class PlaybackBar(QWidget):
)
self._stop_btn.clicked.connect(self._stop)
self._stop_btn.setEnabled(False)
btn_row.addWidget(self._loop_btn)
btn_row.addWidget(self._prev_btn)
btn_row.addStretch()
@@ -1024,6 +1033,19 @@ class PlaybackBar(QWidget):
btn_row.addStretch()
btn_row.addWidget(self._next_btn)
btn_row.addWidget(self._stop_btn)
self._disabled_style = """
QPushButton { background: transparent; border: none;
color: #44445a; font-size: 15pt; }
"""
self._disabled_extra = """
QPushButton { background: transparent; border: none;
color: #44445a; font-size: 15pt; }
QPushButton:hover { color: #44445a; }
"""
self._disabled_loop_checked = """
QPushButton:checked { color: #44445a; }
"""
center_layout.addLayout(btn_row)
# ── Progress bar ──
@@ -1263,8 +1285,34 @@ class PlaybackBar(QWidget):
self._player.set_loop(enabled)
self._loop_btn.setChecked(enabled)
def set_buttons_enabled(self, enabled: bool) -> None:
"""Enable or disable playback control buttons."""
if enabled:
normal = self._btn_base
loop_checked = "QPushButton:checked { color: #a78bfa; }"
else:
normal = self._disabled_extra
loop_checked = self._disabled_loop_checked
self._prev_btn.setEnabled(enabled)
self._prev_btn.setStyleSheet(normal)
self._play_btn.setEnabled(enabled)
self._next_btn.setEnabled(enabled)
self._next_btn.setStyleSheet(normal)
self._stop_btn.setEnabled(enabled)
self._stop_btn.setStyleSheet(normal)
self._loop_btn.setEnabled(enabled)
if enabled:
self._loop_btn.setStyleSheet(self._btn_base + loop_checked)
else:
self._loop_btn.setStyleSheet(self._disabled_style + loop_checked)
self._vol_slider.setEnabled(enabled)
self._vol_btn.setEnabled(enabled)
def _restart(self) -> None:
self._player.seek(0)
if self._player.has_previous() and self._player.get_position() < 3000:
self._player.previous()
else:
self._player.seek(0)
def _next(self) -> None:
self._player.skip()
@@ -2214,6 +2262,7 @@ class TunettiWindow(QMainWindow):
self.player.playback_state_changed.connect(self._on_playback_state_changed)
self.player.error.connect(self._on_player_error)
self.player.seeked.connect(self._on_player_seeked)
self.player.song_loaded.connect(self._on_song_loaded)
# ── Visualizer audio buffer input ──
# Connect the player's audio buffer output to our visualizer
@@ -2714,6 +2763,10 @@ class TunettiWindow(QMainWindow):
log.error("Player error: %s", err.get("error", "unknown"))
self._playback.show_error(err.get("error", "Playback error"))
@Slot(bool)
def _on_song_loaded(self, loaded: bool) -> None:
self._playback.set_buttons_enabled(loaded)
@Slot(int)
def _on_player_seeked(self, position_ms: int) -> None:
"""Recalculate Discord RPC start timestamp after a seek."""