diff --git a/pkg/launcher/commands.go b/pkg/launcher/commands.go index 88b0f8d6..0a37e817 100644 --- a/pkg/launcher/commands.go +++ b/pkg/launcher/commands.go @@ -26,6 +26,7 @@ import ( "github.com/wizzomafizzo/tapto/pkg/service/tokens" "net/url" "os" + "os/exec" "path/filepath" "strings" @@ -57,6 +58,7 @@ var commandMappings = map[string]func(platforms.Platform, platforms.CmdEnv) erro "mister.core": forwardCmd, "mister.script": forwardCmd, "mister.mgl": forwardCmd, + "mister.video": cmdMisterVideo, "http.get": cmdHttpGet, "http.post": cmdHttpPost, @@ -218,3 +220,24 @@ func LaunchToken( CurrentIndex: currentIndex, }), true } + +func cmdMisterVideo(pl platforms.Platform, env platforms.CmdEnv) error { + if len(env.Args) == 0 { + return fmt.Errorf("URL argument missing for mister.video command") + } + + videoURL := env.Args + log.Info().Msgf("Playing video from URL: %s", videoURL) + + cmd := exec.Command("tmp/tapto/vplay.sh", videoURL) + + output, err := cmd.CombinedOutput() + if err != nil { + return fmt.Errorf("error playing video: %v\nOutput: %s", err, output) + } + + log.Info().Msg("Video playing successfully") + return nil +} + + diff --git a/pkg/platforms/mister/config.go b/pkg/platforms/mister/config.go index 8fc6b201..c58a5431 100644 --- a/pkg/platforms/mister/config.go +++ b/pkg/platforms/mister/config.go @@ -15,6 +15,7 @@ const ( FailSoundFile = TempFolder + "/fail.wav" SocketFile = TempFolder + "/tapto.sock" PidFile = TempFolder + "/tapto.pid" + vplayFilePath = TempFolder + "/vplay.sh" MappingsFile = "/media/fat/nfc.csv" TokenReadFile = "/tmp/TOKENREAD" ConfigFolder = mrextConfig.ScriptsConfigFolder + "/tapto" @@ -24,6 +25,94 @@ const ( ArcadeDbFile = ConfigFolder + "/ArcadeDatabase.csv" ScriptsFolder = mrextConfig.ScriptsFolder CmdInterface = "/dev/MiSTer_cmd" + vplayContent = `#!/bin/bash + +declare -g crtmode_640="video_mode=640,16,64,80,240,1,3,14,12380" +declare -g crtmode_320="video_mode=320,-16,32,32,240,1,3,13,5670" + +# Read the contents of the INI file +declare -g ini_file="/media/fat/MiSTer.ini" +declare -g ini_contents=$(cat "$ini_file") + +declare -g branch="main" +declare -g repository_url="https://github.com/mrchrisster/MiSTer_SAM" + +function curl_download() { # curl_download ${filepath} ${URL} + + curl \ + --connect-timeout 15 --max-time 600 --retry 3 --retry-delay 5 --silent --show-error \ + --insecure \ + --fail \ + --location \ + -o "${1}" \ + "${2}" +} + +function get_mplayer() { + echo " Downloading wizzo's mplayer for SAM..." + echo " Created for MiSTer by wizzo" + echo " https://github.com/wizzomafizzo/mrext" + latest_mplayer="${repository_url}/blob/${branch}/.MiSTer_SAM/mplayer.zip?raw=true" + latest_mbc="${repository_url}/blob/${branch}/.MiSTer_SAM/mbc?raw=true" + curl_download "/tmp/tapto/mplayer.zip" "${latest_mplayer}" + curl_download "/tmp/tapto/mbc" "${latest_mbc}" + unzip -ojq /tmp/tapto/mplayer.zip -d "/tmp/tapto" + chmod +x /tmp/tapto/mplayer + chmod +x /tmp/tapto/mbc + rm /tmp/tapto/mplayer.zip + echo " Done." +} + +if [ ! -f /tmp/tapto/mplayer ]; then + get_mplayer +fi + +function mplayer() { + LD_LIBRARY_PATH=/tmp/tapto /tmp/tapto/mplayer "$@" +} + +url=$1 + +res="$(mplayer -vo null -ao null -identify -frames 0 $url | grep "VIDEO:" | awk '{print $3}')" +res_comma=$(echo "$res" | tr 'x' ',') +res_space=$(echo "$res" | tr 'x' ' ') + +function change_menures() { +# Backup mister.ini +if [ -f "$ini_file" ]; then + cp "$ini_file" "${ini_file}".vpl +else + touch "$ini_file" +fi + +#append menu info +echo -e "\n[menu]" >> "$ini_file" +echo -e "$crtmode_320" >> "$ini_file" +echo "[menu] entry created." + +# Replace video_mode if it exists within [menu] entry +if [[ $ini_contents =~ \[menu\].*video_mode=([^,[:space:]]+) ]]; then + awk -v res_comma="$res_comma" '/\[menu\]/{p=1} p&&/video_mode/{sub(/=.*/, "="res_comma",60"); p=0} 1' "$ini_file" > "$ini_file.tmp" && mv "$ini_file.tmp" "$ini_file" + echo "video_mode replaced in [menu] entry." +fi +} + +## Play video +change_menures +echo load_core /media/fat/menu.rbf > /dev/MiSTer_cmd +sleep 2 +# open mister terminal +/media/fat/Scripts/.MiSTer_SAM/mbc raw_seq :43 +chvt 2 +vmode -r ${res_space} rgb32 +sleep 2 +mplayer -cache 8192 "$url" +cp "$ini_file.vpl" "$ini_file" +echo load_core /media/fat/menu.rbf > /dev/MiSTer_cmd +` + + + ) func UserConfigToMrext(cfg *config.UserConfig) *mrextConfig.UserConfig { diff --git a/pkg/platforms/mister/methods.go b/pkg/platforms/mister/methods.go index d1dbb1c0..afb1fa71 100644 --- a/pkg/platforms/mister/methods.go +++ b/pkg/platforms/mister/methods.go @@ -43,6 +43,25 @@ func Setup(tr *Tracker) error { } _ = ff.Close() + vplayFile, err := os.Create(vplayFilePath) + if err != nil { + log.Error().Msgf("error creating vplay.sh file: %s", err) + return err + } + + _, err = vplayFile.WriteString(vplayContent) + if err != nil { + log.Error().Msgf("error writing to vplay.sh file: %s", err) + return err + } + _ = vplayFile.Close() + + err = os.Chmod(vplayFilePath, 0755) + if err != nil { + log.Error().Msgf("error setting executable permissions for vplay.sh: %s", err) + return err + } + // attempt arcadedb update go func() { haveInternet := utils.WaitForInternet(30) diff --git a/pkg/service/readers.go b/pkg/service/readers.go index a9ee86d5..81721d99 100644 --- a/pkg/service/readers.go +++ b/pkg/service/readers.go @@ -5,6 +5,7 @@ import ( "github.com/wizzomafizzo/tapto/pkg/service/tokens" "strings" "time" + "os/exec" "github.com/rs/zerolog/log" "github.com/wizzomafizzo/tapto/pkg/config" @@ -125,6 +126,39 @@ func connectReaders( return nil } +func stopMPlayer() { + psCmd := exec.Command("sh", "-c", "ps aux | grep mplayer | grep -v grep") + output, err := psCmd.Output() + if err != nil { + log.Info().Msgf("mplayer processes not detected.") + return + } + + lines := strings.Split(string(output), "\n") + for _, line := range lines { + if line == "" { + continue + } + + log.Debug().Msgf("Processing line: %s", line) + + fields := strings.Fields(line) + if len(fields) < 2 { + log.Warn().Msgf("Unexpected line format: %s", line) + continue + } + + pid := fields[0] + log.Info().Msgf("Killing mplayer process with PID: %s", pid) + + killCmd := exec.Command("kill", "-9", pid) + if err := killCmd.Run(); err != nil { + log.Error().Msgf("Failed to kill process %s: %v", pid, err) + } + } +} + + func readerManager( pl platforms.Platform, cfg *config.UserConfig, @@ -270,6 +304,7 @@ func readerManager( } else { log.Info().Msg("token was removed") st.SetActiveCard(tokens.Token{}) + stopMPlayer() if shouldExit(cfg, pl, st) { startTimedExit() }