#!/usr/bin/python3
# encoding=utf-8
#
# Copyright © 2024 Sébastien Noel
# SPDX-License-Identifier: GPL-2.0-or-later

import configparser
import json
import os
import sys
import zipfile

from contextlib import suppress
from typing import Any

from game_data_packager.data import Package
from game_data_packager.game import load_games
from game_data_packager.games.scummvm_common import ScummvmGameData
from game_data_packager.packaging import (
    PackagingSystem,
    get_native_packaging_system,
)
from game_data_packager.util import mkdir_p


def write_desktop_file(
        pgm: str,
        game: ScummvmGameData,
        package: Package,
        packaging: PackagingSystem,
        desktop_subdir: str,
) -> None:
    gdp_launcher = '$assets/game-data-packager-runtime/gdp-launcher'
    gdp_launcher = packaging.substitute(gdp_launcher, package.name)

    desktop = configparser.RawConfigParser()
    desktop.optionxform = lambda option: option     # type: ignore
    desktop['Desktop Entry'] = {}
    entry = desktop['Desktop Entry']
    entry['Name'] = package.longname or game.longname
    assert type(game.genre) is str
    entry['GenericName'] = game.genre + ' Game'
    entry['TryExec'] = 'scummvm'
    entry['Exec'] = '%s --id %s' % (gdp_launcher, pgm)
    entry['Icon'] = pgm
    entry['Terminal'] = 'false'
    entry['Type'] = 'Application'
    entry['Categories'] = (
        'Game;%sGame;' % game.genre.replace(' ', '')
    )

    with open(
        os.path.join(desktop_subdir, '%s.desktop' % pgm),
        'w', encoding='utf-8',
    ) as output:
        desktop.write(output, space_around_delimiters=False)


def main(vfs_zip: str, outfile: str, desktop_subdir: str) -> None:
    with suppress(FileNotFoundError):
        os.unlink(outfile)

    mkdir_p(desktop_subdir)
    packaging = get_native_packaging_system()
    games = load_games(use_vfs=vfs_zip)

    with zipfile.ZipFile(outfile, mode="w") as archive:
        for g_name, game in games.items():
            if not isinstance(game, ScummvmGameData):
                continue

            for p_name, package in game.packages.items():
                if package.section != 'games':
                    continue
                if package.data_type != 'data':
                    continue
                if package.name.endswith('-music'):
                    continue
                if package.name.endswith('-video'):
                    continue

                assert package.name.endswith('-data'), package.name
                pgm = package.name[0:len(package.name)-len('-data')]

                write_desktop_file(pgm, game, package,
                                   packaging, desktop_subdir)

                gameid = game.gameid
                if package.gameid is not None:
                    gameid = package.gameid

                langs = package.langs

                launcher_path = 'launch-%s.json' % pgm
                launcher: dict[str, Any] = {}
                launcher['argv'] = 'scummvm -p %s %s' % \
                                   (package.install_to, gameid)
                launcher['argv'] = packaging.substitute(
                                          launcher['argv'],
                                          package.name,
                                        )
                if len(langs) > 1 and gameid != 'nippon':
                    launcher['languages'] = {'choices': langs, 'arg': '-q'}

                info = zipfile.ZipInfo(launcher_path)
                archive.writestr(
                    info,
                    json.dumps(launcher),
                    compress_type=zipfile.ZIP_DEFLATED,
                    compresslevel=9,
                )


if __name__ == '__main__':
    main(*sys.argv[1:])
