import es
import playerlib
import random
import gamethread

import wcs
from wcs import wcs

raceName = 'Pandaren Brewmaster'
race     = wcs.Race(raceName)

""" Load the strings into the variable text """
text     = race.loadStrings()

""" ############################### """
""" ### Begin the configuration ### """
""" ############################### """

config   = race.config()

config.addComment('********************')
config.addComment('Breath of Fire')
config.addComment('  When a player damages another player, they have a chance to')
config.addComment('  cause initial damage, followed by burn damage.')
config.addComment('********************')
config.addComment()
breathMaxLevel          = config.addVar('breathMaxLevel',      5, 'The maximum level for the Breath of Fire Skill')
breathLevelInterval     = config.addVar('breathLevelInterval', 2, 'The intervals between the abilities to upgrade their Breath of Fire skill')
breathDamage            = config.addVar('breathDamage',        3, 'This is the amount of additional damage gave multiplied by their level')

config.addComment()
config.addComment('********************')
config.addComment('Drunken Brawler')
config.addComment('    This skill gives a chance to dodge attacks, and deal more damage')
config.addComment('********************')
config.addComment()
brawlerMaxLevel         = config.addVar('brawlerMaxLevel',      5, 'The maximum level for the Drunken Brawler skill')
brawlerLevelInterval    = config.addVar('brawlerLevelInterval', 3, 'The intervals between the abilities to upgrade their Drunken Brawler skill')
brawlerPercentage       = config.addVar('brawlerPercentage',   10, 'The percent of the real damage that will be dealt to the victim, multiplied via their level.') 

config.addComment()
config.addComment('********************')
config.addComment('Drunken Haze')
config.addComment('  Decrease victim\'s speed')
config.addComment('********************')
config.addComment()
hazeMaxLevel            = config.addVar('hazeMaxLevel',      5, 'The maximum level for the Drunken Haze skill')
hazeLevelInterval       = config.addVar('hazeLevelInterval', 5, 'The intervals between the abilities to upgrade their Reincarnation skill')
config.addComment('This is relative to the player\'s level, and determines how long the player will be slowed for.')
hazePercent             = config.addVar('hazePercent',      50, 'For example, if this was 50, and the players level was 5, the player would be slowed for 2.5 seconds (50% of 5)')

config.addComment()
config.addComment('********************')
config.addComment('Storm, Earth and Fire')
config.addComment('  This ultimate allows you to charge yourself ') 
config.addComment('  to become either storm, earth or fire. Each ') 
config.addComment('  \'element\' has it\'s own special abilities and')
config.addComment('  attributes. The better the level, the longer the time.')
config.addComment('  allowed to be inside this mode.')
config.addComment('********************')
config.addComment()
stormMinLevel           = config.addVar('stormMinLevel',        8,  'The level required before this ultimate can be bought')
stormMaxLevel           = config.addVar('stormMaxLevel',        8,  'The maximum level for the Storm, Earth and Fire skill')
stormLevelInterval      = config.addVar('stormLevelInterval',   4,  'The interval between the skill upgrades')
stormCoolDown           = config.addVar('stormCoolDown',        45, 'The amount of seconds after a player has used their ultimate that they cannot use it again')
stormTime               = config.addVar('stormTime',            4,  'The amount of time stayed in the element form, multiplied by their level.')

config.load(True)

""" ##################### """
""" ### END OF CONFIG ### """
""" ##################### """

race.registerSkill('Breath of Fire', int(breathMaxLevel), int(breathLevelInterval), 'Cause initial damage, followed by burn damage.')
race.registerSkill('Drunken Haze', int(hazeMaxLevel), int(hazeLevelInterval), 'Your victims speed decreases')
race.registerSkill('Drunken Brawler', int(brawlerMaxLevel), int(brawlerLevelInterval), 'Have a chance to dodge enemy attacks, and deal more damage.')
race.registerUltimate('Storm, Earth and Fire', int(stormMinLevel), int(stormMaxLevel), int(stormLevelInterval), 'Turn into Fire, Earth or Storm!')

race.registerMinLevel(30)
race.registerTeamLimit(3)

def load():
    es.doblock('corelib/noisy_on')
    gamethread.delayed(1, (lambda x: es.ServerVar(x, 1) if not int(es.ServerVar(x))  else ''), 'eventscripts_noisy')
    
def unload():
    es.doblock('corelib/noisy_off')
    
def player_spawn(ev):
    userid = ev['userid']
    storm  = wcs.GetLevel(userid, raceName, 'Storm, Earth and Fire')
    if storm:
        wcs.Command(userid).UpdateDict('brewElement', '')
        wcs.Command(userid).UpdateDict('brewCounter', 0)
        
def player_death(ev):
    if wcs.GetLevel(ev['userid'], raceName, 'Storm, Earth and Fire'):
        if wcs.Command(ev['userid']).ReturnDict('brewCounter'):
            transformBack(ev['userid'])
            
def player_hurt(ev):
    userid   = ev['userid']
    attacker = ev['attacker']
    if not int(ev['es_userdead']):
        dblevelu = wcs.GetLevel(userid, raceName, 'Drunken Brawler')
        dblevela = wcs.GetLevel(attacker, raceName, 'Drunken Brawler')
        dhlevel  = wcs.GetLevel(attacker, raceName, 'Drunken Haze')
        boflevel = wcs.GetLevel(attacker, raceName, 'Breath of Fire')
        
        if dblevelu and (random.randint(1,20) <= dblevelu):
            wcs.Command(userid).Heal(int(ev['dmg_health']))
            es.tell(userid, '#multi', text('drunken brawler dodge', lang = playerlib.getPlayer(userid).get("lang") ) )
            
        if dblevela and int(ev['dmg_health']) > 20 and (random.randint(1,20) <= dblevela):
            wcs.Command(userid).Damage((int(ev['dmg_health']) * dblevela * (int(brawlerPercentage) / 100.)), 32, attacker)
            es.tell(attacker, '#multi', text('drunken brawler damage', lang = playerlib.getPlayer(attacker).get("lang") ) )
            
        if dhlevel and (random.randint(1,20) <= dhlevel):
            wcs.Command(userid).SpeedAdd(dhlevel * -0.05)
            gamethread.delayed(dhlevel * (int(hazePercent) / 100.), normalSpeed, (userid, attacker, dhlevel))
            es.tell(attacker, '#multi', text('drunken haze', lang = playerlib.getPlayer(attacker).get("lang") ) )
            
        if boflevel and (random.randint(1,20) <= boflevel):
            wcs.Command(userid).Damage(boflevel * int(breathDamage), 32, attacker)
            wcs.Command(userid).Burn(boflevel)
            es.tell(attacker, '#multi', text('breath of fire', lang = playerlib.getPlayer(attacker).get("lang") ) )
            
def player_footstep(ev):
	userid = ev['userid']
	if wcs.GetLevel(userid, raceName, 'Storm, Earth and Fire') and wcs.Command(userid).ReturnDict('brewElement'):
	
		element = wcs.Command(userid).ReturnDict('brewElement')
		level   = wcs.GetLevel(userid, raceName, 'Storm, Earth and Fire')
		filt    = '%s'%('#t' if int(es.getplayerteam(userid)) == 3 else '#ct')
		
		if element == 'Fire':
			wcs.effect.Follow(userid, 255, 0, 0)
			wcs.effect.Ring3(userid, random.randint(20,80), random.randint(1,3), 255, 0, 0)
			wcs.Command(userid).Near(level * 50, burn, ('#t' if int(es.getplayerteam(userid)) == 3 else '#ct') )
			
		elif element == 'Storm':
			es.emitsound('player', userid, 'player/footsteps/mud%s.wav' % random.randint(1,4), '1.0', '0.4')
			wcs.effect.Ring1(userid, 30, 1, 0, 0, 255)
			gamethread.delayed(1,wcs.effect.Ring1, (userid, 50, 1, 0, 0, 255))
			wcs.Command(userid).Near(level * 50, shock, ('#t' if int(es.getplayerteam(userid)) == 3 else '#ct') )
			
		elif element == 'Earth':
			es.emitsound('player', userid, 'ambient/explosions/explode_%s.wav' % random.choice(['5','8','9']), '1.0', '0.0')
			wcs.effect.Ring2(userid, random.randint(80, 100), 1, 128, 128, 128) 
			wcs.Command(userid).Near(level * 50, shake, ('#t' if int(es.getplayerteam(userid)) == 3 else '#ct') )

def burn(userid, attacker):
    #wcs.Command(userid).GetWallBetween(attacker, checkBurn, userid):
    # getWallBetween = broken!!! 
    wcs.Command(userid).Burn(5)

def shock(userid, attacker):
    #wcs.Command(userid).GetWallBetween(attacker, checkShock, userid):
    # getWallBetween = broken!!!
    wcs.Command(userid).Freeze(1)
    wcs.Command(userid).Shake(1, 3)
    es.emitsound('player', userid, 'ambient/energy/zap3.wav', '0.5', '0.6')
    wcs.effect.Beam1(attacker, userid, 3, random.randint(1,255), 0, random.randint(1,255))
	
def shake(userid, attacker):
    #wcs.Command(userid).GetWallBetween(attacker, checkShake, userid):
    # getWallBetween = broken!!!
    wcs.Command(userid).Shake(2, 5)
    wcs.Command(userid).Push(0, 0, 150)
    if random.randint(1,5) == 1:
        wcs.Command(userid).Drop()
    wcs.effect.Ring2(userid, 100, 2, 255, 255, 255)
		
def normalSpeed(userid, attacker, dhlevel):
    if not es.getplayerprop(userid, 'CBasePlayer.pl.deadflag'):
        wcs.Command(userid).SpeedAdd(dhlevel * 0.05)
		
def player_ultimate_on(ev):
    userid = ev['userid']
    storm = wcs.GetLevel(userid, raceName, 'Storm, Earth and Fire')
    if storm:
        wcs.Command(userid).UpdateDict('brewElement', '')
        wcs.Command(userid).UpdateDict('brewCounter', 0)
        increment(userid)

def increment(userid):
    wcs.Command(userid).Freeze(1)
    loopCounter = wcs.Command(userid).ReturnDict('brewCounter')
    es.emitsound('player', userid, 'buttons/blip2.wav', 0.5, 0.5)
    wcs.effect.Ring2(userid, loopCounter * 15, 11 - loopCounter, random.randint(1,255), random.randint(1,255), random.randint(1,255) )
    if loopCounter < 10:
        wcs.Command(userid).HudHint("%s\n%s" % (text('charging', lang = playerlib.getPlayer(userid).get("lang") ), '|' * (loopCounter + 1) ) )
        wcs.Command(userid).ModDict('brewCounter', 1)
        wcs.Command(userid).Delayed(1, increment, userid, True, 'brew_%s' % userid)
    else:
        es.cexec(userid, '-ultimate')
		
def player_ultimate_off(ev):
    userid = ev['userid']
    storm  = wcs.GetLevel(userid, raceName, 'Storm, Earth and Fire')
    if storm:
        gamethread.cancelDelayed('brew_%s'%userid)
        if not int(ev['cooldown']):
            command = wcs.Command(userid)
            looped = command.ReturnDict('brewCounter')
            if looped < 10:
                command.SetCoolDown('Storm, Earth and Fire', looped)
            else:
                element = random.choice(['Storm','Earth','Fire'])
                command.SetCoolDown('Storm, Earth and Fire', int(stormCoolDown) )
                command.UpdateDict('brewElement', element)
                
                if element == 'Storm':
                    alpha = command.ReturnDict('Alpha')
                    command.Color('grey',alpha=alpha/2.0)
                    command.ChangeGravity(-0.3)
                    command.SpeedAdd(0.3)
                    atmosphereStorm(userid)
                    
                elif element == 'Earth':
                    command.Color('brown')
                    command.ChangeGravity(0.3)
                    command.SpeedAdd(-0.3)
                    command.HealthAdd(100)
                else:
                    command.Color('red')
                    es.emitsound('player',userid,'ambient/fire/mtov_flame2.wav','1.0','0.0')
                tokens            = {}
                tokens['element'] = element
                es.tell(userid, '#multi', text('transformed', tokens, playerlib.getPlayer(userid).get("lang") ) )
                command.UpdateDict('brewCounter', storm * int(stormTime) )
                command.Delayed(1, decrement, userid, True, 'decrement_%s' % userid)
			
def atmosphereStorm(userid):
    es.emitsound('player', userid, 'ambient/atmosphere/thunder%s.wav' % random.randint(1,4), '1.0', '0.0')
    wcs.Command(userid).Delayed(4, atmosphereStorm, userid, True, 'sfx_%s' % userid)

def round_end(ev):
    for player in es.getUseridList():
        if wcs.GetLevel(player, raceName, 'Storm, Earth and Fire'):
            if wcs.Command(player).ReturnDict('brewCounter'):
                transformBack(player)
			
def decrement(userid):
    currentLoop = wcs.Command(userid).ReturnDict('brewCounter')
    if currentLoop:
        tokens = {}
        tokens['element'] = wcs.Command(userid).ReturnDict('brewElement')
        tokens['time']    = currentLoop
        wcs.Command(userid).HudHint("%s\n%s" % (text('time left', tokens, playerlib.getPlayer(userid).get("lang") ), text('seconds', tokens, playerlib.getPlayer(userid).get("lang") ) ) )
        wcs.Command(userid).ModDict('brewCounter', -1)
        wcs.Command(userid).Delayed(1, decrement, userid, True, 'decrement_%s' % userid)
    else:
        transformBack(userid)
		
def transformBack(userid):
    wcs.Command(userid).CancelDelayed('decrement_%s' % userid)
    wcs.Command(userid).CancelDelayed('sfx_%s' % userid)
    command = wcs.Command(userid)
    command.UpdateDict('brewElement', '')
    command.UpdateDict('brewCounter', 0)
    command.Color()
    command.Health(100)
    command.SetGravity(1.0)
    command.Speed(1.0)
    es.tell(userid, '#multi', text('transformed back', lang = playerlib.getPlayer(userid).get("lang") ) )
