134 lines
3.4 KiB
Bash
Executable File
134 lines
3.4 KiB
Bash
Executable File
#!/bin/sh
|
|
set -eu
|
|
|
|
PROG="$(basename "${0}")"
|
|
SOCKET_PATH="/tmp/mpv-${USER}.sock"
|
|
|
|
die() {
|
|
echo "Error: $*" >&2
|
|
exit 1
|
|
}
|
|
|
|
usage() {
|
|
cat <<EOF
|
|
Usage: ${PROG} <command> [args]
|
|
|
|
Commands:
|
|
radio <CHANNEL> Switch to a radio station
|
|
local, music [PATH] Switch to local music playlist (default: ~/Music)
|
|
next, n Next track
|
|
prev, p Previous track
|
|
pause, stop, toggle, s Toggle pause
|
|
help Show this message
|
|
|
|
Radio Channels:
|
|
lofi, fallout, wasteland, retrofm, rusradio, rock, phonk, dorognoe
|
|
EOF
|
|
}
|
|
|
|
get_radio_url() {
|
|
channel="${1:-}"
|
|
case "${channel}" in
|
|
lofi) echo 'https://radiorecord.hostingradio.ru/lofi96.aacp' ;;
|
|
fallout) echo 'http://fallout.fm:8000/falloutfm1.ogg' ;;
|
|
wasteland) echo 'http://wasteland.su:8080/radio' ;;
|
|
retrofm) echo 'http://hls-01-retro.emgsound.ru/12/128/playlist.m3u8' ;;
|
|
rusradio) echo 'https://rusradio.hostingradio.ru/rusradio128.mp3' ;;
|
|
rock) echo 'https://radiorecord.hostingradio.ru/rock96.aacp' ;;
|
|
phonk) echo 'https://radiorecord.hostingradio.ru/phonk96.aacp' ;;
|
|
dorognoe) echo 'https://dorognoe.hostingradio.ru:8000/dorognoe' ;;
|
|
*) die "Unknown radio channel '${channel}'. Available: lofi/fallout/wasteland/retrofm/rusradio/rock/phonk/dorognoe" ;;
|
|
esac
|
|
}
|
|
|
|
send_cmd() {
|
|
if [ ! -S "${SOCKET_PATH}" ]; then
|
|
die "MPV socket not found at '${SOCKET_PATH}'. Is mpv running?"
|
|
fi
|
|
|
|
printf '{ "command": %s }\n' "${1}" | socat - "${SOCKET_PATH}" >/dev/null
|
|
}
|
|
|
|
tune_radio() {
|
|
channel="${1:-}"
|
|
if [ -z "${channel}" ]; then
|
|
die "Radio channel required. Usage: ${PROG} radio <channel>"
|
|
fi
|
|
|
|
url="$(get_radio_url "${channel}")"
|
|
send_cmd "[\"loadfile\", \"${url}\", \"replace\"]"
|
|
echo "📻 Switched to radio: ${channel}"
|
|
}
|
|
|
|
play_local_playlist() {
|
|
playlist_path="${1:-${HOME}/Music}"
|
|
|
|
if [ ! -e "${playlist_path}" ]; then
|
|
die "Path not found: ${playlist_path}"
|
|
fi
|
|
|
|
if command -v realpath >/dev/null 2>&1; then
|
|
playlist_path="$(realpath "${playlist_path}")"
|
|
fi
|
|
|
|
escaped_path=$(printf '%s' "${playlist_path}" | sed 's/\\/\\\\/g; s/"/\\"/g')
|
|
send_cmd '["set", "pause", "yes"]'
|
|
sleep 0.1
|
|
send_cmd "[\"loadfile\", \"${escaped_path}\", \"replace\"]"
|
|
sleep 0.1
|
|
send_cmd '["set", "pause", "yes"]'
|
|
sleep 0.1
|
|
send_cmd '["playlist-shuffle"]'
|
|
sleep 0.1
|
|
send_cmd '["playlist-next"]'
|
|
sleep 0.1
|
|
send_cmd '["set", "pause", "no"]'
|
|
|
|
echo "🎵 Switched to local playlist: ${playlist_path}"
|
|
}
|
|
|
|
handle_control() {
|
|
action="${1}"
|
|
case "${action}" in
|
|
next|n)
|
|
send_cmd '["playlist-next"]'
|
|
echo "➡️ Next"
|
|
;;
|
|
prev|p)
|
|
send_cmd '["playlist-prev"]'
|
|
echo "⬅️ Prev"
|
|
;;
|
|
pause|stop|toggle|t|s)
|
|
send_cmd '["cycle", "pause"]'
|
|
echo "⏯️ Pause toggled"
|
|
;;
|
|
*)
|
|
usage
|
|
exit 1
|
|
;;
|
|
esac
|
|
}
|
|
|
|
ACTION="${1:-}"
|
|
shift 2>/dev/null || true
|
|
|
|
case "${ACTION}" in
|
|
radio|tune)
|
|
tune_radio "$@"
|
|
;;
|
|
local|music|m)
|
|
play_local_playlist "$@"
|
|
;;
|
|
next|n|prev|p|pause|stop|toggle|t|s)
|
|
handle_control "${ACTION}"
|
|
;;
|
|
help|"")
|
|
usage
|
|
;;
|
|
*)
|
|
echo "Unknown command: ${ACTION}" >&2
|
|
usage
|
|
exit 1
|
|
;;
|
|
esac
|