2023-05-14 15:12:17 +10:00
import encode , decode , shared
2022-12-21 15:22:44 +11:00
import tables
import os
conf = { }
confp = os . path . expanduser ( ' ~/.config/swat.cfg ' ) # This won't work on Windows. You'll need to tweak this to run it on Windows. Not my problem.
2023-05-14 15:12:17 +10:00
defaults = { ' classes ' : [ ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 0 , 0 ) , ( 0 , 0 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) ] , ' guns ' : [ ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 0 , 0 ) , ( 0 , 0 ) , ( 0 , 0 ) ] , ' armour ' : [ ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) ] , ' traits ' : [ ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) ] , ' specs ' : [ ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) ] , ' talents ' : [ ( 12 , 12 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) , ( 1 , 3 ) ] , ' medals ' : { } }
2022-12-21 15:22:44 +11:00
def add_user ( name ) :
namehash = encode . hash_name ( name ) # Store the hash so that if they request a different name that happens to have the same hash, it can just be stored together.
if namehash in conf : conf [ namehash ] [ ' names ' ] . add ( name )
else : conf [ namehash ] = defaults . copy ( ) | { ' names ' : { name } }
save_conf ( )
global active_profile
active_profile = namehash
def parse_conf_line ( line ) :
a = line . split ( ' ' )
out = [ ]
for n in a :
b = n . split ( ' / ' )
out . append ( ( int ( b [ 0 ] ) , int ( b [ 1 ] ) ) )
return out
def load_conf ( ) :
if not os . path . exists ( confp ) : return
a = open ( confp ) . read ( )
for n in a . split ( ' \n \n ' ) :
lines = n . split ( ' \n ' )
header = lines [ 0 ] . split ( ' ' )
nhash = int ( header [ 0 ] ) ; names = set ( header [ 1 : ] ) # Makes deduping way easier
2023-05-14 15:12:17 +10:00
medals = { }
if ' : ' in lines [ - 1 ] : # Since this isn't used in any other line, it's safe
medals = { n . split ( ' : ' ) [ 0 ] : n . split ( ' : ' ) [ 1 ] for n in lines . pop ( - 1 ) . split ( ' ' ) }
2022-12-21 15:22:44 +11:00
stuff = { k : parse_conf_line ( v ) for k , v in zip ( tables . displays_str [ : - 1 ] , lines [ 1 : ] ) }
2023-05-14 15:12:17 +10:00
conf [ nhash ] = { ' names ' : names } | stuff | { ' medals ' : medals }
2022-12-21 15:22:44 +11:00
update_all_talents ( )
global active_profile
active_profile = nhash
def unparse_conf_line ( line ) :
return ' ' . join ( [ str ( n [ 0 ] ) + ' / ' + str ( n [ 1 ] ) for n in line ] )
def save_conf ( ) :
write = ' '
for k , v in conf . items ( ) :
write + = ' ' . join ( [ str ( k ) ] + list ( v [ ' names ' ] ) ) + ' \n '
for n in map ( lambda x : unparse_conf_line ( v [ x ] ) , tables . displays_str [ : - 1 ] ) :
write + = n + ' \n '
2023-05-14 15:12:17 +10:00
write + = ' ' . join ( f ' { h } : { m } ' for h , m in v [ ' medals ' ] . items ( ) ) + ' \n '
2022-12-21 15:22:44 +11:00
write + = ' \n '
write = write [ : - 2 ]
open ( confp , ' w ' ) . write ( write )
def update_all_talents ( ) :
for profile in conf :
cl = dict ( enumerate ( conf [ profile ] [ ' classes ' ] ) )
t = defaults [ ' talents ' ] . copy ( )
conf [ profile ] [ ' talents ' ] = t
for n in range ( 1 , 7 ) :
t [ n ] = update_talent ( n , cl )
def update_talents ( clas , profile = None ) :
if profile is None : profile = active_profile
cl = dict ( enumerate ( conf [ profile ] [ ' classes ' ] ) )
for talent in tables . clas [ clas ] [ 1 : ] : # Don't care about courage
conf [ profile ] [ ' talents ' ] [ talent ] = update_talent ( talent , cl )
def update_talent ( talent , classes ) :
a = enumerate ( tables . clas ) ; b = filter ( lambda x : talent in x [ 1 ] , a ) ; c = list ( map ( lambda x : x [ 0 ] , b ) ) ; d = filter ( lambda x : x [ 0 ] in c , classes . items ( ) ) ; rel_classes = list ( map ( lambda x : x [ 1 ] , d ) )
ranks , caps = [ ] , [ ]
for n in rel_classes : ranks . append ( n [ 0 ] ) ; caps . append ( n [ 1 ] )
ranks , caps = sorted ( ranks ) , sorted ( caps )
lon = len ( ranks ) / / 2 + len ( ranks ) % 2
return ( ranks [ - lon ] , caps [ - lon ] )
def read_code ( code , save = True ) :
data = list ( decode . decode ( code , active_profile ) )
check , validator = data . pop ( - 1 ) , data . pop ( - 1 )
talent = data . pop ( 5 )
hero = data [ 0 : 6 ]
show = list ( map ( lambda x : x [ 0 ] [ x [ 1 ] ] , zip ( tables . displays , hero ) ) )
rank , cap = data [ 6 : 8 ]
2023-04-20 00:00:04 +10:00
cap = tables . cap [ cap ]
if rank == 12 : cap = 12
2022-12-21 15:22:44 +11:00
data = data [ 8 : ]
if rank < 9 : show [ - 1 ] = ' Hidden ' # Don't spoil the talent
print ( show )
print ( str ( rank ) + ' / ' + str ( cap ) )
2023-05-14 15:12:17 +10:00
print ( data ) # Extract medals and save them
medals = data [ 1 : - 1 ]
if any ( medals ) : conf [ active_profile ] [ ' medals ' ] [ shared . muxhero ( hero [ 0 ] , hero [ 3 ] , hero [ 4 ] ) ] = shared . muxmedals ( medals )
2022-12-21 15:22:44 +11:00
if not check : print ( ' No name given, code validation not performed ' )
else :
if check != validator : print ( ' code did not validate: ' , validator , check ) ; return
else : print ( ' code validated ' )
for thing in zip ( tables . displays_str [ : - 1 ] , hero ) :
saved = conf [ active_profile ] [ thing [ 0 ] ] [ thing [ 1 ] ]
saved = ( max ( saved [ 0 ] , rank ) , max ( saved [ 1 ] , cap ) )
conf [ active_profile ] [ thing [ 0 ] ] [ thing [ 1 ] ] = saved
update_talents ( hero [ 0 ] )
2023-05-14 15:12:17 +10:00
if not save : return
2022-12-21 15:22:44 +11:00
save_conf ( )
def mass_add ( ) :
a = input ( ' > ' )
while a :
2023-05-14 15:12:17 +10:00
try : read_code ( a , false )
2022-12-21 15:22:44 +11:00
except : pass
a = input ( ' > ' )
2023-05-14 15:12:17 +10:00
save_conf ( )
2022-12-21 15:22:44 +11:00
def generate ( officer = None ) :
pro = conf [ active_profile ]
if officer is None : officer = input ( ' > ' )
pieces = officer . split ( ' / ' )
c = pieces [ 0 ] . lower ( )
if ' mav ' in c :
gun = c [ 0 ]
pieces [ 0 ] = ' mav '
elif ' wm ' in c :
gun = c [ 0 : 2 ]
pieces [ 0 ] = ' wm '
else : gun = ' '
out = [ ]
rank , cap = 12 , 12
for n in zip ( pieces , tables . displays_nogun , tables . displays_nogun_str ) :
ind = lookup_piece ( n [ 0 ] , n [ 1 ] )
rank , cap = min ( rank , pro [ n [ 2 ] ] [ ind ] [ 0 ] ) , min ( cap , pro [ n [ 2 ] ] [ ind ] [ 1 ] )
out . append ( ind )
cap = ( cap - ( cap < 10 ) + ( cap > 10 ) ) / / 3 # Derp
2023-01-02 23:36:34 +11:00
if gun : out . insert ( 1 , lookup_piece ( gun , tables . guns , True ) )
2022-12-21 15:22:44 +11:00
else : out . insert ( 1 , tables . gunmaps_wrapped [ out [ 0 ] ] )
out [ - 1 ] = tables . clas [ out [ 0 ] ] . index ( out [ - 1 ] )
2023-05-14 15:12:17 +10:00
muxed = shared . muxhero ( out [ 0 ] , out [ 3 ] , out [ 4 ] )
meds = [ ]
if muxed in pro [ ' medals ' ] : meds = shared . muxmedals ( pro [ ' medals ' ] [ muxed ] )
return encode . encode ( active_profile , * out , rank , cap , 0 , * meds )
2022-12-21 15:22:44 +11:00
2023-01-02 23:36:34 +11:00
def lookup_piece ( piece , table , partial = False ) :
2022-12-21 15:22:44 +11:00
if len ( piece ) < 3 : p = piece . upper ( )
else : p = piece . capitalize ( ) # Bloody Americans
2023-01-02 23:36:34 +11:00
if not partial :
try : return table . index ( p )
except ValueError : return None
res = list ( filter ( lambda x : x . startswith ( p ) , table ) )
if len ( res ) != 1 : return None # Ambiguous lookups not allowed
return table . index ( res [ 0 ] )
2022-12-21 15:22:44 +11:00
def ranks ( ) :
for n , m in zip ( tables . displays_str , tables . displays ) :
a = zip ( m , conf [ active_profile ] [ n ] )
for o in a :
print ( f ' { o [ 0 ] } : { o [ 1 ] [ 0 ] } / { o [ 1 ] [ 1 ] } ' , end = ' , ' )
print ( )
2023-05-14 15:12:17 +10:00
load_conf ( )
if __name__ == " __main__ " : print ( " Please open an interpreter and use ' import codegen ' , this script doesn ' t serve as an entrypoint on its own yet. " )