diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index e72fc180..013825f0 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -140,12 +140,13 @@ jobs:
env:
GROUT_VERSION: ${{ needs.prepare.outputs.version }}
- - name: Package Batocera AMD64
- run: task package:batocera-amd64
+ - name: Package AMD64 platforms
+ run: task package:batocera-amd64 package:esde
- - name: Create distribution
+ - name: Create distributions
run: |
- cd dist/Batocera-amd64 && zip -r ../Grout-Batocera-amd64.zip Grout.sh Grout
+ cd dist/Batocera-amd64 && zip -r ../Grout-Batocera-amd64.zip Grout.sh Grout && cd ../..
+ cd dist/ESDE && zip -r ../Grout-ESDE.zip Grout.sh Grout && cd ../..
- name: Upload artifacts
uses: actions/upload-artifact@v4
@@ -153,6 +154,7 @@ jobs:
name: amd64-artifacts
path: |
dist/Grout-Batocera-amd64.zip
+ dist/Grout-ESDE.zip
build-x86:
needs: prepare
@@ -306,6 +308,7 @@ jobs:
**/Grout-Batocera-arm64.zip
**/Grout-Batocera-x86.zip
**/Grout-Batocera-amd64.zip
+ **/Grout-ESDE.zip
**/grout
draft: false
prerelease: ${{ inputs.beta }}
@@ -383,6 +386,7 @@ jobs:
"Grout-Batocera-arm64.zip"
"Grout-Batocera-amd64.zip"
"Grout-Batocera-x86.zip"
+ "Grout-ESDE.zip"
)
# Build the assets JSON object
diff --git a/README.md b/README.md
index 248c16c2..14cb2d82 100644
--- a/README.md
+++ b/README.md
@@ -9,7 +9,7 @@
A RomM Client for your retro doo-dad.
-[Allium][allium] · [Batocera][batocera] · [Knulli][knulli] · [Koriki][koriki] · [MinUI][minui] · [muOS][muos] · [NextUI][nextui] · [Onion][onion] · [ROCKNIX][rocknix] · [Spruce][spruce] · [SprigUI][sprigui] · [TwigUI][twigui] · [TrimUI][trimui]
+[Allium][allium] · [Batocera][batocera] · [EmuDeck / ES-DE][emudeck] · [Knulli][knulli] · [Koriki][koriki] · [MinUI][minui] · [muOS][muos] · [NextUI][nextui] · [Onion][onion] · [ROCKNIX][rocknix] · [Spruce][spruce] · [SprigUI][sprigui] · [TwigUI][twigui] · [TrimUI][trimui]
@@ -88,6 +88,8 @@ If you enjoy using Grout and feel inclined to pay it forward, go do something ni
[allium]: https://github.com/goweiwen/Allium
[batocera]: https://batocera.org
+[emudeck]: https://www.emudeck.com
+[es-de]: https://es-de.org
[knulli]: https://knulli.org
[koriki]: https://github.com/Rparadise-Team/Koriki
[minui]: https://github.com/shauninman/MinUI
diff --git a/app/setup.go b/app/setup.go
index a09d4154..18dbf891 100644
--- a/app/setup.go
+++ b/app/setup.go
@@ -21,12 +21,14 @@ import (
"log/slog"
"os"
"path/filepath"
+ "strings"
"time"
gaba "github.com/BrandonKowalski/gabagool/v2/pkg/gabagool"
buttons "github.com/BrandonKowalski/gabagool/v2/pkg/gabagool/constants"
"github.com/BrandonKowalski/gabagool/v2/pkg/gabagool/i18n"
goi18n "github.com/nicksnyder/go-i18n/v2/i18n"
+ "github.com/veandco/go-sdl2/sdl"
)
type SetupResult struct {
@@ -58,6 +60,24 @@ func setup() SetupResult {
}
}
+func isSteamDeckHardware() bool {
+ for _, path := range []string{
+ "/sys/class/dmi/id/product_name",
+ "/sys/class/dmi/id/product_version",
+ "/sys/class/dmi/id/board_name",
+ } {
+ data, err := os.ReadFile(path)
+ if err != nil {
+ continue
+ }
+ value := strings.ToLower(strings.TrimSpace(string(data)))
+ if strings.Contains(value, "steam deck") || strings.Contains(value, "jupiter") || strings.Contains(value, "galileo") {
+ return true
+ }
+ }
+ return false
+}
+
func setupInputMapping(currentCFW cfw.CFW) {
cwd, err := os.Getwd()
if err != nil {
@@ -126,6 +146,14 @@ func initFramework(currentCFW cfw.CFW) {
}
gaba.Init(gabaOptions)
+ if currentCFW == cfw.ESDE || isSteamDeckHardware() {
+ // Steam Deck/Steam Input can emit continuous tiny analog-stick motion events,
+ // which flood SDL's event queue and make button input appear delayed or jittery.
+ // D-pad/buttons are sufficient for Grout navigation, so drop axis motion events.
+ sdl.EventState(sdl.CONTROLLERAXISMOTION, sdl.IGNORE)
+ sdl.EventState(sdl.JOYAXISMOTION, sdl.IGNORE)
+ }
+
gaba.RegisterChord("unlock-kid-mode", []buttons.VirtualButton{
buttons.VirtualButtonL1,
buttons.VirtualButtonR1,
diff --git a/cfw/cfw.go b/cfw/cfw.go
index b45cde6e..320cc90a 100644
--- a/cfw/cfw.go
+++ b/cfw/cfw.go
@@ -19,6 +19,7 @@ const (
Onion CFW = "ONION"
Koriki CFW = "KORIKI"
Batocera CFW = "BATOCERA"
+ ESDE CFW = "ESDE"
MinUI CFW = "MINUI"
)
@@ -27,18 +28,18 @@ func GetCFW() CFW {
cfw := CFW(cfwEnv)
switch cfw {
- case MuOS, NextUI, Knulli, Spruce, ROCKNIX, Trimui, Allium, Onion, Koriki, Batocera, MinUI:
+ case MuOS, NextUI, Knulli, Spruce, ROCKNIX, Trimui, Allium, Onion, Koriki, Batocera, ESDE, MinUI:
return cfw
default:
log.SetOutput(os.Stderr)
- log.Fatalf("Unsupported CFW: '%s'. Valid options: NextUI, muOS, Knulli, Spruce, ROCKNIX, Trimui, Allium, Onion, Koriki, Batocera, MinUI", cfwEnv)
+ log.Fatalf("Unsupported CFW: '%s'. Valid options: NextUI, muOS, Knulli, Spruce, ROCKNIX, Trimui, Allium, Onion, Koriki, Batocera, ESDE, MinUI", cfwEnv)
return ""
}
}
func (c CFW) IsBasedOnEmulationStation() bool {
switch c {
- case Knulli, ROCKNIX, Batocera:
+ case Knulli, ROCKNIX, Batocera, ESDE:
return true
default:
return false
diff --git a/cfw/directories.go b/cfw/directories.go
index 5d648670..b78dad8c 100644
--- a/cfw/directories.go
+++ b/cfw/directories.go
@@ -3,6 +3,7 @@ package cfw
import (
"grout/cfw/allium"
"grout/cfw/batocera"
+ "grout/cfw/esde"
"grout/cfw/knulli"
"grout/cfw/koriki"
"grout/cfw/minui"
@@ -38,6 +39,8 @@ func GetRomDirectory() string {
return koriki.GetRomDirectory()
case Batocera:
return batocera.GetRomDirectory()
+ case ESDE:
+ return esde.GetRomDirectory()
case MinUI:
return minui.GetRomDirectory()
}
@@ -79,6 +82,8 @@ func GetBIOSDirectory() string {
return koriki.GetBIOSDirectory()
case Batocera:
return batocera.GetBIOSDirectory()
+ case ESDE:
+ return esde.GetBIOSDirectory()
case MinUI:
return minui.GetBIOSDirectory()
}
@@ -130,6 +135,8 @@ func GetArtDirectory(romDir string, platformFSSlug, platformName string) string
return koriki.GetArtDirectory(romDir)
case Batocera:
return batocera.GetArtDirectory(romDir)
+ case ESDE:
+ return esde.GetArtDirectory(romDir)
case MinUI:
return minui.GetArtDirectory(romDir)
default:
@@ -178,6 +185,8 @@ func BaseSavePath() string {
return koriki.GetBaseSavePath()
case Batocera:
return batocera.GetBaseSavePath()
+ case ESDE:
+ return esde.GetBaseSavePath()
case MinUI:
return minui.GetBaseSavePath()
}
@@ -192,6 +201,8 @@ func GetArtMarqueeDirectory(romDir string, platformFSSlug, platformName string)
return knulli.GetArtDirectory(romDir)
case Batocera:
return batocera.GetArtDirectory(romDir)
+ case ESDE:
+ return esde.GetArtDirectory(romDir)
default:
return ""
}
@@ -205,6 +216,8 @@ func GetArtVideoDirectory(romDir string, platformFSSlug, platformName string) st
return knulli.GetVideoDirectory(romDir)
case Batocera:
return batocera.GetVideoDirectory(romDir)
+ case ESDE:
+ return esde.GetVideoDirectory(romDir)
default:
return ""
@@ -219,6 +232,8 @@ func GetArtThumbnailDirectory(romDir string, platformFSSlug, platformName string
return knulli.GetArtDirectory(romDir)
case Batocera:
return knulli.GetArtDirectory(romDir)
+ case ESDE:
+ return esde.GetArtDirectory(romDir)
default:
return ""
}
@@ -232,6 +247,8 @@ func GetArtBezelDirectory(romDir string, platformFSSlug, platformName string) st
return knulli.GetBezelDirectory(romDir)
case Batocera:
return batocera.GetBezelDirectory(romDir)
+ case ESDE:
+ return esde.GetBezelDirectory(romDir)
default:
return ""
}
@@ -245,6 +262,8 @@ func GetManualDirectory(romDir string, platformFSSlug, platformName string) stri
return knulli.GetManualDirectory(romDir)
case Batocera:
return batocera.GetManualDirectory(romDir)
+ case ESDE:
+ return esde.GetManualDirectory(romDir)
default:
return ""
}
@@ -258,6 +277,8 @@ func GetBoxbackDirectory(romDir string, platformFSSlug, platformName string) str
return knulli.GetArtDirectory(romDir)
case Batocera:
return batocera.GetArtDirectory(romDir)
+ case ESDE:
+ return esde.GetArtDirectory(romDir)
default:
return ""
}
@@ -271,6 +292,8 @@ func GetFanartDirectory(romDir string, platformFSSlug, platformName string) stri
return knulli.GetArtDirectory(romDir)
case Batocera:
return batocera.GetArtDirectory(romDir)
+ case ESDE:
+ return esde.GetArtDirectory(romDir)
default:
return ""
}
diff --git a/cfw/esde/data/platforms.json b/cfw/esde/data/platforms.json
new file mode 100644
index 00000000..b7031d62
--- /dev/null
+++ b/cfw/esde/data/platforms.json
@@ -0,0 +1,265 @@
+{
+ "3do": [
+ "3do"
+ ],
+ "3ds": [
+ "n3ds",
+ "3ds"
+ ],
+ "acpc": [
+ "amstradcpc"
+ ],
+ "amiga": [
+ "amiga",
+ "amigacd32"
+ ],
+ "arcade": [
+ "arcade",
+ "mame",
+ "fbneo",
+ "neogeo"
+ ],
+ "arduboy": [
+ "arduboy"
+ ],
+ "atari-st": [
+ "atarist"
+ ],
+ "atari2600": [
+ "atari2600"
+ ],
+ "atari5200": [
+ "atari5200"
+ ],
+ "atari7800": [
+ "atari7800"
+ ],
+ "atari800": [
+ "atari800"
+ ],
+ "c128": [
+ "c128"
+ ],
+ "c16": [
+ "c16"
+ ],
+ "c64": [
+ "c64"
+ ],
+ "cave-story": [
+ "cavestory"
+ ],
+ "colecovision": [
+ "colecovision"
+ ],
+ "cpet": [
+ "pet"
+ ],
+ "dc": [
+ "dreamcast"
+ ],
+ "dos": [
+ "dos"
+ ],
+ "fairchild-channel-f": [
+ "channelf"
+ ],
+ "famicom": [
+ "famicom",
+ "nes"
+ ],
+ "fds": [
+ "fds"
+ ],
+ "g-and-w": [
+ "gameandwatch"
+ ],
+ "galaksija": [],
+ "gamegear": [
+ "gamegear"
+ ],
+ "gb": [
+ "gb"
+ ],
+ "gba": [
+ "gba"
+ ],
+ "gbc": [
+ "gbc"
+ ],
+ "genesis": [
+ "genesis",
+ "megadrive"
+ ],
+ "intellivision": [
+ "intellivision"
+ ],
+ "j2me": [
+ "j2me"
+ ],
+ "jaguar": [
+ "atarijaguar",
+ "jaguar"
+ ],
+ "lynx": [
+ "atarilynx",
+ "lynx"
+ ],
+ "mega-duck-slash-cougar-boy": [
+ "megaduck"
+ ],
+ "msx": [
+ "msx",
+ "msx1",
+ "msx2",
+ "msx2plus",
+ "msxturbor"
+ ],
+ "n64": [
+ "n64"
+ ],
+ "nds": [
+ "nds"
+ ],
+ "neo-geo-cd": [
+ "neogeocd"
+ ],
+ "neo-geo-pocket": [
+ "ngp"
+ ],
+ "neo-geo-pocket-color": [
+ "ngpc"
+ ],
+ "neogeoaes": [
+ "neogeo"
+ ],
+ "neogeomvs": [
+ "neogeo"
+ ],
+ "nes": [
+ "nes"
+ ],
+ "ngc": [
+ "gc",
+ "gamecube"
+ ],
+ "odyssey": [
+ "odyssey2",
+ "videopac"
+ ],
+ "openbor": [
+ "openbor"
+ ],
+ "pc-8000": [
+ "pc88"
+ ],
+ "pc-9800-series": [
+ "pc98"
+ ],
+ "pc-fx": [
+ "pcfx"
+ ],
+ "philips-cd-i": [
+ "cdi"
+ ],
+ "pico": [
+ "pico8"
+ ],
+ "pico-8": [
+ "pico8"
+ ],
+ "pokemon-mini": [
+ "pokemini"
+ ],
+ "ps2": [
+ "ps2"
+ ],
+ "ps3": [
+ "ps3"
+ ],
+ "psp": [
+ "psp"
+ ],
+ "psx": [
+ "psx",
+ "ps1"
+ ],
+ "saturn": [
+ "saturn"
+ ],
+ "sega32": [
+ "sega32x"
+ ],
+ "segacd": [
+ "segacd"
+ ],
+ "sfam": [
+ "snes"
+ ],
+ "sg1000": [
+ "sg-1000",
+ "sg1000"
+ ],
+ "sharp-x68000": [
+ "x68000"
+ ],
+ "sms": [
+ "mastersystem"
+ ],
+ "snes": [
+ "snes"
+ ],
+ "supergrafx": [
+ "supergrafx"
+ ],
+ "supervision": [
+ "supervision"
+ ],
+ "tg16": [
+ "pcengine",
+ "tg16"
+ ],
+ "tic-80": [
+ "tic80"
+ ],
+ "turbografx-cd": [
+ "pcenginecd",
+ "tg-cd"
+ ],
+ "vectrex": [
+ "vectrex"
+ ],
+ "vic-20": [
+ "vic20",
+ "c20"
+ ],
+ "videopac": [
+ "videopac"
+ ],
+ "virtualboy": [
+ "virtualboy"
+ ],
+ "wii": [
+ "wii"
+ ],
+ "wiiu": [
+ "wiiu"
+ ],
+ "wonderswan": [
+ "wonderswan",
+ "wswan"
+ ],
+ "wonderswan-color": [
+ "wonderswancolor",
+ "wswanc"
+ ],
+ "x1": [
+ "x1"
+ ],
+ "zx81": [
+ "zx81"
+ ],
+ "zxs": [
+ "zxspectrum"
+ ]
+}
diff --git a/cfw/esde/data/save_directories.json b/cfw/esde/data/save_directories.json
new file mode 100644
index 00000000..b772cbe5
--- /dev/null
+++ b/cfw/esde/data/save_directories.json
@@ -0,0 +1,200 @@
+{
+ "3do": [
+ "retroarch/saves"
+ ],
+ "acpc": [
+ "retroarch/saves"
+ ],
+ "arcade": [
+ "retroarch/saves"
+ ],
+ "atari-st": [
+ "retroarch/saves"
+ ],
+ "atari2600": [
+ "retroarch/saves"
+ ],
+ "atari5200": [
+ "retroarch/saves"
+ ],
+ "atari7800": [
+ "retroarch/saves"
+ ],
+ "atari800": [
+ "retroarch/saves"
+ ],
+ "c128": [
+ "retroarch/saves"
+ ],
+ "c16": [
+ "retroarch/saves"
+ ],
+ "c64": [
+ "retroarch/saves"
+ ],
+ "colecovision": [
+ "retroarch/saves"
+ ],
+ "cpet": [
+ "retroarch/saves"
+ ],
+ "fairchild-channel-f": [
+ "retroarch/saves"
+ ],
+ "famicom": [
+ "retroarch/saves"
+ ],
+ "fds": [
+ "retroarch/saves"
+ ],
+ "gamegear": [
+ "retroarch/saves"
+ ],
+ "gb": [
+ "retroarch/saves"
+ ],
+ "gba": [
+ "retroarch/saves"
+ ],
+ "gbc": [
+ "retroarch/saves"
+ ],
+ "genesis": [
+ "retroarch/saves"
+ ],
+ "intellivision": [
+ "retroarch/saves"
+ ],
+ "jaguar": [
+ "retroarch/saves"
+ ],
+ "lynx": [
+ "retroarch/saves"
+ ],
+ "msx": [
+ "retroarch/saves"
+ ],
+ "n64": [
+ "retroarch/saves"
+ ],
+ "nds": [
+ "retroarch/saves"
+ ],
+ "neo-geo-cd": [
+ "retroarch/saves"
+ ],
+ "neo-geo-pocket": [
+ "retroarch/saves"
+ ],
+ "neo-geo-pocket-color": [
+ "retroarch/saves"
+ ],
+ "neogeoaes": [
+ "retroarch/saves"
+ ],
+ "neogeomvs": [
+ "retroarch/saves"
+ ],
+ "nes": [
+ "retroarch/saves"
+ ],
+ "odyssey": [
+ "retroarch/saves"
+ ],
+ "pc-8000": [
+ "retroarch/saves"
+ ],
+ "pc-9800-series": [
+ "retroarch/saves"
+ ],
+ "pc-fx": [
+ "retroarch/saves"
+ ],
+ "pico": [
+ "retroarch/saves"
+ ],
+ "pico-8": [
+ "retroarch/saves"
+ ],
+ "pokemon-mini": [
+ "retroarch/saves"
+ ],
+ "psx": [
+ "retroarch/saves"
+ ],
+ "saturn": [
+ "retroarch/saves"
+ ],
+ "sega32": [
+ "retroarch/saves"
+ ],
+ "segacd": [
+ "retroarch/saves"
+ ],
+ "sfam": [
+ "retroarch/saves"
+ ],
+ "sg1000": [
+ "retroarch/saves"
+ ],
+ "sharp-x68000": [
+ "retroarch/saves"
+ ],
+ "sms": [
+ "retroarch/saves"
+ ],
+ "snes": [
+ "retroarch/saves"
+ ],
+ "supergrafx": [
+ "retroarch/saves"
+ ],
+ "supervision": [
+ "retroarch/saves"
+ ],
+ "tg16": [
+ "retroarch/saves"
+ ],
+ "tic-80": [
+ "retroarch/saves"
+ ],
+ "turbografx-cd": [
+ "retroarch/saves"
+ ],
+ "vectrex": [
+ "retroarch/saves"
+ ],
+ "vic-20": [
+ "retroarch/saves"
+ ],
+ "videopac": [
+ "retroarch/saves"
+ ],
+ "virtualboy": [
+ "retroarch/saves"
+ ],
+ "wonderswan": [
+ "retroarch/saves"
+ ],
+ "wonderswan-color": [
+ "retroarch/saves"
+ ],
+ "x1": [
+ "retroarch/saves"
+ ],
+ "zx81": [
+ "retroarch/saves"
+ ],
+ "zxs": [
+ "retroarch/saves"
+ ],
+ "dc": [
+ "flycast"
+ ],
+ "psp": [
+ "ppsspp/PSP/SAVEDATA"
+ ],
+ "3ds": [
+ "citra/sdmc"
+ ]
+}
diff --git a/cfw/esde/esde.go b/cfw/esde/esde.go
new file mode 100644
index 00000000..93804f08
--- /dev/null
+++ b/cfw/esde/esde.go
@@ -0,0 +1,55 @@
+package esde
+
+import (
+ "embed"
+ "grout/internal/jsonutil"
+ "os"
+ "path/filepath"
+)
+
+//go:embed data/*.json
+var embeddedFiles embed.FS
+
+var (
+ Platforms = jsonutil.MustLoadJSONMap[string, []string](embeddedFiles, "data/platforms.json")
+ SaveDirectories = jsonutil.MustLoadJSONMap[string, []string](embeddedFiles, "data/save_directories.json")
+)
+
+func GetBasePath() string {
+ if basePath := os.Getenv("BASE_PATH"); basePath != "" {
+ return basePath
+ }
+ return filepath.Join(os.Getenv("HOME"), "Emulation")
+}
+
+func GetRomDirectory() string {
+ return filepath.Join(GetBasePath(), "roms")
+}
+
+func GetBIOSDirectory() string {
+ return filepath.Join(GetBasePath(), "bios")
+}
+
+func GetBaseSavePath() string {
+ return filepath.Join(GetBasePath(), "saves")
+}
+
+func GetArtDirectory(romDir string) string {
+ return filepath.Join(romDir, "images")
+}
+
+func GetGroutGamelist() string {
+ return filepath.Join(GetRomDirectory(), "ports", "gamelist.xml")
+}
+
+func GetVideoDirectory(romDir string) string {
+ return filepath.Join(romDir, "videos")
+}
+
+func GetBezelDirectory(romDir string) string {
+ return filepath.Join(romDir, "bezels")
+}
+
+func GetManualDirectory(romDir string) string {
+ return filepath.Join(romDir, "manuals")
+}
diff --git a/cfw/metadata.go b/cfw/metadata.go
index de344ca1..bfd4d1ee 100644
--- a/cfw/metadata.go
+++ b/cfw/metadata.go
@@ -2,6 +2,7 @@ package cfw
import (
"grout/cfw/batocera"
+ "grout/cfw/esde"
"grout/cfw/knulli"
"grout/cfw/muos"
"grout/cfw/rocknix"
@@ -26,6 +27,9 @@ func AddGroutToGamelist(c CFW) {
gamelist.AddGroutEntry(rocknix.GetGroutGamelist(), "./Grout.sh")
case Batocera:
gamelist.AddGroutEntry(batocera.GetGroutGamelist(), "./Grout/Grout.sh")
+ case ESDE:
+ gamelist.AddGroutEntry(esde.GetGroutGamelist(), "./Grout.sh")
+ return
default:
return
}
@@ -40,6 +44,10 @@ func FillGamesMetadata(entries []gamelist.RomGameEntry) {
logger.Warn("Failed to add games to ES gamelist.xml", "error", err)
}
scheduleESRestart()
+ case ESDE:
+ if err := gamelist.AddRomGamesToGamelist(entries, gamelist.GameListFileName); err != nil {
+ logger.Warn("Failed to add games to ES-DE gamelist.xml", "error", err)
+ }
case Spruce, Allium, Onion, Koriki:
if err := gamelist.AddRomGamesToGamelist(entries, gamelist.MiyooGameListFileName); err != nil {
logger.Warn("Failed to add games to miyoogamelist.xml", "error", err)
diff --git a/cfw/platforms.go b/cfw/platforms.go
index 82a5b41c..4d9476c2 100644
--- a/cfw/platforms.go
+++ b/cfw/platforms.go
@@ -3,6 +3,7 @@ package cfw
import (
"grout/cfw/allium"
"grout/cfw/batocera"
+ "grout/cfw/esde"
"grout/cfw/knulli"
"grout/cfw/koriki"
"grout/cfw/minui"
@@ -32,6 +33,7 @@ func buildPlatformAliasMap() map[string][]string {
onion.Platforms,
koriki.Platforms,
batocera.Platforms,
+ esde.Platforms,
minui.Platforms,
}
@@ -136,6 +138,8 @@ func GetPlatformMap(c CFW) map[string][]string {
return koriki.Platforms
case Batocera:
return batocera.Platforms
+ case ESDE:
+ return esde.Platforms
case MinUI:
return minui.Platforms
default:
diff --git a/cfw/saves.go b/cfw/saves.go
index 71ecce50..31bc0634 100644
--- a/cfw/saves.go
+++ b/cfw/saves.go
@@ -3,6 +3,7 @@ package cfw
import (
"grout/cfw/allium"
"grout/cfw/batocera"
+ "grout/cfw/esde"
"grout/cfw/knulli"
"grout/cfw/koriki"
"grout/cfw/minui"
@@ -38,6 +39,8 @@ func EmulatorFolderMap(c CFW) map[string][]string {
return trimui.SaveDirectories
case Batocera:
return batocera.Platforms
+ case ESDE:
+ return esde.SaveDirectories
case MinUI:
return minui.SaveDirectories
default:
diff --git a/docs/_includes/cfw-links.md b/docs/_includes/cfw-links.md
index 1fbdf27a..213dc74f 100644
--- a/docs/_includes/cfw-links.md
+++ b/docs/_includes/cfw-links.md
@@ -1,5 +1,7 @@
[allium]: https://github.com/goweiwen/Allium
[batocera]: https://batocera.org
+[emudeck]: https://www.emudeck.com
+[es-de]: https://es-de.org
[knulli]: https://knulli.org
[koriki]: https://github.com/Rparadise-Team/Koriki
[minui]: https://github.com/shauninman/MinUI
diff --git a/docs/contributing/development.md b/docs/contributing/development.md
index 91919ee2..b20ef3b4 100644
--- a/docs/contributing/development.md
+++ b/docs/contributing/development.md
@@ -33,7 +33,7 @@ brew install sdl2 sdl2_image sdl2_ttf sdl2_gfx
- `WINDOW_WIDTH` (optional)
- `WINDOW_HEIGHT` (optional)
- `NITRATES` [true | false] (optional) This is used for Gabagool development debugging
- - `CFW` [MUOS | KNULLI | SPRUCE | NEXTUI] (mandatory), this controls how Grout interacts with and places files
+ - `CFW` [MUOS | KNULLI | SPRUCE | NEXTUI | ESDE] (mandatory), this controls how Grout interacts with and places files
- `BASE_PATH` (mandatory), this acts as the root path like you would have on a handheld (e.g. `/mmc/sdcard` on
muOS). Have the subdirectory structure of this path match the CFW you are working on.
5. Run / Debug `app/grout.go`, making sure to reference the `.env` file in your run configuration.
@@ -93,6 +93,7 @@ After building, you can package for individual platforms:
| `task package-next` | NextUI (TrimUI) | `build/Grout.pak/` |
| `task package-muos` | muOS | `build/muOS/Grout/`, `build/Grout.muxapp` |
| `task package-knulli` | Knulli | `build/Knulli/Grout/` |
+| `task package-esde` | EmuDeck / ES-DE | `dist/ESDE/` |
| `task package-spruce` | Spruce | `build/Spruce/Grout/` |
Each packaging task copies the binary, launch scripts from `scripts//`, shared libraries, and documentation
diff --git a/docs/getting-started/index.md b/docs/getting-started/index.md
index 3751d966..02ba82d4 100644
--- a/docs/getting-started/index.md
+++ b/docs/getting-started/index.md
@@ -7,7 +7,7 @@ Get up and running with Grout in five steps.
Make sure you have:
- A RomM server running and accessible
-- A compatible device running [Allium][allium], [Batocera][batocera], [Knulli][knulli], [muOS][muos], [NextUI][nextui], [Onion][onion], [ROCKNIX][rocknix], [Spruce v4][spruce], or [TrimUI][trimui]
+- A compatible device running [Allium][allium], [Batocera][batocera], [EmuDeck / ES-DE][emudeck], [Knulli][knulli], [muOS][muos], [NextUI][nextui], [Onion][onion], [ROCKNIX][rocknix], [Spruce v4][spruce], or [TrimUI][trimui]
- Your device connected to Wi-Fi
---
@@ -20,6 +20,7 @@ Choose your platform:
- [Allium Installation](install-allium.md)
- [Batocera Installation](install-batocera.md)
+- [EmuDeck / ES-DE Installation](install-emudeck.md)
- [Knulli Installation](install-knulli.md)
- [muOS Installation](install-muos.md)
- [NextUI Installation](install-nextui.md)
diff --git a/docs/getting-started/install-emudeck.md b/docs/getting-started/install-emudeck.md
new file mode 100644
index 00000000..27b25df6
--- /dev/null
+++ b/docs/getting-started/install-emudeck.md
@@ -0,0 +1,54 @@
+# Installation Guide for Steam Deck / EmuDeck ES-DE
+
+This guide will help you install Grout as an ES-DE port on a Steam Deck using [EmuDeck][emudeck].
+
+## Tested Devices
+
+Grout has been tested on the following devices running EmuDeck with ES-DE:
+
+| Manufacturer | Device |
+|--------------|------------|
+| _None yet_ | _Please report your results!_ |
+
+_Please help verify compatibility by reporting your results!_
+
+## Installation Steps
+
+1. Ensure EmuDeck and ES-DE are installed on your Steam Deck.
+2. Download the [latest Grout release](https://github.com/rommapp/grout/releases/latest/download/Grout-ESDE.zip) for
+ EmuDeck / ES-DE.
+3. Unzip the downloaded archive.
+4. Copy the `Grout` folder and `Grout.sh` file to your EmuDeck Ports directory:
+ - Internal storage: `~/Emulation/roms/ports/`
+ - SD card: `/run/media//Emulation/roms/ports/`
+5. Restart ES-DE or refresh your game list.
+6. Launch Grout from the `Ports` system and enjoy!
+
+## Important Configuration
+
+!!! important
+ Grout expects the standard EmuDeck folder layout where `roms`, `bios`, and `saves` are inside the same
+ `Emulation` directory. The launcher derives this path from the `roms/ports` folder that contains `Grout.sh`.
+
+!!! note
+ Save sync support on EmuDeck is best-effort because save locations vary by emulator. ROM downloads, BIOS downloads,
+ artwork downloads, and ES-DE `gamelist.xml` updates use the standard EmuDeck directories.
+
+## Update
+
+### In-App update (Recommended)
+
+Grout has a built-in update mechanism. To update Grout, launch the application and navigate to the `Settings` menu. From there,
+select `Check for Updates`. If a new version is available, follow the on-screen prompts to download and install the update.
+
+### Manual update
+
+To update Grout manually, download the latest release and replace the existing `Grout` folder and `Grout.sh` file in your
+EmuDeck Ports directory. If you have made any custom configurations, ensure to back them up before replacing the folder.
+Be sure to keep the `config.json` file if you do not want to authenticate again, and configure platform folder mappings again.
+
+## Next Steps
+
+After installation is complete, check out the [User Guide](../usage/guide.md) to learn how to use Grout.
+
+--8<-- "docs/_includes/cfw-links.md"
diff --git a/docs/index.md b/docs/index.md
index 4be37f8f..a5529c67 100644
--- a/docs/index.md
+++ b/docs/index.md
@@ -13,7 +13,7 @@ hide:
Download and manage games from your [RomM](https://romm.app) instance directly on your Linux based retro handheld.
-[Allium](getting-started/install-allium.md) · [Batocera](getting-started/install-batocera.md) · [Knulli](getting-started/install-knulli.md) · [MinUI](getting-started/install-minui.md) · [muOS](getting-started/install-muos.md) · [NextUI](getting-started/install-nextui.md) · [Onion](getting-started/install-onion.md) · [ROCKNIX](getting-started/install-rocknix.md) · [Spruce](getting-started/install-spruce.md) · [TrimUI](getting-started/install-trimui.md)
+[Allium](getting-started/install-allium.md) · [Batocera](getting-started/install-batocera.md) · [EmuDeck / ES-DE](getting-started/install-emudeck.md) · [Knulli](getting-started/install-knulli.md) · [MinUI](getting-started/install-minui.md) · [muOS](getting-started/install-muos.md) · [NextUI](getting-started/install-nextui.md) · [Onion](getting-started/install-onion.md) · [ROCKNIX](getting-started/install-rocknix.md) · [Spruce](getting-started/install-spruce.md) · [TrimUI](getting-started/install-trimui.md)
[:fontawesome-solid-gamepad: Get Started](getting-started/index.md){ .md-button .md-button--primary }
diff --git a/docs/platforms/esde.md b/docs/platforms/esde.md
new file mode 100644
index 00000000..0b205e71
--- /dev/null
+++ b/docs/platforms/esde.md
@@ -0,0 +1,87 @@
+# EmuDeck / ES-DE Platform Mappings
+
+This table shows the mappings of RomM Fs Slug to EmuDeck's ES-DE platform folders.
+
+| Platform Name | RomM Fs Slug | Folder(s) |
+|---|---|---|
+| 3DO Interactive Multiplayer | 3do | 3do |
+| Amiga | amiga | amiga, amigacd32 |
+| Amstrad CPC | acpc | amstradcpc |
+| Arcade | arcade | arcade, mame, fbneo, neogeo |
+| Arduboy | arduboy | arduboy |
+| Atari 2600 | atari2600 | atari2600 |
+| Atari 5200 | atari5200 | atari5200 |
+| Atari 7800 | atari7800 | atari7800 |
+| Atari 800 | atari800 | atari800 |
+| Atari Jaguar | jaguar | atarijaguar, jaguar |
+| Atari Lynx | lynx | atarilynx, lynx |
+| Atari ST/STE | atari-st | atarist |
+| Cave Story | cave-story | cavestory |
+| ColecoVision | colecovision | colecovision |
+| Commodore 128 | c128 | c128 |
+| Commodore 16 | c16 | c16 |
+| Commodore C64/128/MAX | c64 | c64 |
+| Commodore PET | cpet | pet |
+| Commodore VIC-20 | vic-20 | vic20, c20 |
+| DOS | dos | dos |
+| Dreamcast | dc | dreamcast |
+| Fairchild Channel F | fairchild-channel-f | channelf |
+| Family Computer | famicom | famicom, nes |
+| Family Computer Disk System | fds | fds |
+| Galaksija | galaksija | *(none)* |
+| Game & Watch | g-and-w | gameandwatch |
+| Game Boy | gb | gb |
+| Game Boy Advance | gba | gba |
+| Game Boy Color | gbc | gbc |
+| Intellivision | intellivision | intellivision |
+| J2ME | j2me | j2me |
+| MSX | msx | msx, msx1, msx2, msx2plus, msxturbor |
+| Mega Duck/Cougar Boy | mega-duck-slash-cougar-boy | megaduck |
+| Neo Geo AES | neogeoaes | neogeo |
+| Neo Geo CD | neo-geo-cd | neogeocd |
+| Neo Geo MVS | neogeomvs | neogeo |
+| Neo Geo Pocket | neo-geo-pocket | ngp |
+| Neo Geo Pocket Color | neo-geo-pocket-color | ngpc |
+| Nintendo 3DS | 3ds | n3ds, 3ds |
+| Nintendo 64 | n64 | n64 |
+| Nintendo DS | nds | nds |
+| Nintendo Entertainment System | nes | nes |
+| Nintendo GameCube | ngc | gc, gamecube |
+| Nintendo Wii | wii | wii |
+| Nintendo Wii U | wiiu | wiiu |
+| Odyssey | odyssey | odyssey2, videopac |
+| OpenBOR | openbor | openbor |
+| PC Engine SuperGrafx | supergrafx | supergrafx |
+| PC-8000 | pc-8000 | pc88 |
+| PC-9800 Series | pc-9800-series | pc98 |
+| PC-FX | pc-fx | pcfx |
+| PICO-8 | pico | pico8 |
+| PICO-8 | pico-8 | pico8 |
+| Philips CD-i | philips-cd-i | cdi |
+| PlayStation | psx | psx, ps1 |
+| PlayStation 2 | ps2 | ps2 |
+| PlayStation 3 | ps3 | ps3 |
+| PlayStation Portable | psp | psp |
+| Pokemon Mini | pokemon-mini | pokemini |
+| SG-1000 | sg1000 | sg-1000, sg1000 |
+| Sega 32X | sega32 | sega32x |
+| Sega CD | segacd | segacd |
+| Sega Game Gear | gamegear | gamegear |
+| Sega Genesis | genesis | genesis, megadrive |
+| Sega Master System | sms | mastersystem |
+| Sega Saturn | saturn | saturn |
+| Sharp X1 | x1 | x1 |
+| Sharp X68000 | sharp-x68000 | x68000 |
+| Super Famicom | sfam | snes |
+| Super Nintendo | snes | snes |
+| Supervision | supervision | supervision |
+| TIC-80 | tic-80 | tic80 |
+| TurboGrafx-16 | tg16 | pcengine, tg16 |
+| TurboGrafx-CD | turbografx-cd | pcenginecd, tg-cd |
+| Vectrex | vectrex | vectrex |
+| Videopac | videopac | videopac |
+| Virtual Boy | virtualboy | virtualboy |
+| WonderSwan | wonderswan | wonderswan, wswan |
+| WonderSwan Color | wonderswan-color | wonderswancolor, wswanc |
+| ZX Spectrum | zxs | zxspectrum |
+| ZX81 | zx81 | zx81 |
diff --git a/docs/usage/guide.md b/docs/usage/guide.md
index e099d3d2..c18354f8 100644
--- a/docs/usage/guide.md
+++ b/docs/usage/guide.md
@@ -177,6 +177,7 @@ Grout uses platform mappings to determine where to save downloaded games on your
different folder naming conventions. Use these references to see the exact folder names used by your CFW:
- [KNULLI](../platforms/knulli.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
+- [EmuDeck / ES-DE](../platforms/esde.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
- [muOS](../platforms/muos.md) - Mixed short codes and descriptive names (e.g., `gb`, `Nintendo Game Boy`)
- [NextUI](../platforms/nextui.md) - Descriptive names with tags (e.g., `Game Boy (GB)`)
- [ROCKNIX](../platforms/rocknix.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
diff --git a/docs/usage/settings.md b/docs/usage/settings.md
index a3d2d188..f2959224 100644
--- a/docs/usage/settings.md
+++ b/docs/usage/settings.md
@@ -127,6 +127,7 @@ For detailed documentation on platform mapping, see the [User Guide](guide.md#pl
Each CFW uses different folder naming conventions:
- [KNULLI](../platforms/knulli.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
+- [EmuDeck / ES-DE](../platforms/esde.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
- [muOS](../platforms/muos.md) - Mixed short codes and descriptive names (e.g., `gb`, `Nintendo Game Boy`)
- [NextUI](../platforms/nextui.md) - Descriptive names with tags (e.g., `Game Boy (GB)`)
- [ROCKNIX](../platforms/rocknix.md) - ES-DE style folder names (e.g., `gb`, `snes`, `psx`)
diff --git a/mkdocs.yml b/mkdocs.yml
index 8377774f..e963c067 100644
--- a/mkdocs.yml
+++ b/mkdocs.yml
@@ -68,6 +68,7 @@ nav:
- getting-started/index.md
- Allium: getting-started/install-allium.md
- Batocera: getting-started/install-batocera.md
+ - EmuDeck / ES-DE: getting-started/install-emudeck.md
- Knulli: getting-started/install-knulli.md
- MinUI: getting-started/install-minui.md
- muOS: getting-started/install-muos.md
@@ -84,6 +85,7 @@ nav:
- CFW Specific Info:
- Allium: platforms/allium.md
- Batocera: platforms/BATOCERA.md
+ - EmuDeck / ES-DE: platforms/esde.md
- Knulli: platforms/knulli.md
- Koriki: platforms/koriki.md
- MinUI: platforms/minui.md
diff --git a/scripts/ESDE/Grout.sh b/scripts/ESDE/Grout.sh
new file mode 100644
index 00000000..ba340e6d
--- /dev/null
+++ b/scripts/ESDE/Grout.sh
@@ -0,0 +1,43 @@
+#!/bin/bash
+CUR_DIR="$(cd "$(dirname "$0")" && pwd)"
+APP_DIR="$CUR_DIR/Grout"
+LOCK_DIR="${XDG_RUNTIME_DIR:-/tmp}/grout-esde.lock"
+
+if ! mkdir "$LOCK_DIR" 2>/dev/null; then
+ if [ -f "$LOCK_DIR/pid" ] && kill -0 "$(cat "$LOCK_DIR/pid")" 2>/dev/null; then
+ exit 0
+ fi
+ rm -rf "$LOCK_DIR"
+ mkdir "$LOCK_DIR" 2>/dev/null || exit 0
+fi
+printf '%s\n' "$$" > "$LOCK_DIR/pid"
+trap 'rm -rf "$LOCK_DIR"' EXIT
+
+# Apply pending update
+if [ -d "$CUR_DIR/.update" ]; then
+ cp -rf "$CUR_DIR/.update/"* "$CUR_DIR/"
+ rm -rf "$CUR_DIR/.update"
+fi
+
+cd "$APP_DIR" || exit 1
+
+# EmuDeck's ES-DE ports folder is normally /roms/ports.
+export CFW=ESDE
+export BASE_PATH="$(cd "$CUR_DIR/../.." && pwd)"
+export LD_LIBRARY_PATH="$APP_DIR/lib:$LD_LIBRARY_PATH"
+
+# Steam Deck uses Xbox-style face buttons, so use direct A=A/B=B mappings.
+export FLIP_FACE_BUTTONS=1
+
+# Prefer SDL's game controller API and ignore duplicate keyboard/raw joystick events.
+export DISABLE_KEYBOARD_INPUT=1
+export DISABLE_JOYSTICK_INPUT=1
+
+# Grout uses its own gamepad-driven keyboard. On Steam Deck, SDL/Steam can
+# also surface the Steam keyboard, which can interfere with Grout's keyboard.
+export SDL_ENABLE_SCREEN_KEYBOARD=0
+export SDL_IME_SHOW_UI=0
+
+./grout
+
+exit 0
diff --git a/scripts/ESDE/logo.png b/scripts/ESDE/logo.png
new file mode 100644
index 00000000..bb49d84b
Binary files /dev/null and b/scripts/ESDE/logo.png differ
diff --git a/taskfiles/build.yml b/taskfiles/build.yml
index e875d1f2..0e14ff69 100644
--- a/taskfiles/build.yml
+++ b/taskfiles/build.yml
@@ -23,6 +23,7 @@ tasks:
- echo "Extracting {{.BUILD_DIR}}..."
- docker cp {{.CONTAINER_NAME}}-{{.BUILD_DIR}}:/build/grout {{.BUILD_DIR}}/grout
- 'if [ -n "{{.LIB_PATH}}" ]; then docker cp {{.CONTAINER_NAME}}-{{.BUILD_DIR}}:{{.LIB_PATH}} {{.BUILD_DIR}}/lib/libSDL2_gfx-1.0.so.0; fi'
+ - 'EXTRA_LIBS="{{.EXTRA_LIBS}}"; if [ -n "$EXTRA_LIBS" ]; then for spec in $EXTRA_LIBS; do src="${spec%%:*}"; dest="${spec##*:}"; docker cp {{.CONTAINER_NAME}}-{{.BUILD_DIR}}:$src {{.BUILD_DIR}}/lib/$dest; done; fi'
- docker rm {{.CONTAINER_NAME}}-{{.BUILD_DIR}} >/dev/null 2>&1
- docker image prune --filter "label={{.LABEL}}" -f >/dev/null 2>&1 || true
- echo "Extract {{.BUILD_DIR}} complete"
@@ -35,7 +36,7 @@ tasks:
- task: _build
vars: { PLATFORM: linux/arm64, BUILD_DIR: build64, IMAGE_TAG: "{{.IMAGE_NAME}}-arm64", DOCKERFILE: docker/Dockerfile, LOCAL: "{{.LOCAL}}" }
- task: _extract
- vars: { BUILD_DIR: build64, IMAGE_TAG: "{{.IMAGE_NAME}}-arm64", LIB_PATH: /usr/lib/aarch64-linux-gnu/libSDL2_gfx-1.0.so.0.0.2 }
+ vars: { BUILD_DIR: build64, IMAGE_TAG: "{{.IMAGE_NAME}}-arm64", LIB_PATH: /usr/lib/aarch64-linux-gnu/libSDL2_gfx-1.0.so.0.0.2, EXTRA_LIBS: "" }
amd64:
desc: Build and extract for AMD64 (x86_64)
@@ -43,7 +44,11 @@ tasks:
- task: _build
vars: { PLATFORM: linux/amd64, BUILD_DIR: build, IMAGE_TAG: "{{.IMAGE_NAME}}-amd64", DOCKERFILE: docker/Dockerfile }
- task: _extract
- vars: { BUILD_DIR: build, IMAGE_TAG: "{{.IMAGE_NAME}}-amd64", LIB_PATH: /usr/lib/x86_64-linux-gnu/libSDL2_gfx-1.0.so.0.0.2 }
+ vars:
+ BUILD_DIR: build
+ IMAGE_TAG: "{{.IMAGE_NAME}}-amd64"
+ LIB_PATH: /usr/lib/x86_64-linux-gnu/libSDL2_gfx-1.0.so.0.0.2
+ EXTRA_LIBS: "/usr/lib/x86_64-linux-gnu/libSDL2-2.0.so.0.14.0:libSDL2-2.0.so.0 /usr/lib/x86_64-linux-gnu/libSDL2_image-2.0.so.0.2.3:libSDL2_image-2.0.so.0 /usr/lib/x86_64-linux-gnu/libSDL2_ttf-2.0.so.0.14.1:libSDL2_ttf-2.0.so.0 /usr/lib/x86_64-linux-gnu/libjpeg.so.62.3.0:libjpeg.so.62 /usr/lib/x86_64-linux-gnu/libpng16.so.16.37.0:libpng16.so.16 /usr/lib/x86_64-linux-gnu/libtiff.so.5.6.0:libtiff.so.5 /usr/lib/x86_64-linux-gnu/libwebp.so.6.0.2:libwebp.so.6 /usr/lib/x86_64-linux-gnu/libfreetype.so.6.17.4:libfreetype.so.6 /usr/lib/x86_64-linux-gnu/libbrotlidec.so.1.0.9:libbrotlidec.so.1 /usr/lib/x86_64-linux-gnu/libbrotlicommon.so.1.0.9:libbrotlicommon.so.1 /usr/lib/x86_64-linux-gnu/libzstd.so.1.4.8:libzstd.so.1 /lib/x86_64-linux-gnu/liblzma.so.5.2.5:liblzma.so.5 /usr/lib/x86_64-linux-gnu/libjbig.so.0:libjbig.so.0 /usr/lib/x86_64-linux-gnu/libdeflate.so.0:libdeflate.so.0 /lib/x86_64-linux-gnu/libz.so.1.2.11:libz.so.1"
x86:
desc: Build and extract for x86 (32-bit)
@@ -51,7 +56,7 @@ tasks:
- task: _build
vars: { PLATFORM: linux/386, BUILD_DIR: buildx86, IMAGE_TAG: "{{.IMAGE_NAME}}-x86", DOCKERFILE: docker/Dockerfile }
- task: _extract
- vars: { BUILD_DIR: buildx86, IMAGE_TAG: "{{.IMAGE_NAME}}-x86", LIB_PATH: /usr/lib/i386-linux-gnu/libSDL2_gfx-1.0.so.0.0.2 }
+ vars: { BUILD_DIR: buildx86, IMAGE_TAG: "{{.IMAGE_NAME}}-x86", LIB_PATH: /usr/lib/i386-linux-gnu/libSDL2_gfx-1.0.so.0.0.2, EXTRA_LIBS: "" }
arm32:
desc: Build and extract for ARM32
@@ -62,4 +67,4 @@ tasks:
vars: { PLATFORM: linux/arm/v7, BUILD_DIR: build32, IMAGE_TAG: "{{.IMAGE_NAME}}-arm32", DOCKERFILE: docker/32.Dockerfile, LOCAL: "{{.LOCAL}}" }
# TODO: add LIB_PATH once custom SDL build for Miyoo is ready
- task: _extract
- vars: { BUILD_DIR: build32, IMAGE_TAG: "{{.IMAGE_NAME}}-arm32", LIB_PATH: "" }
+ vars: { BUILD_DIR: build32, IMAGE_TAG: "{{.IMAGE_NAME}}-arm32", LIB_PATH: "", EXTRA_LIBS: "" }
diff --git a/taskfiles/package.yml b/taskfiles/package.yml
index 9007c443..e5cba408 100644
--- a/taskfiles/package.yml
+++ b/taskfiles/package.yml
@@ -4,9 +4,9 @@ tasks:
all:
desc: Package for all platforms
- deps: [ next, muos, knulli, spruce, rocknix, trimui, allium, onion, koriki, minui, batocera, batocera-x86, batocera-amd64 ]
+ deps: [ next, muos, knulli, spruce, rocknix, trimui, allium, onion, koriki, minui, batocera, batocera-x86, batocera-amd64, esde ]
cmds:
- - echo "Packaging complete (14 platforms)"
+ - echo "Packaging complete (15 platforms)"
silent: true
next:
@@ -147,3 +147,13 @@ tasks:
- cp -R build/lib/* dist/Batocera-amd64/Grout/lib/
- chmod a+x dist/Batocera-amd64/Grout/grout dist/Batocera-amd64/Grout.sh
silent: true
+
+ esde:
+ cmds:
+ - rm -rf dist/ESDE
+ - mkdir -p dist/ESDE/Grout/lib
+ - cp scripts/ESDE/Grout.sh dist/ESDE/
+ - cp build/grout scripts/ESDE/logo.png README.md LICENSE dist/ESDE/Grout/
+ - cp -R build/lib/* dist/ESDE/Grout/lib/
+ - chmod a+x dist/ESDE/Grout/grout dist/ESDE/Grout.sh
+ silent: true
diff --git a/update/updater.go b/update/updater.go
index dd9b0f1a..f62755d5 100644
--- a/update/updater.go
+++ b/update/updater.go
@@ -64,6 +64,11 @@ func GetDistributionAssetName(c cfw.CFW) string {
default:
return ""
}
+ case cfw.ESDE:
+ if runtime.GOARCH == "amd64" {
+ return "Grout-ESDE.zip"
+ }
+ return ""
default:
return ""
}
@@ -257,6 +262,8 @@ func getLaunchScriptPath(c cfw.CFW) string {
return "Grout.pak/launch.sh"
case cfw.Batocera:
return "Grout.sh"
+ case cfw.ESDE:
+ return "Grout.sh"
default:
return ""
}