From c69198c97f9b8b2f0cee5b4b3274b38da164cf7d Mon Sep 17 00:00:00 2001 From: Andrei Karas Date: Mon, 29 Dec 2014 14:19:20 +0300 Subject: hercules: add support for convert npc scripts from tmw. --- hercules/code/server/evol/main.py | 2 +- hercules/code/server/evol/npcs.py | 281 ++++++++++++++++++++++++++++++++++++ hercules/code/server/npcs.py | 281 ------------------------------------ hercules/code/server/tmw/main.py | 4 +- hercules/code/server/tmw/npcs.py | 297 ++++++++++++++++++++++++++++++++++++++ 5 files changed, 581 insertions(+), 284 deletions(-) create mode 100644 hercules/code/server/evol/npcs.py delete mode 100644 hercules/code/server/npcs.py create mode 100644 hercules/code/server/tmw/npcs.py (limited to 'hercules/code') diff --git a/hercules/code/server/evol/main.py b/hercules/code/server/evol/main.py index 8919c76..15bde78 100644 --- a/hercules/code/server/evol/main.py +++ b/hercules/code/server/evol/main.py @@ -8,7 +8,7 @@ from code.server.consts import * from code.server.evol.itemdb import * from code.server.mobdb import * from code.server.mobskilldb import * -from code.server.npcs import * +from code.server.evol.npcs import * from code.server.utils import * from code.server.questsdb import * from code.serverutils import * diff --git a/hercules/code/server/evol/npcs.py b/hercules/code/server/evol/npcs.py new file mode 100644 index 0000000..2082b23 --- /dev/null +++ b/hercules/code/server/evol/npcs.py @@ -0,0 +1,281 @@ +# -*- coding: utf8 -*- +# +# Copyright (C) 2014 Evol Online +# Author: Andrei Karas (4144) + +import re + +from code.fileutils import * +from code.stringutils import * + +mapsConfFile = "newserverdata/conf/maps.conf" +mapsIndexFile = "newserverdata/db/map_index.txt" +npcMainScript = "newserverdata/npc/re/scripts_main.conf" +mapsIndex = 1 +scriptRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)(|,(?P[\d]+))" + + "[\t](?Pscript)[\t](?P[\w#' ]+)[\t]" + "(?P[\d]+)((,((?P[\d]+),(?P[\d]+)))|)(|;(?P[\d]+))(|,|;){$") + +shopRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)(|,(?P[\d]+))" + + "[\t](?Pshop)[\t](?P[\w#' ]+)[\t]" + "(?P[\d]+),(?P(.+))$") + +mapFlagRe = re.compile("^(?P[^/](.+))[.]gat" + + "[ ](?Pmapflag)[ ](?P[\w#']+)(|[ ](?P.*))$") + +warpRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)[\t]" + "(?Pwarp)[\t](?P[^\t]+)[\t](?P[\d-]+),(?P[\d-]+),(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)$") + +monsterRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d-]+),(?P[\d-]+)\t" + "(?Pmonster)[\t](?P[\w#' ]+)[\t]" + "(?P[\d]+),(?P[\d]+),(?P[\d-]+),(?P[\d]+),(?P[\d]+)$") + +setRe = re.compile("^(?P[ ]+)set[ ](?P[^,]+),([ ]*)(?P[^;]+);$"); + +class ScriptTracker: + pass + +def createMainScript(): + with open(npcMainScript, "w") as w: + w.write("npc: npc/functions/main.txt\n") + w.write("import: npc/scripts.conf\n") + +def convertNpcs(items): + processNpcDir("oldserverdata/npc/", "newserverdata/npc/", items) + +def processNpcDir(srcDir, dstDir, items): + makeDir(dstDir) + files = os.listdir(srcDir) + for file1 in files: + if file1[0] == '.': + continue + srcPath = os.path.abspath(srcDir + os.path.sep + file1) + dstPath = os.path.abspath(dstDir + os.path.sep + file1) + if not os.path.isfile(srcPath): + processNpcDir(srcPath, dstPath, items) + else: + if file1[-5:] == ".conf" or file1[-4:] == ".txt": + processNpcFile(srcPath, dstPath, items) + +def processNpcFile(srcFile, dstFile, items): +# print "file: " + srcFile + tracker = ScriptTracker() + tracker.insideScript = False + tracker.items = items + with open(srcFile, "r") as r: + with open(dstFile, "w") as w: + tracker.w = w + for line in r: + tracker.line = line + res = convertTextLine(tracker) + if res: + w.write(tracker.line) + +def convertTextLine(tracker): + line = tracker.line + if line[:5] == "map: ": + processScriptMapLine(line) + return False + + idx = line.find("\tscript\t") + if idx >= 0: + processScript(tracker) + return False + idx = line.find("\tshop\t") + if idx >= 0: + processShop(tracker) + return False + idx = line.find("\tmonster\t") + if idx >= 0: + processMonster(tracker) + return False + idx = line.find("\twarp\t") + if idx >= 0: + processWarp(tracker) + return False + idx = line.find(".gat mapflag ") + if idx >= 0: + processMapFlag(tracker) + return False + processStrReplace(tracker) + return False + +def processScriptMapLine(line): + global mapsIndex + line = stripNewLine(line) + if line[-4:] == ".gat": + line = line[:-4] + with open(mapsConfFile, "a") as w: + w.write(line + "\n") + + with open(mapsIndexFile, "a") as w: + w.write("{0} {1}\n".format(line[5:], mapsIndex)) + mapsIndex = mapsIndex + 1 + +def writeScript(w, m): + if m.group("gender") != None: + w.write("// Gender = {0}\n".format(m.group("gender"))); + + if m.group("x") == 0 and m.group("y") == 0: # float npc + w.write("-") + else: + w.write("{0},{1},{2},{3}".format(m.group("map"), m.group("x"), m.group("y"), m.group("dir"))) + class_ = m.group("class") + if class_ == "0": # hidden npc + class_ = "32767" + else: + class_ = int(class_) + if class_ > 125 and class_ <= 400: + class_ = class_ + 100 + w.write("\t{0}\t{1}\t{2}".format(m.group("tag"), m.group("name"), class_)); + +def processScript(tracker): + line = tracker.line + w = tracker.w + if line[:9] == "function\t": + tracker.w.write(line) + return + + m = scriptRe.search(line) + if m == None: + print "error in parsing: " + line + w.write("!!!error parsing line") + w.write(line) + return +# print "source=" + line[:-1] +# print "map={0} x={1} y={2} dir={3} gender={4} tag={5} name={6} class={7}, xs={8}, ys={9}, size={10}".format( +# m.group("map"), m.group("x"), m.group("y"), m.group("dir"), m.group("gender"), +# m.group("tag"), m.group("name"), m.group("class"), m.group("xs"), m.group("ys"), m.group("size")) + + if m.group("size") != None: + w.write("// Size = {0}\n".format(m.group("size"))); + writeScript(w, m) + if m.group("xs") != None: + w.write(",{0},{1}".format(m.group("xs"), m.group("ys"))); + w.write(",{\n"); + + +def itemsToShop(tracker, itemsStr): + itemsSplit = re.compile(",") + itemsSplit2 = re.compile(":") + itemsDict = tracker.items + outStr = "" + items = itemsSplit.split(itemsStr) + for str2 in items: + parts = itemsSplit2.split(str2) + if outStr != "": + outStr = outStr + "," + outStr = outStr + itemsDict[parts[0].strip()] + ":" + parts[1] + return outStr + +def processShop(tracker): + line = tracker.line + w = tracker.w + + m = shopRe.search(line) + if m == None: + print "error in parsing: " + line + w.write("!!!error parsing line") + w.write(line) + return +# print "source=" + line[:-1] +# print "map={0} x={1} y={2} dir={3} gender={4} tag={5} name={6} class={7} items={8}".format( +# m.group("map"), m.group("x"), m.group("y"), m.group("dir"), m.group("gender"), +# m.group("tag"), m.group("name"), m.group("class"), m.group("items")) + + writeScript(w, m) + w.write("," + itemsToShop(tracker, m.group("items")) + "\n") + +def processMapFlag(tracker): + line = tracker.line + w = tracker.w + + m = mapFlagRe.search(line) + if m == None: + print "error in parsing: " + line + w.write("!!!error parsing line") + w.write(line) + return +# print "source=" + line[:-1] +# print "map={0} tag={1} name={2} flag={3}".format( +# m.group("map"), m.group("tag"), m.group("name"), m.group("flag")) + + w.write("{0}\t{1}\t{2}".format(m.group("map"), m.group("tag"), m.group("name"))) + if m.group("flag") == None: + w.write("\n") + else: + w.write("\t{0}\n".format(m.group("flag"))) + +def processWarp(tracker): + line = tracker.line + w = tracker.w + m = warpRe.search(line) + if m == None: + print "error in parsing: " + line + w.write("!!!error parsing line") + w.write(line) + return + +# print "source=" + line[:-1] +# print "map={0} xy={1},{2} tag={3} name={4} xs={5} ys={6} target: map={7} xy={8},{9}".format( +# m.group("map"), m.group("x"), m.group("y"), m.group("tag"), m.group("name"), m.group("xs"), m.group("ys"), m.group("targetmap"), m.group("targetx"), m.group("targety")) + + xs = int(m.group("xs")) + ys = int(m.group("ys")) + if xs < 0: + xs = 0 + if ys < 0: + ys = 0 + w.write("{0},{1},{2},{3}\t{4}\t{5}\t{6},{7},{8},{9},{10}\n".format( + m.group("map"), m.group("x"), m.group("y"), "0", m.group("tag"), m.group("name"), + xs, ys, m.group("targetmap"), m.group("targetx"), m.group("targety"))) + + +def processMonster(tracker): + line = tracker.line + w = tracker.w + m = monsterRe.search(line) + if m == None: + print "error in parsing: " + line + w.write("!!!error parsing line") + w.write(line) + return + +# print "source=" + line[:-1] +# print ("map={0} xy={1},{2} xs={3} ys={4} tag={5} name={6} class={7} " + +# "num={8} look={9} delays={10},{11}").format( +# m.group("map"), m.group("x"), m.group("y"), m.group("xs"), m.group("ys"), +# m.group("tag"), m.group("name"), m.group("class"), +# m.group("num"), m.group("look"), m.group("delay1"), m.group("delay2")) + w.write("{0},{1},{2},{3},{4}\t{5}\t{6}\t{7},{8},{9},{10}\n".format(m.group("map"), + m.group("x"), m.group("y"), m.group("xs"), m.group("ys"), + m.group("tag"), m.group("name"), + m.group("class"), m.group("num"), m.group("delay1"), m.group("delay2"))) + + +def processStrReplace(tracker): + line = tracker.line + w = tracker.w + line = line.replace("setskill ", "addtoskill ") + line = line.replace("zeny", "Zeny") + line = line.replace("countitem(", "countitemcolor(") + line = line.replace("getclientversion(\"\")", "ClientVersion") + line = line.replace("getclientversion()", "ClientVersion") + line = line.replace("setlang @", "Lang = @") + line = re.sub("([^@^$])@([^@])", "\\1.@\\2", line) + line = line.replace(".@menu", "@menu") + idx = line.find("getmapmobs(") + if idx >= 0: + idx2 = line.find("\"", idx + len("getmapmobs(") + 1) + idx3 = line.find(")", idx + len("getmapmobs(") + 1) + if idx2 + 1 == idx3: + line = line[:idx2 + 1] + ",\"all\"" + line[idx2 + 1:] + + line = line.replace("getmapmobs(", "mobcount(") + + m = setRe.search(line); + if m != None: + line = "{0}{1} = {2};\n".format(m.group("space"), m.group("var"), m.group("val")) + + w.write(line) + diff --git a/hercules/code/server/npcs.py b/hercules/code/server/npcs.py deleted file mode 100644 index 2082b23..0000000 --- a/hercules/code/server/npcs.py +++ /dev/null @@ -1,281 +0,0 @@ -# -*- coding: utf8 -*- -# -# Copyright (C) 2014 Evol Online -# Author: Andrei Karas (4144) - -import re - -from code.fileutils import * -from code.stringutils import * - -mapsConfFile = "newserverdata/conf/maps.conf" -mapsIndexFile = "newserverdata/db/map_index.txt" -npcMainScript = "newserverdata/npc/re/scripts_main.conf" -mapsIndex = 1 -scriptRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)(|,(?P[\d]+))" + - "[\t](?Pscript)[\t](?P[\w#' ]+)[\t]" - "(?P[\d]+)((,((?P[\d]+),(?P[\d]+)))|)(|;(?P[\d]+))(|,|;){$") - -shopRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)(|,(?P[\d]+))" + - "[\t](?Pshop)[\t](?P[\w#' ]+)[\t]" - "(?P[\d]+),(?P(.+))$") - -mapFlagRe = re.compile("^(?P[^/](.+))[.]gat" + - "[ ](?Pmapflag)[ ](?P[\w#']+)(|[ ](?P.*))$") - -warpRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)[\t]" - "(?Pwarp)[\t](?P[^\t]+)[\t](?P[\d-]+),(?P[\d-]+),(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)$") - -monsterRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d-]+),(?P[\d-]+)\t" - "(?Pmonster)[\t](?P[\w#' ]+)[\t]" - "(?P[\d]+),(?P[\d]+),(?P[\d-]+),(?P[\d]+),(?P[\d]+)$") - -setRe = re.compile("^(?P[ ]+)set[ ](?P[^,]+),([ ]*)(?P[^;]+);$"); - -class ScriptTracker: - pass - -def createMainScript(): - with open(npcMainScript, "w") as w: - w.write("npc: npc/functions/main.txt\n") - w.write("import: npc/scripts.conf\n") - -def convertNpcs(items): - processNpcDir("oldserverdata/npc/", "newserverdata/npc/", items) - -def processNpcDir(srcDir, dstDir, items): - makeDir(dstDir) - files = os.listdir(srcDir) - for file1 in files: - if file1[0] == '.': - continue - srcPath = os.path.abspath(srcDir + os.path.sep + file1) - dstPath = os.path.abspath(dstDir + os.path.sep + file1) - if not os.path.isfile(srcPath): - processNpcDir(srcPath, dstPath, items) - else: - if file1[-5:] == ".conf" or file1[-4:] == ".txt": - processNpcFile(srcPath, dstPath, items) - -def processNpcFile(srcFile, dstFile, items): -# print "file: " + srcFile - tracker = ScriptTracker() - tracker.insideScript = False - tracker.items = items - with open(srcFile, "r") as r: - with open(dstFile, "w") as w: - tracker.w = w - for line in r: - tracker.line = line - res = convertTextLine(tracker) - if res: - w.write(tracker.line) - -def convertTextLine(tracker): - line = tracker.line - if line[:5] == "map: ": - processScriptMapLine(line) - return False - - idx = line.find("\tscript\t") - if idx >= 0: - processScript(tracker) - return False - idx = line.find("\tshop\t") - if idx >= 0: - processShop(tracker) - return False - idx = line.find("\tmonster\t") - if idx >= 0: - processMonster(tracker) - return False - idx = line.find("\twarp\t") - if idx >= 0: - processWarp(tracker) - return False - idx = line.find(".gat mapflag ") - if idx >= 0: - processMapFlag(tracker) - return False - processStrReplace(tracker) - return False - -def processScriptMapLine(line): - global mapsIndex - line = stripNewLine(line) - if line[-4:] == ".gat": - line = line[:-4] - with open(mapsConfFile, "a") as w: - w.write(line + "\n") - - with open(mapsIndexFile, "a") as w: - w.write("{0} {1}\n".format(line[5:], mapsIndex)) - mapsIndex = mapsIndex + 1 - -def writeScript(w, m): - if m.group("gender") != None: - w.write("// Gender = {0}\n".format(m.group("gender"))); - - if m.group("x") == 0 and m.group("y") == 0: # float npc - w.write("-") - else: - w.write("{0},{1},{2},{3}".format(m.group("map"), m.group("x"), m.group("y"), m.group("dir"))) - class_ = m.group("class") - if class_ == "0": # hidden npc - class_ = "32767" - else: - class_ = int(class_) - if class_ > 125 and class_ <= 400: - class_ = class_ + 100 - w.write("\t{0}\t{1}\t{2}".format(m.group("tag"), m.group("name"), class_)); - -def processScript(tracker): - line = tracker.line - w = tracker.w - if line[:9] == "function\t": - tracker.w.write(line) - return - - m = scriptRe.search(line) - if m == None: - print "error in parsing: " + line - w.write("!!!error parsing line") - w.write(line) - return -# print "source=" + line[:-1] -# print "map={0} x={1} y={2} dir={3} gender={4} tag={5} name={6} class={7}, xs={8}, ys={9}, size={10}".format( -# m.group("map"), m.group("x"), m.group("y"), m.group("dir"), m.group("gender"), -# m.group("tag"), m.group("name"), m.group("class"), m.group("xs"), m.group("ys"), m.group("size")) - - if m.group("size") != None: - w.write("// Size = {0}\n".format(m.group("size"))); - writeScript(w, m) - if m.group("xs") != None: - w.write(",{0},{1}".format(m.group("xs"), m.group("ys"))); - w.write(",{\n"); - - -def itemsToShop(tracker, itemsStr): - itemsSplit = re.compile(",") - itemsSplit2 = re.compile(":") - itemsDict = tracker.items - outStr = "" - items = itemsSplit.split(itemsStr) - for str2 in items: - parts = itemsSplit2.split(str2) - if outStr != "": - outStr = outStr + "," - outStr = outStr + itemsDict[parts[0].strip()] + ":" + parts[1] - return outStr - -def processShop(tracker): - line = tracker.line - w = tracker.w - - m = shopRe.search(line) - if m == None: - print "error in parsing: " + line - w.write("!!!error parsing line") - w.write(line) - return -# print "source=" + line[:-1] -# print "map={0} x={1} y={2} dir={3} gender={4} tag={5} name={6} class={7} items={8}".format( -# m.group("map"), m.group("x"), m.group("y"), m.group("dir"), m.group("gender"), -# m.group("tag"), m.group("name"), m.group("class"), m.group("items")) - - writeScript(w, m) - w.write("," + itemsToShop(tracker, m.group("items")) + "\n") - -def processMapFlag(tracker): - line = tracker.line - w = tracker.w - - m = mapFlagRe.search(line) - if m == None: - print "error in parsing: " + line - w.write("!!!error parsing line") - w.write(line) - return -# print "source=" + line[:-1] -# print "map={0} tag={1} name={2} flag={3}".format( -# m.group("map"), m.group("tag"), m.group("name"), m.group("flag")) - - w.write("{0}\t{1}\t{2}".format(m.group("map"), m.group("tag"), m.group("name"))) - if m.group("flag") == None: - w.write("\n") - else: - w.write("\t{0}\n".format(m.group("flag"))) - -def processWarp(tracker): - line = tracker.line - w = tracker.w - m = warpRe.search(line) - if m == None: - print "error in parsing: " + line - w.write("!!!error parsing line") - w.write(line) - return - -# print "source=" + line[:-1] -# print "map={0} xy={1},{2} tag={3} name={4} xs={5} ys={6} target: map={7} xy={8},{9}".format( -# m.group("map"), m.group("x"), m.group("y"), m.group("tag"), m.group("name"), m.group("xs"), m.group("ys"), m.group("targetmap"), m.group("targetx"), m.group("targety")) - - xs = int(m.group("xs")) - ys = int(m.group("ys")) - if xs < 0: - xs = 0 - if ys < 0: - ys = 0 - w.write("{0},{1},{2},{3}\t{4}\t{5}\t{6},{7},{8},{9},{10}\n".format( - m.group("map"), m.group("x"), m.group("y"), "0", m.group("tag"), m.group("name"), - xs, ys, m.group("targetmap"), m.group("targetx"), m.group("targety"))) - - -def processMonster(tracker): - line = tracker.line - w = tracker.w - m = monsterRe.search(line) - if m == None: - print "error in parsing: " + line - w.write("!!!error parsing line") - w.write(line) - return - -# print "source=" + line[:-1] -# print ("map={0} xy={1},{2} xs={3} ys={4} tag={5} name={6} class={7} " + -# "num={8} look={9} delays={10},{11}").format( -# m.group("map"), m.group("x"), m.group("y"), m.group("xs"), m.group("ys"), -# m.group("tag"), m.group("name"), m.group("class"), -# m.group("num"), m.group("look"), m.group("delay1"), m.group("delay2")) - w.write("{0},{1},{2},{3},{4}\t{5}\t{6}\t{7},{8},{9},{10}\n".format(m.group("map"), - m.group("x"), m.group("y"), m.group("xs"), m.group("ys"), - m.group("tag"), m.group("name"), - m.group("class"), m.group("num"), m.group("delay1"), m.group("delay2"))) - - -def processStrReplace(tracker): - line = tracker.line - w = tracker.w - line = line.replace("setskill ", "addtoskill ") - line = line.replace("zeny", "Zeny") - line = line.replace("countitem(", "countitemcolor(") - line = line.replace("getclientversion(\"\")", "ClientVersion") - line = line.replace("getclientversion()", "ClientVersion") - line = line.replace("setlang @", "Lang = @") - line = re.sub("([^@^$])@([^@])", "\\1.@\\2", line) - line = line.replace(".@menu", "@menu") - idx = line.find("getmapmobs(") - if idx >= 0: - idx2 = line.find("\"", idx + len("getmapmobs(") + 1) - idx3 = line.find(")", idx + len("getmapmobs(") + 1) - if idx2 + 1 == idx3: - line = line[:idx2 + 1] + ",\"all\"" + line[idx2 + 1:] - - line = line.replace("getmapmobs(", "mobcount(") - - m = setRe.search(line); - if m != None: - line = "{0}{1} = {2};\n".format(m.group("space"), m.group("var"), m.group("val")) - - w.write(line) - diff --git a/hercules/code/server/tmw/main.py b/hercules/code/server/tmw/main.py index bd4f5eb..9512a97 100644 --- a/hercules/code/server/tmw/main.py +++ b/hercules/code/server/tmw/main.py @@ -8,7 +8,7 @@ from code.server.consts import * from code.server.tmw.itemdb import * from code.server.mobdb import * from code.server.mobskilldb import * -from code.server.npcs import * +from code.server.tmw.npcs import * from code.server.utils import * from code.server.questsdb import * from code.serverutils import * @@ -17,7 +17,7 @@ def serverTmwMain(): cleanServerData() createMainScript() items = convertItemDb() - #convertNpcs(items) + convertNpcs(items) #convertMobDb() #quests = convertQuestsDb() #convertConsts(quests) diff --git a/hercules/code/server/tmw/npcs.py b/hercules/code/server/tmw/npcs.py new file mode 100644 index 0000000..f4b3ef6 --- /dev/null +++ b/hercules/code/server/tmw/npcs.py @@ -0,0 +1,297 @@ +# -*- coding: utf8 -*- +# +# Copyright (C) 2014 Evol Online +# Author: Andrei Karas (4144) + +import re + +from code.fileutils import * +from code.stringutils import * + +mapsConfFile = "newserverdata/conf/maps.conf" +mapsIndexFile = "newserverdata/db/map_index.txt" +npcMainScript = "newserverdata/npc/re/scripts_main.conf" +mapsIndex = 1 +scriptRe = re.compile("^(((?P[^/](.+))([.]gat|),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+))|(?Pfunction)|-)" + + "[|](?Pscript)[|](?P[^|]+)([|]" + "(?P[\d-]+)((,((?P[\d]+),(?P[\d]+)))|)|)$") + +shopRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)(|,(?P[\d]+))" + + "[|](?Pshop)[|](?P[\w#' ]+)[|]" + "(?P[\d]+),(?P(.+))$") + +mapFlagRe = re.compile("^(?P[^/](.+))[.]gat" + + "[|](?Pmapflag)[|](?P[\w#']+)(|[|](?P.*))$") + +warpRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)[|]" + "(?Pwarp)[|](?P[^|]+)[|](?P[\d-]+),(?P[\d-]+),(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+)$") + +monsterRe = re.compile("^(?P[^/](.+))[.]gat,([ ]*)(?P[\d]+),([ ]*)(?P[\d]+),([ ]*)(?P[\d-]+),(?P[\d-]+)[|]" + "(?Pmonster)[|](?P[\w#' ]+)[|]" + "(?P[\d]+),(?P[\d]+),(?P[\d]+)ms,(?P[\d]+)ms(|,(?P