help="list all known games and their tags",
action="store_true"
)
+global_actions.add_argument("--session-time",
+ help="time played per game",
+ action="store_true"
+)
+global_actions.add_argument("--export-sessions",
+ help="export play sessions of all known games",
+ action="store_true"
+)
+global_actions.add_argument("--import-sessions",
+ help="import (and merge) play sessions",
+ action="store_true"
+)
# Select a game
game_selection = parser.add_argument_group('game selection')
help="get the icon of the game",
metavar="GAME"
)
+game_actions.add_argument("--info-sessions",
+ help="get the play sessions of the game",
+ metavar="GAME"
+)
args = parser.parse_args()
elif (args.list_tags):
builder.list_tags()
exit(0)
+elif (args.session_time):
+ builder.session_time()
+ exit(0)
+elif (args.export_sessions):
+ builder.export_sessions()
+ exit(0)
+elif (args.import_sessions):
+ builder.import_sessions()
+ exit(0)
g = ""
if (args.info):
g = args.info_options
elif (args.info_icon):
g = args.info_icon
+elif (args.info_sessions):
+ g = args.info_sessions
else:
g = args.GAME
elif (args.info_icon):
if ("Icon" in game):
print(game["Icon"])
+elif (args.info_sessions):
+ print("Listing play sessions of:", game.name)
+ game.read_sessions()
+ for sess in game.sessions:
+ print(sess)
else:
game.run(args.OPTION)
+from sys import stdin, stderr
from pathlib import Path, PurePath
-from gamiki import Game, Support, Library
+from gamiki import Game, Support, Library, Session
from gamiki.support import (
SupportDos, SupportWin31, SupportGog, SupportExt, SupportWin
)
"(" + ";".join(game.tags) +")")
i += 1
+ def session_time(self):
+ i = 1
+ for game in self.games:
+ if (game.total_time > 0):
+ num = "{0:6d}".format(i)
+ print(f"{num} {game.total_htime}: {game.name}");
+ i += 1
+
+ def export_sessions(self):
+ for lib in self.libraries:
+ for game in lib:
+ game.read_sessions()
+ if (len(game.sessions)):
+ print(">", lib.name + "/" + game.code)
+ for sess in game.sessions:
+ print(sess)
+
+ def import_sessions(self):
+ sgam = ""
+ slib = ""
+ curr_lib = None
+ curr_gam = None
+ sss = None
+
+ for ln in stdin:
+ ln = ln.strip()
+ if (ln and ln[0] == ">"):
+ slib = ln.split("/")[0][2:]
+ sgam = ln.split("/", maxsplit=1)[1]
+
+ # TODO fix speed
+ if (curr_lib and curr_lib.name != slib):
+ curr_lib = None
+ if (not curr_lib):
+ for lib in self.libraries:
+ if (lib.name == slib):
+ curr_lib = lib
+ if (curr_gam and curr_gam.code != sgam):
+ Session.rewrite_sessions(curr_gam.dir, list(sss.values()))
+ curr_gam = None
+ if (curr_lib and not curr_gam):
+ for gam in curr_lib:
+ if (gam.code == sgam):
+ curr_gam = gam
+ else:
+ if (curr_gam):
+ if (sss == None):
+ curr_gam.read_sessions()
+ sss = {}
+ for sess in curr_gam.sessions:
+ sss[sess.when] = sess
+
+ new_sess = Session.from_str(ln)
+ sss[new_sess.when] = new_sess
+ else:
+ print("Ignoring unknown game:", slib + "/" + sgam, file=stderr)
+
+ if (curr_gam):
+ Session.rewrite_sessions(curr_gam.dir, list(sss.values()))
+
def find(self, key: str) -> Game:
game: Game = None
opts : dict = None # option name -> description
desc : str = ""
total_time : int = 0
+ total_htime : str = "" # human readable time (HH:MM:SS)
total_sessions : int = 0
sessions : list = None # list:Session (call read_sessions() first)
icon : Path = None # "main" icon
except FileNotFoundError:
pass
- self.total, self.sessions = Session.read_total(self.dir)
- # TODO: read the total per option times
+ # TODO: read the total per option times?
+ tot, htot, sessions = Session.read_total(self.dir)
+ self.total_time = tot
+ self.total_htime = htot
+ self.total_sessions = sessions
def _read_icon(self, suffix: str = "") -> PurePath:
"""
humanf = Session._human(self.elapsed)
return f"Session of {dat} ({hour}) lasted: {humanf}{oopt}"
- def read_total(dir: PurePath) -> (int, int):
+ def read_total(dir: PurePath) -> (int, int, int):
"""
Read a session.total file.
@param dir: the game directory where to find the session.total file
- @return (total play time in second, number of sessions played)
+ @return (
+ total play time in second,
+ total play time in HH:MM:SS format,
+ number of sessions played
+ )
"""
ln1 = "(not read yet)"
)
# TODO: read the total per option times?
- return (total, num_sessions)
+ return (total, Session._human(total), num_sessions)
except FileNotFoundError:
pass
except Exception as e:
num_sessions += 1
total += sess.elapsed
- return (total, num_sessions)
+ return (total, Session._human(total), num_sessions)
def read_sessions(dir: PurePath) -> list['Session']:
sessions = []
Session.write_total(dir, sessions)
except Exception as e:
print(f"Cannot save total time: {e}", file=stderr)
+
+ def rewrite_sessions(dir: PurePath, sessions: list):
+ """
+ Rewrite the list of sessions, overriding the previous one -- will also
+ update the sessions.total file or create it if needed.
+
+ @param dir: the game directory where to find the session.total file
+ @param sessions: the new play sessions (will be used to overwrite
+ the previous information, be careful!)
+
+ """
+
+ # Can throw:
+ file = dir.joinpath("sessions.txt")
+ with open(file, "w", encoding="utf-8") as data:
+ for sess in sessions:
+ data.write(str(sess))
+ data.write("\n")
+
+ # We catch the exceptions, as this file can be recomputed if needed
+ try:
+ Session.write_total(dir, sessions)
+ except Exception as e:
+ print(f"Cannot save total time: {e}", file=stderr)
def _human(seconds: int) -> str:
ss = (seconds % 60)