CommonClient: allow running it as text client
CommonClient: move logging init to library Setup: add TextClient
This commit is contained in:
		
							parent
							
								
									bde02f696b
								
							
						
					
					
						commit
						8b2433584d
					
				| 
						 | 
					@ -4,6 +4,7 @@ import typing
 | 
				
			||||||
import asyncio
 | 
					import asyncio
 | 
				
			||||||
import urllib.parse
 | 
					import urllib.parse
 | 
				
			||||||
import sys
 | 
					import sys
 | 
				
			||||||
 | 
					import os
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import websockets
 | 
					import websockets
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -17,6 +18,9 @@ logger = logging.getLogger("Client")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gui_enabled = Utils.is_frozen() or "--nogui" not in sys.argv
 | 
					gui_enabled = Utils.is_frozen() or "--nogui" not in sys.argv
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					log_folder = Utils.local_path("logs")
 | 
				
			||||||
 | 
					os.makedirs(log_folder, exist_ok=True)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class ClientCommandProcessor(CommandProcessor):
 | 
					class ClientCommandProcessor(CommandProcessor):
 | 
				
			||||||
    def __init__(self, ctx: CommonContext):
 | 
					    def __init__(self, ctx: CommonContext):
 | 
				
			||||||
| 
						 | 
					@ -198,7 +202,7 @@ class CommonContext():
 | 
				
			||||||
    def event_invalid_game(self):
 | 
					    def event_invalid_game(self):
 | 
				
			||||||
        raise Exception('Invalid Game; please verify that you connected with the right game to the correct world.')
 | 
					        raise Exception('Invalid Game; please verify that you connected with the right game to the correct world.')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    async def server_auth(self, password_requested):
 | 
					    async def server_auth(self, password_requested: bool = False):
 | 
				
			||||||
        if password_requested and not self.password:
 | 
					        if password_requested and not self.password:
 | 
				
			||||||
            logger.info('Enter the password required to join this game:')
 | 
					            logger.info('Enter the password required to join this game:')
 | 
				
			||||||
            self.password = await self.console_input()
 | 
					            self.password = await self.console_input()
 | 
				
			||||||
| 
						 | 
					@ -315,6 +319,7 @@ async def process_server_cmd(ctx: CommonContext, args: dict):
 | 
				
			||||||
            logger.info("Server protocol tags: " + ", ".join(args["tags"]))
 | 
					            logger.info("Server protocol tags: " + ", ".join(args["tags"]))
 | 
				
			||||||
            if args['password']:
 | 
					            if args['password']:
 | 
				
			||||||
                logger.info('Password required')
 | 
					                logger.info('Password required')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            for permission_name, permission_flag in args.get("permissions", {}).items():
 | 
					            for permission_name, permission_flag in args.get("permissions", {}).items():
 | 
				
			||||||
                flag = Permission(permission_flag)
 | 
					                flag = Permission(permission_flag)
 | 
				
			||||||
                logger.info(f"{permission_name.capitalize()} permission: {flag.name}")
 | 
					                logger.info(f"{permission_name.capitalize()} permission: {flag.name}")
 | 
				
			||||||
| 
						 | 
					@ -324,8 +329,7 @@ async def process_server_cmd(ctx: CommonContext, args: dict):
 | 
				
			||||||
                f" for each location checked. Use !hint for more information.")
 | 
					                f" for each location checked. Use !hint for more information.")
 | 
				
			||||||
            ctx.hint_cost = int(args['hint_cost'])
 | 
					            ctx.hint_cost = int(args['hint_cost'])
 | 
				
			||||||
            ctx.check_points = int(args['location_check_points'])
 | 
					            ctx.check_points = int(args['location_check_points'])
 | 
				
			||||||
            ctx.forfeit_mode = args['forfeit_mode']
 | 
					
 | 
				
			||||||
            ctx.remaining_mode = args['remaining_mode']
 | 
					 | 
				
			||||||
            if len(args['players']) < 1:
 | 
					            if len(args['players']) < 1:
 | 
				
			||||||
                logger.info('No player connected')
 | 
					                logger.info('No player connected')
 | 
				
			||||||
            else:
 | 
					            else:
 | 
				
			||||||
| 
						 | 
					@ -453,3 +457,78 @@ async def console_loop(ctx: CommonContext):
 | 
				
			||||||
                commandprocessor(input_text)
 | 
					                commandprocessor(input_text)
 | 
				
			||||||
        except Exception as e:
 | 
					        except Exception as e:
 | 
				
			||||||
            logger.exception(e)
 | 
					            logger.exception(e)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def init_logging(name: str):
 | 
				
			||||||
 | 
					    if gui_enabled:
 | 
				
			||||||
 | 
					        logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO,
 | 
				
			||||||
 | 
					                            filename=os.path.join(log_folder, f"{name}.txt"), filemode="w", force=True)
 | 
				
			||||||
 | 
					    else:
 | 
				
			||||||
 | 
					        logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO, force=True)
 | 
				
			||||||
 | 
					        logging.getLogger().addHandler(logging.FileHandler(os.path.join(log_folder, f"{name}.txt"), "w"))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if __name__ == '__main__':
 | 
				
			||||||
 | 
					    # Text Mode to use !hint and such with games that have no text entry
 | 
				
			||||||
 | 
					    init_logging("TextClient")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    class TextContext(CommonContext):
 | 
				
			||||||
 | 
					        async def server_auth(self, password_requested: bool = False):
 | 
				
			||||||
 | 
					            if password_requested and not self.password:
 | 
				
			||||||
 | 
					                await super(TextContext, self).server_auth(password_requested)
 | 
				
			||||||
 | 
					            if not self.auth:
 | 
				
			||||||
 | 
					                logger.info('Enter slot name:')
 | 
				
			||||||
 | 
					                self.auth = await self.console_input()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            await self.send_msgs([{"cmd": 'Connect',
 | 
				
			||||||
 | 
					                                   'password': self.password, 'name': self.auth, 'version': Utils.version_tuple,
 | 
				
			||||||
 | 
					                                   'tags': ['AP', 'IgnoreGame'],
 | 
				
			||||||
 | 
					                                   'uuid': Utils.get_unique_identifier(), 'game': self.game
 | 
				
			||||||
 | 
					                                   }])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    async def main(args):
 | 
				
			||||||
 | 
					        ctx = TextContext(args.connect, args.password)
 | 
				
			||||||
 | 
					        ctx.server_task = asyncio.create_task(server_loop(ctx), name="ServerLoop")
 | 
				
			||||||
 | 
					        if gui_enabled:
 | 
				
			||||||
 | 
					            input_task = None
 | 
				
			||||||
 | 
					            from kvui import TextManager
 | 
				
			||||||
 | 
					            ctx.ui = TextManager(ctx)
 | 
				
			||||||
 | 
					            ui_task = asyncio.create_task(ctx.ui.async_run(), name="UI")
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            input_task = asyncio.create_task(console_loop(ctx), name="Input")
 | 
				
			||||||
 | 
					            ui_task = None
 | 
				
			||||||
 | 
					        await ctx.exit_event.wait()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        ctx.server_address = None
 | 
				
			||||||
 | 
					        if ctx.server and not ctx.server.socket.closed:
 | 
				
			||||||
 | 
					            await ctx.server.socket.close()
 | 
				
			||||||
 | 
					        if ctx.server_task:
 | 
				
			||||||
 | 
					            await ctx.server_task
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        while ctx.input_requests > 0:
 | 
				
			||||||
 | 
					            ctx.input_queue.put_nowait(None)
 | 
				
			||||||
 | 
					            ctx.input_requests -= 1
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if ui_task:
 | 
				
			||||||
 | 
					            await ui_task
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if input_task:
 | 
				
			||||||
 | 
					            input_task.cancel()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    import argparse
 | 
				
			||||||
 | 
					    import colorama
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    parser = argparse.ArgumentParser(description="Gameless Archipelago Client, for text interfaction.")
 | 
				
			||||||
 | 
					    parser.add_argument('--connect', default=None, help='Address of the multiworld host.')
 | 
				
			||||||
 | 
					    parser.add_argument('--password', default=None, help='Password of the multiworld host.')
 | 
				
			||||||
 | 
					    if not Utils.is_frozen():  # Frozen state has no cmd window in the first place
 | 
				
			||||||
 | 
					        parser.add_argument('--nogui', default=False, action='store_true', help="Turns off Client GUI.")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    args, rest = parser.parse_known_args()
 | 
				
			||||||
 | 
					    colorama.init()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    loop = asyncio.get_event_loop()
 | 
				
			||||||
 | 
					    loop.run_until_complete(main(args))
 | 
				
			||||||
 | 
					    loop.close()
 | 
				
			||||||
 | 
					    colorama.deinit()
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -10,7 +10,8 @@ import factorio_rcon
 | 
				
			||||||
import colorama
 | 
					import colorama
 | 
				
			||||||
import asyncio
 | 
					import asyncio
 | 
				
			||||||
from queue import Queue
 | 
					from queue import Queue
 | 
				
			||||||
from CommonClient import CommonContext, server_loop, console_loop, ClientCommandProcessor, logger, gui_enabled
 | 
					from CommonClient import CommonContext, server_loop, console_loop, ClientCommandProcessor, logger, gui_enabled, \
 | 
				
			||||||
 | 
					    init_logging
 | 
				
			||||||
from MultiServer import mark_raw
 | 
					from MultiServer import mark_raw
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import Utils
 | 
					import Utils
 | 
				
			||||||
| 
						 | 
					@ -19,17 +20,7 @@ from NetUtils import NetworkItem, ClientStatus, JSONtoTextParser, JSONMessagePar
 | 
				
			||||||
 | 
					
 | 
				
			||||||
from worlds.factorio import Factorio
 | 
					from worlds.factorio import Factorio
 | 
				
			||||||
 | 
					
 | 
				
			||||||
log_folder = Utils.local_path("logs")
 | 
					init_logging("FactorioClient")
 | 
				
			||||||
 | 
					 | 
				
			||||||
os.makedirs(log_folder, exist_ok=True)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
if gui_enabled:
 | 
					 | 
				
			||||||
    logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO,
 | 
					 | 
				
			||||||
                        filename=os.path.join(log_folder, "FactorioClient.txt"), filemode="w", force=True)
 | 
					 | 
				
			||||||
else:
 | 
					 | 
				
			||||||
    logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO, force=True)
 | 
					 | 
				
			||||||
    logging.getLogger().addHandler(logging.FileHandler(os.path.join(log_folder, "FactorioClient.txt"), "w"))
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class FactorioCommandProcessor(ClientCommandProcessor):
 | 
					class FactorioCommandProcessor(ClientCommandProcessor):
 | 
				
			||||||
| 
						 | 
					@ -66,7 +57,7 @@ class FactorioContext(CommonContext):
 | 
				
			||||||
        self.awaiting_bridge = False
 | 
					        self.awaiting_bridge = False
 | 
				
			||||||
        self.factorio_json_text_parser = FactorioJSONtoTextParser(self)
 | 
					        self.factorio_json_text_parser = FactorioJSONtoTextParser(self)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    async def server_auth(self, password_requested):
 | 
					    async def server_auth(self, password_requested: bool = False):
 | 
				
			||||||
        if password_requested and not self.password:
 | 
					        if password_requested and not self.password:
 | 
				
			||||||
            await super(FactorioContext, self).server_auth(password_requested)
 | 
					            await super(FactorioContext, self).server_auth(password_requested)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -268,13 +259,15 @@ async def factorio_spinup_server(ctx: FactorioContext) -> bool:
 | 
				
			||||||
        ctx.exit_event.set()
 | 
					        ctx.exit_event.set()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    else:
 | 
					    else:
 | 
				
			||||||
        logger.info(f"Got World Information from AP Mod {tuple(ctx.mod_version)} for seed {ctx.seed_name} in slot {ctx.auth}")
 | 
					        logger.info(
 | 
				
			||||||
 | 
					            f"Got World Information from AP Mod {tuple(ctx.mod_version)} for seed {ctx.seed_name} in slot {ctx.auth}")
 | 
				
			||||||
        return True
 | 
					        return True
 | 
				
			||||||
    finally:
 | 
					    finally:
 | 
				
			||||||
        factorio_process.terminate()
 | 
					        factorio_process.terminate()
 | 
				
			||||||
        factorio_process.wait(5)
 | 
					        factorio_process.wait(5)
 | 
				
			||||||
    return False
 | 
					    return False
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
async def main(args):
 | 
					async def main(args):
 | 
				
			||||||
    ctx = FactorioContext(args.connect, args.password)
 | 
					    ctx = FactorioContext(args.connect, args.password)
 | 
				
			||||||
    ctx.server_task = asyncio.create_task(server_loop(ctx), name="ServerLoop")
 | 
					    ctx.server_task = asyncio.create_task(server_loop(ctx), name="ServerLoop")
 | 
				
			||||||
| 
						 | 
					@ -345,7 +338,8 @@ if __name__ == '__main__':
 | 
				
			||||||
    args, rest = parser.parse_known_args()
 | 
					    args, rest = parser.parse_known_args()
 | 
				
			||||||
    colorama.init()
 | 
					    colorama.init()
 | 
				
			||||||
    rcon_port = args.rcon_port
 | 
					    rcon_port = args.rcon_port
 | 
				
			||||||
    rcon_password = args.rcon_password if args.rcon_password else ''.join(random.choice(string.ascii_letters) for x in range(32))
 | 
					    rcon_password = args.rcon_password if args.rcon_password else ''.join(
 | 
				
			||||||
 | 
					        random.choice(string.ascii_letters) for x in range(32))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    factorio_server_logger = logging.getLogger("FactorioServer")
 | 
					    factorio_server_logger = logging.getLogger("FactorioServer")
 | 
				
			||||||
    options = Utils.get_options()
 | 
					    options = Utils.get_options()
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -26,24 +26,14 @@ from NetUtils import *
 | 
				
			||||||
from worlds.alttp import Regions, Shops
 | 
					from worlds.alttp import Regions, Shops
 | 
				
			||||||
from worlds.alttp import Items
 | 
					from worlds.alttp import Items
 | 
				
			||||||
import Utils
 | 
					import Utils
 | 
				
			||||||
from CommonClient import CommonContext, server_loop, console_loop, ClientCommandProcessor, gui_enabled
 | 
					from CommonClient import CommonContext, server_loop, console_loop, ClientCommandProcessor, gui_enabled, init_logging
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					init_logging("LttPClient")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
snes_logger = logging.getLogger("SNES")
 | 
					snes_logger = logging.getLogger("SNES")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
from MultiServer import mark_raw
 | 
					from MultiServer import mark_raw
 | 
				
			||||||
 | 
					
 | 
				
			||||||
log_folder = Utils.local_path("logs")
 | 
					 | 
				
			||||||
os.makedirs(log_folder, exist_ok=True)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
# Log to file in gui case
 | 
					 | 
				
			||||||
if gui_enabled:
 | 
					 | 
				
			||||||
    logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO,
 | 
					 | 
				
			||||||
                        filename=os.path.join(log_folder, "LttPClient.txt"), filemode="w", force=True)
 | 
					 | 
				
			||||||
else:
 | 
					 | 
				
			||||||
    logging.basicConfig(format='[%(name)s]: %(message)s', level=logging.INFO, force=True)
 | 
					 | 
				
			||||||
    logging.getLogger().addHandler(logging.FileHandler(os.path.join(log_folder, "LttPClient.txt"), "w"))
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class LttPCommandProcessor(ClientCommandProcessor):
 | 
					class LttPCommandProcessor(ClientCommandProcessor):
 | 
				
			||||||
    def _cmd_slow_mode(self, toggle: str = ""):
 | 
					    def _cmd_slow_mode(self, toggle: str = ""):
 | 
				
			||||||
        """Toggle slow mode, which limits how fast you send / receive items."""
 | 
					        """Toggle slow mode, which limits how fast you send / receive items."""
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -54,9 +54,10 @@ Name: "generator/lttp"; Description: "A Link to the Past ROM Setup"; Types: full
 | 
				
			||||||
Name: "generator/oot"; Description: "Ocarina of Time ROM Setup"; Types: full hosting
 | 
					Name: "generator/oot"; Description: "Ocarina of Time ROM Setup"; Types: full hosting
 | 
				
			||||||
Name: "server"; Description: "Server"; Types: full hosting
 | 
					Name: "server"; Description: "Server"; Types: full hosting
 | 
				
			||||||
Name: "client"; Description: "Clients"; Types: full playing
 | 
					Name: "client"; Description: "Clients"; Types: full playing
 | 
				
			||||||
Name: "client/lttp"; Description: "A Link to the Past"; Types: full playing hosting
 | 
					Name: "client/lttp"; Description: "A Link to the Past"; Types: full playing
 | 
				
			||||||
Name: "client/factorio"; Description: "Factorio"; Types: full playing
 | 
					Name: "client/factorio"; Description: "Factorio"; Types: full playing
 | 
				
			||||||
Name: "client/minecraft"; Description: "Minecraft"; Types: full playing; ExtraDiskSpaceRequired: 226894278
 | 
					Name: "client/minecraft"; Description: "Minecraft"; Types: full playing; ExtraDiskSpaceRequired: 226894278
 | 
				
			||||||
 | 
					Name: "client/text"; Description: "Text, to !command and chat"; Types: full playing
 | 
				
			||||||
 | 
					
 | 
				
			||||||
[Dirs]
 | 
					[Dirs]
 | 
				
			||||||
NAME: "{app}"; Flags: setntfscompression; Permissions: everyone-modify users-modify authusers-modify;
 | 
					NAME: "{app}"; Flags: setntfscompression; Permissions: everyone-modify users-modify authusers-modify;
 | 
				
			||||||
| 
						 | 
					@ -71,6 +72,7 @@ Source: "{#sourcepath}\EnemizerCLI\*"; Excludes: "*.sfc, *.log"; DestDir: "{app}
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoGenerate.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: generator
 | 
					Source: "{#sourcepath}\ArchipelagoGenerate.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: generator
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoServer.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: server
 | 
					Source: "{#sourcepath}\ArchipelagoServer.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: server
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoFactorioClient.exe";  DestDir: "{app}"; Flags: ignoreversion; Components: client/factorio
 | 
					Source: "{#sourcepath}\ArchipelagoFactorioClient.exe";  DestDir: "{app}"; Flags: ignoreversion; Components: client/factorio
 | 
				
			||||||
 | 
					Source: "{#sourcepath}\ArchipelagoTextClient.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/text
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoLttPClient.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/lttp
 | 
					Source: "{#sourcepath}\ArchipelagoLttPClient.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/lttp
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoLttPAdjuster.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/lttp
 | 
					Source: "{#sourcepath}\ArchipelagoLttPAdjuster.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/lttp
 | 
				
			||||||
Source: "{#sourcepath}\ArchipelagoMinecraftClient.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/minecraft
 | 
					Source: "{#sourcepath}\ArchipelagoMinecraftClient.exe"; DestDir: "{app}"; Flags: ignoreversion; Components: client/minecraft
 | 
				
			||||||
| 
						 | 
					@ -82,6 +84,7 @@ Source: "{tmp}\forge-installer.jar"; DestDir: "{app}"; Flags: skipifsourcedoesnt
 | 
				
			||||||
[Icons]
 | 
					[Icons]
 | 
				
			||||||
Name: "{group}\{#MyAppName} Folder"; Filename: "{app}";
 | 
					Name: "{group}\{#MyAppName} Folder"; Filename: "{app}";
 | 
				
			||||||
Name: "{group}\{#MyAppName} Server"; Filename: "{app}\{#MyAppExeName}"; Components: server
 | 
					Name: "{group}\{#MyAppName} Server"; Filename: "{app}\{#MyAppExeName}"; Components: server
 | 
				
			||||||
 | 
					Name: "{group}\{#MyAppName} Text Client"; Filename: "{app}\ArchipelagoTextClient.exe"; Components: client/lttp
 | 
				
			||||||
Name: "{group}\{#MyAppName} LttP Client"; Filename: "{app}\ArchipelagoLttPClient.exe"; Components: client/lttp
 | 
					Name: "{group}\{#MyAppName} LttP Client"; Filename: "{app}\ArchipelagoLttPClient.exe"; Components: client/lttp
 | 
				
			||||||
Name: "{group}\{#MyAppName} Factorio Client"; Filename: "{app}\ArchipelagoFactorioClient.exe"; Components: client/factorio
 | 
					Name: "{group}\{#MyAppName} Factorio Client"; Filename: "{app}\ArchipelagoFactorioClient.exe"; Components: client/factorio
 | 
				
			||||||
Name: "{group}\{#MyAppName} Minecraft Client"; Filename: "{app}\ArchipelagoMinecraftClient.exe"; Components: client/minecraft
 | 
					Name: "{group}\{#MyAppName} Minecraft Client"; Filename: "{app}\ArchipelagoMinecraftClient.exe"; Components: client/minecraft
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										10
									
								
								kvui.py
								
								
								
								
							
							
						
						
									
										10
									
								
								kvui.py
								
								
								
								
							| 
						 | 
					@ -16,6 +16,7 @@ from kivy.lang import Builder
 | 
				
			||||||
import Utils
 | 
					import Utils
 | 
				
			||||||
from NetUtils import JSONtoTextParser, JSONMessagePart
 | 
					from NetUtils import JSONtoTextParser, JSONMessagePart
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class GameManager(App):
 | 
					class GameManager(App):
 | 
				
			||||||
    logging_pairs = [
 | 
					    logging_pairs = [
 | 
				
			||||||
        ("Client", "Archipelago"),
 | 
					        ("Client", "Archipelago"),
 | 
				
			||||||
| 
						 | 
					@ -83,6 +84,7 @@ class FactorioManager(GameManager):
 | 
				
			||||||
    ]
 | 
					    ]
 | 
				
			||||||
    title = "Archipelago Factorio Client"
 | 
					    title = "Archipelago Factorio Client"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class LttPManager(GameManager):
 | 
					class LttPManager(GameManager):
 | 
				
			||||||
    logging_pairs = [
 | 
					    logging_pairs = [
 | 
				
			||||||
        ("Client", "Archipelago"),
 | 
					        ("Client", "Archipelago"),
 | 
				
			||||||
| 
						 | 
					@ -90,6 +92,14 @@ class LttPManager(GameManager):
 | 
				
			||||||
    ]
 | 
					    ]
 | 
				
			||||||
    title = "Archipelago LttP Client"
 | 
					    title = "Archipelago LttP Client"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class TextManager(GameManager):
 | 
				
			||||||
 | 
					    logging_pairs = [
 | 
				
			||||||
 | 
					        ("Client", "Archipelago")
 | 
				
			||||||
 | 
					    ]
 | 
				
			||||||
 | 
					    title = "Archipelago Text Client"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class LogtoUI(logging.Handler):
 | 
					class LogtoUI(logging.Handler):
 | 
				
			||||||
    def __init__(self, on_log):
 | 
					    def __init__(self, on_log):
 | 
				
			||||||
        super(LogtoUI, self).__init__(logging.DEBUG)
 | 
					        super(LogtoUI, self).__init__(logging.DEBUG)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										1
									
								
								setup.py
								
								
								
								
							
							
						
						
									
										1
									
								
								setup.py
								
								
								
								
							| 
						 | 
					@ -74,6 +74,7 @@ scripts = {
 | 
				
			||||||
    # Core
 | 
					    # Core
 | 
				
			||||||
    "MultiServer.py": ("ArchipelagoServer", False, icon),
 | 
					    "MultiServer.py": ("ArchipelagoServer", False, icon),
 | 
				
			||||||
    "Generate.py": ("ArchipelagoGenerate", False, icon),
 | 
					    "Generate.py": ("ArchipelagoGenerate", False, icon),
 | 
				
			||||||
 | 
					    "CommonClient.py": ("ArchipelagoTextClient", True, icon),
 | 
				
			||||||
    # LttP
 | 
					    # LttP
 | 
				
			||||||
    "LttPClient.py": ("ArchipelagoLttPClient", True, icon),
 | 
					    "LttPClient.py": ("ArchipelagoLttPClient", True, icon),
 | 
				
			||||||
    "LttPAdjuster.py": ("ArchipelagoLttPAdjuster", True, icon),
 | 
					    "LttPAdjuster.py": ("ArchipelagoLttPAdjuster", True, icon),
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue