#!/usr/bin/env lua

local launcher = "dmenu"

local dmenu_args = {
    "-i",
    "-fn", "JetBrainsMono Nerd Font-10",
    "-nb", "#121212",
    "-nf", "#e0e0e0",
    "-sb", "#222222",
    "-sf", "#e0e0e0",
    "-l", "10",
}

local music_dir = "/home/coast/Music"
local max_length = 30
local default_icon = "/usr/share/icons/hicolor/48x48/apps/musical-note.png"

local function build_menu(prompt)
    if launcher == "rofi" then
        return string.format("rofi -dmenu -i -p '%s'", prompt)
    else
        local args = "dmenu"
        for _, v in ipairs(dmenu_args) do
            args = args .. " '" .. v .. "'"
        end
        args = args .. string.format(" -p '%s'", prompt)
        return args
    end
end

local function escape(str)
    return str:gsub("'", "'\\''")
end

local function capture(cmd)
    local f = io.popen(cmd, 'r')
    local s = f:read('*a')
    f:close()
    return s:gsub("^%s*(.-)%s*$", "%1")
end

local function truncate(str, len)
    if #str > len then
        return str:sub(1, len) .. "..."
    end
    return str
end

local function get_cover(song_file)
    if not song_file or song_file == "" then return default_icon end
    local full_path = music_dir .. "/" .. song_file
    local dir = full_path:match("(.*[/\\])") or music_dir
    local names = {"cover.jpg", "cover.png", "folder.jpg", "folder.png", "front.jpg", "front.png"}
    for _, name in ipairs(names) do
        local path = dir .. name
        local f = io.open(path, "r")
        if f then
            f:close()
            return path
        end
    end
    return default_icon
end

local action = arg[1]

if action == "shuf" then
    os.execute("mpc random on >/dev/null && notify-send 'Shuffle enabled'")
    os.exit(0)
elseif action == "shufno" then
    os.execute("mpc random off >/dev/null && notify-send 'Shuffle disabled'")
    os.exit(0)
elseif action == "next" then
    os.execute("mpc next >/dev/null")
    os.exit(0)
elseif action == "prev" then
    os.execute("mpc prev >/dev/null")
    os.exit(0)
elseif action == "toggle" then
    os.execute("mpc toggle >/dev/null")
    os.exit(0)
elseif action == "current" then
    local current = capture("mpc current")
    if current ~= "" then io.write(current .. "\n") end
    os.exit(0)
elseif action == "info" then
    local file = capture("mpc --format '%file%' current")
    local title = capture("mpc current")
    local cover = get_cover(file)
    os.execute(string.format("notify-send 'Currently Playing' '%s' -i '%s'", escape(title), cover))
    os.exit(0)
elseif action == "album" then
    local album = capture("mpc list album | " .. build_menu("Select Album"))
    if album ~= "" then
        os.execute(string.format("mpc clear >/dev/null && mpc find album '%s' | mpc add && mpc play >/dev/null", escape(album)))
    end
    os.exit(0)
elseif action == "artist" then
    local artist = capture("mpc list artist | " .. build_menu("Select Artist"))
    if artist ~= "" then
        os.execute(string.format("mpc clear >/dev/null && mpc find artist '%s' | mpc add && mpc play >/dev/null", escape(artist)))
    end
    os.exit(0)
elseif action == "search" then
    local menu = "mpc --format '%title% - %artist% - %album%\t%file%' search any '' | " .. build_menu("Search music")
    local choice = capture(menu)
    if choice == "" then os.exit(0) end
    local file = choice:match("\t(.-)$")
    if file then
        os.execute(string.format("mpc clear >/dev/null && mpc add '%s' >/dev/null && mpc play >/dev/null", escape(file)))
        os.exit(0)
    end
elseif action == "reload" then
    os.execute("mpc update && mpc clear && mpc add / && mpc play >/dev/null")
    os.execute("notify-send 'Library refreshed. Now playing...'")
    os.exit(0)
end

os.execute("mpc play >/dev/null 2>&1")
os.execute("mpc volume 15 >/dev/null 2>&1")
local file = capture("mpc --format '%file%' current")
local title = capture("mpc current")
local cover = get_cover(file)
local display = truncate(title, max_length)
os.execute(string.format("notify-send 'Now playing...' '%s' -i '%s'", escape(display), cover))
