From: Niki Roo Date: Sun, 23 Mar 2025 21:14:29 +0000 (+0100) Subject: move strange commands to commands.py and simplify them X-Git-Url: http://git.nikiroo.be/?a=commitdiff_plain;h=cbf2ceed8af278bc7ba97a75ecaf8a10b2029916;p=gamiki.git move strange commands to commands.py and simplify them --- diff --git a/gamiki/support/commands.py b/gamiki/support/commands.py new file mode 100644 index 0000000..5f4b58f --- /dev/null +++ b/gamiki/support/commands.py @@ -0,0 +1,64 @@ +from subprocess import run +from shutil import which +from os import environ +from pathlib import PurePath + +__programs: dict[str, str] = None + +def program(program: str) -> str: + global __programs + + if (__programs == None): + __programs = {} + + if (program not in __programs): + __programs[program] = which(program) + + return __programs[program] + +def dosbox(dir: PurePath, link: PurePath) -> int: + if (program("app.sh") != None): + cmd = [ program("app.sh"),"--wait","dosbox","--link",link.as_posix() ] + elif(program("dosbox") != None): + cmd = [ program("dosbox") ] + else: + raise RuntimeError("DosBox not found") + + base = dir.joinpath("base.conf") + if (base.exists()): + cmd.append("-conf") + cmd.append(base.as_posix()) + cmd.append("-conf") + cmd.append(dir.joinpath("start.conf").as_posix()) + + return run(cmd, cwd=dir).returncode + +def start_sh(start: PurePath) -> int: + env = environ.copy() + + if (program("launch.sh") != None): + cmd = [ program("launch.sh"), "games", "--dlink", start.as_posix() ] + env["OPTS"] = "--entrypoint=bash" + else: + cmd = [ start.as_posix() ] + + + return run(cmd, cwd=start.parent, env=env).returncode + +def wine(dir: PurePath) -> int: + env = environ.copy() + + wine_bat = dir.joinpath("wine.bat").as_posix() + wine_prefix = dir.joinpath("wine.prefix").as_posix() + + if (program("launch.sh") != None): + cmd = [ program("launch.sh"), "wine", "--dlink", wine_bat ] + env["OPTS"] = "-e WINEPREFIX='" + wine_prefix.replace("'", "\\'") + "'" + elif (program("wine") != None): + cmd = [ "wine", wine_bat ] + else: + raise RuntimeError("wine not found") + + + return run(cmd, cwd=dir, env=env).returncode + diff --git a/gamiki/support/support.py b/gamiki/support/support.py index ab92571..282a5b0 100644 --- a/gamiki/support/support.py +++ b/gamiki/support/support.py @@ -4,25 +4,18 @@ from shutil import which from ..game import Game class Support: - programs: dict[str, str] = None - """Can detect and start games.""" - def __init__(self): - pass - + def supports(self, game: Game) -> bool: return False def start(self, game: Game, params: list[str] = []): if (not self.supports(game)): raise RuntimeError("Unsupported game was called: " + game.name) - - def program(name: str) -> str: - if (Support.programs == None): - Support.programs = {} - - if (name not in Support.programs): - Support.programs[name] = which(name) + + def running(self, game: Game): + print("Running", game.name) - return Support.programs[name] + def error(self, game: Game, rc: int): + print("\nError when running", game.name + ":", "RC", rc) diff --git a/gamiki/support/support_dos.py b/gamiki/support/support_dos.py index 9c67655..3e96334 100644 --- a/gamiki/support/support_dos.py +++ b/gamiki/support/support_dos.py @@ -1,43 +1,16 @@ -from subprocess import run -from shutil import which - -from . import Support -from ..game import Game +from . import Support +from .commands import dosbox +from ..game import Game class SupportDos(Support): """Supports DOS games via DosBox.""" - def __init__(self): - pass - + def supports(self, game: Game): return game.dir.joinpath("start.conf").exists() def start(self, game: Game, params: list[str] = []): - dir = game.dir.resolve() - link_dir = self.get_link_dir(game).resolve() - - if (Support.program("app.sh") != None): - cmd = [ - Support.program("app.sh"), - "--wait", "dosbox", "--link", link_dir.as_posix() - ] - elif (Support.program("dosbox") != None): - cmd = [ Support.program("dosbox") ] - else: - raise RuntimeError("DosBox not found") - - base = dir.joinpath("base.conf") - if (base.exists()): - cmd.append("-conf") - cmd.append(base.as_posix()) - cmd.append("-conf") - cmd.append(dir.joinpath("start.conf").as_posix()) - - print("Running", game.name) - rep = run(cmd, cwd=dir) - if (rep.returncode != 0): - print("\nError when running", game.name, ": RC", rep.returncode) - - def get_link_dir(self, game: Game) -> str: - return game.dir + self.running(game) + rep = dosbox(game.dir.resolve(), game.dir.resolve()) + if (rep != 0): + self.error(game, rep) diff --git a/gamiki/support/support_ext.py b/gamiki/support/support_ext.py index ff01430..8eb1e92 100644 --- a/gamiki/support/support_ext.py +++ b/gamiki/support/support_ext.py @@ -1,51 +1,18 @@ -from random import random -from math import floor -from os import environ -from pathlib import Path -from subprocess import run -from shutil import which - -from . import Support -from ..game import Game +from . import Support +from .commands import start_sh +from ..game import Game class SupportExt(Support): """Supports external games via the 'games' docker or natively.""" - def __init__(self): - pass def supports(self, game: Game): return game.dir.joinpath("start.sh").exists() def start(self, game: Game, params: list[str] = []): - dir = game.dir.resolve() - - env = environ.copy() - - ffile = None - if (Support.program("launch.sh") != None): - tfile = Path( - "/tmp/shared/.game-" - + "{0:6d}".format(floor(random() * 1000000)) - + ".sh" - ) - with open(tfile, 'w', encoding="utf-8") as data: - data.write("#!/bin/sh\n") - data.write("cd '" + dir.as_posix() + "'\n") - data.write("./start.sh\n") - tfile.chmod(0o777) - env["OPTS"] = "--entrypoint=" + tfile.as_posix() - cmd = [ - Support.program("launch.sh"), - "games", "--link", dir.as_posix() - ] - else: - cmd = [ dir.joinpath("start.sh").as_posix() ] - - print("Running", game.name) - rep = run(cmd, cwd=dir, env=env) - if (rep.returncode != 0): - print("\nError when running", game.name, ": RC", rep.returncode) + start = game.dir.resolve().joinpath("start.sh") - if (tfile != ""): - tfile.unlink() + self.running(game) + rep = start_sh(start) + if (rep != 0): + self.error(game, rep) diff --git a/gamiki/support/support_gog.py b/gamiki/support/support_gog.py index 2344aa3..a71ef0b 100644 --- a/gamiki/support/support_gog.py +++ b/gamiki/support/support_gog.py @@ -1,56 +1,22 @@ -from random import random -from math import floor -from os import environ -from pathlib import Path -from subprocess import run -from shutil import which - -from . import Support -from ..game import Game +from . import Support +from .commands import start_sh +from ..game import Game class SupportGog(Support): """Supports GoG games via the 'games' docker or natively.""" - def __init__(self): - pass def supports(self, game: Game): return game.dir.joinpath("gameinfo").exists() def start(self, game: Game, params: list[str] = []): - dir = game.dir.resolve() + start = game.dir.resolve().joinpath("start.sh") - if (not dir.joinpath("start.sh").exists()): + if (not start.exists()): raise RuntimeError("GoG game without a start.sh script") - env = environ.copy() - - tfile = None - if (Support.program("launch.sh") != None): - tfile = Path( - "/tmp/shared/.game-" - + "{0:6d}".format(floor(random() * 1000000)) - + ".sh" - ) - with open(tfile, 'w', encoding="utf-8") as data: - data.write("#!/bin/sh\n") - data.write("cd '" + dir.as_posix() + "'\n") - data.write("./start.sh\n") - tfile.chmod(0o777) - env["OPTS"] = "--entrypoint=" + tfile.as_posix() - cmd = [ - Support.program("launch.sh"), - "games", "--link", dir.as_posix() - ] - else: - cmd = [ dir.joinpath("start.sh").as_posix() ] - - # GoG launcher already does this: - # print("Running", game.name) - rep = run(cmd, cwd=dir, env=env) - if (rep.returncode != 0): - print("\nError when running", game.name, ": RC", rep.returncode) - - if (tfile != None): - tfile.unlink() - + # No running, GoG launcher already does it: + #self.running(game) + rep = start_sh(start) + if (rep != 0): + self.error(game, rep) diff --git a/gamiki/support/support_win.py b/gamiki/support/support_win.py index 17e802b..6d6db08 100644 --- a/gamiki/support/support_win.py +++ b/gamiki/support/support_win.py @@ -1,17 +1,9 @@ -from random import random -from math import floor -from os import environ -from pathlib import Path -from subprocess import run -from shutil import which - -from . import Support -from ..game import Game +from . import Support +from .commands import wine +from ..game import Game class SupportWin(Support): """Supports Windows games via wine.""" - def __init__(self): - pass def supports(self, game: Game): return game.dir.joinpath("wine.bat").exists() @@ -22,25 +14,8 @@ class SupportWin(Support): if (not dir.joinpath("wine.prefix").exists()): raise RuntimeError("Windows game without a wine.prefix") - wine_bat = dir.joinpath("wine.bat") - wine_prefix = dir.joinpath("wine.prefix").as_posix() - - env = environ.copy() - - tfile = None - if (Support.program("launch.sh") != None): - env["OPTS"] = "-e WINEPREFIX='" +wine_prefix.replace("'","\\'")+ "'" - cmd = [ - Support.program("launch.sh"), - "wine", "--dlink", wine_bat - ] - else: - env["WINEPREFIX"] = wine_prefix - cmd = [ "wine", wine_bat ] - - print("Running", game.name) - rep = run(cmd, env=env) - if (rep.returncode != 0): - print("\nError when running", game.name, ": RC", rep.returncode) - + self.running(game) + rep = wine(dir) + if (rep != 0): + self.error(game, rep) diff --git a/gamiki/support/support_win31.py b/gamiki/support/support_win31.py index 8fd07e9..45350db 100644 --- a/gamiki/support/support_win31.py +++ b/gamiki/support/support_win31.py @@ -1,14 +1,9 @@ -from pathlib import PurePath -from subprocess import run -from shutil import which +from . import Support +from .commands import dosbox +from ..game import Game -from . import Support, SupportDos -from ..game import Game - -class SupportWin31(SupportDos): +class SupportWin31(Support): """Supports Windows 3.1 games via DosBox.""" - - # TODO: must be tried befoer SupportDos def supports(self, game: Game): return ( @@ -16,6 +11,9 @@ class SupportWin31(SupportDos): and game.dir.joinpath("C", "WINDOWS").exists() ) - def get_link_dir(self, game: Game) -> PurePath: - return game.library.dir + def start(self, game: Game, params: list[str] = []): + self.running(game) + rep = dosbox(game.dir.resolve(), game.library.dir.resolve()) + if (rep != 0): + self.error(game, rep)