Jump to content
Korean Random
goodman

Динамические макросы в Python

Recommended Posts

'тык'

Тут тоже один минус, в таком виде расчет для одной команды будет неверным так как переменная с максимальным начальным значением запаса прочности берется из большего значения толь или иной команды.

 

'hp_panel.py ; battleLabelsTemplates.xc ; shot-1.png'

{{py:xvm.frag_correlation.percent_hp(0)}}
{{py:xvm.frag_correlation.percent_hp(1)}}
import BigWorld
import xvm_battle.python.fragCorrelationPanel as panel

actual_arenaUniqueID = None
hp_max_team = 0

@xvm.export('xvm.frag_correlation.current_hp', deterministic=False)
def current_hp(current_team):
    return panel.teams_totalhp[current_team]

@xvm.export('xvm.frag_correlation.percent_hp', deterministic=False)
def percent_hp(current_team):
    global actual_arenaUniqueID, hp_max_team
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID and hp_max_team == 0:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_team = max(panel.teams_totalhp)
    return round((100. * current_hp(current_team)) / hp_max_team, 0)

57e4af237927.png

 

 

Во втором случае расчет для одной команды производится нормально, а для другой остается постоянной переменная с максимальным начальным значением запаса прочности.

 

'hp_panel.py ; battleLabelsTemplates.xc ; shot-2.png'

{{py:xvm.frag_correlation.percent_hp(0)}}
{{py:xvm.frag_correlation.percent_hp(1)}}
import BigWorld
import xvm_battle.python.fragCorrelationPanel as panel
actual_arenaUniqueID = None
hp_max_team = 0
@xvm.export('xvm.frag_correlation.percent_hp', deterministic=False)
def percent_hp(current_team):
    global actual_arenaUniqueID, hp_max_team
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID and hp_max_team == 0:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_team = panel.teams_totalhp[current_team]
    return round((100. * current_hp(current_team)) / hp_max_team, 0)

650d53c2e868.png

 

Так что тут для правильного расчета нужно будет создавать две отдельных функции

 

import BigWorld
hp_max_ally = 0
hp_max_enemy = 0
actual_arenaUniqueID = None

@xvm.export('xvm.frag_correlation.percent_hp_ally', deterministic=False)
def percent_hp_ally():
    global actual_arenaUniqueID, hp_max_ally
    arenaUniqueID = BigWorld.player().arenaUniqueID
   if actual_arenaUniqueID != arenaUniqueID and hp_max_ally == 0:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_ally = panel.teams_totalhp[0]
    return round((100. * current_hp(0)) / hp_max_ally, 0)

@xvm.export('xvm.frag_correlation.percent_hp_enemy', deterministic=False)
def percent_hp_enemy():
    global actual_arenaUniqueID, hp_max_enemy
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID and hp_max_enemy == 0:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_enemy = panel.teams_totalhp[1]
    return round((100. * current_hp(1)) / hp_max_enemy, 0)

 

Или можно как то по другому выкрутится?

 

я вот пытался hp_max_team сделать на подобии panel.teams_totalhp[current_team], но чет как-то у меня ошибка лезет =_=, hp_max_team[current_team]

import BigWorld
import xvm_battle.python.fragCorrelationPanel as panel

actual_arenaUniqueID = None
hp_max_team[0] = 0
hp_max_team[1] = 0

@xvm.export('xvm.frag_correlation.percent_hp', deterministic=False)
def percent_hp(current_team):
    global actual_arenaUniqueID, hp_max_team[0], hp_max_team[1]
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_team[0] = panel.teams_totalhp[0]
      hp_max_team[1] = panel.teams_totalhp[1]
    return round((100. * current_hp(current_team)) / hp_max_team[current_team], 0)
Edited by Kupnu4

Share this post


Link to post

Short link
Share on other sites
Так дело же немного в другом, там процент вычисляется для двух команд (в зависимости от переменой - current_team). При первом расчёте для команды "0", союзников, присваивается максимальное значение хп на начало боя в константу "hp_max_team", производится далее расчёт процента относительно текущего значения хп союзников. В тоже время нам нужно вычислить тот же процент, но уже для команды противника "1", а параметр "hp_max_team" уже имеет ненулевое значение и расчёт продолжает вестись относительно него, что неправильно в этом случае.
import BigWorld
import xvm_battle.python.fragCorrelationPanel as panel

actual_arenaUniqueID = None
hp_max_team = [0, 0]

@xvm.export('xvm.frag_correlation.current_hp', deterministic=False)
def current_hp(current_team):
    return panel.teams_totalhp[current_team]

@xvm.export('xvm.frag_correlation.percent_hp', deterministic=False)
def percent_hp(current_team):
    global actual_arenaUniqueID, hp_max_team
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID:
      actual_arenaUniqueID = arenaUniqueID
      hp_max_team[current_team] = panel.teams_totalhp[current_team]
    return round((100. * current_hp(current_team)) / hp_max_team[current_team], 0)

Хах, одновременно запостили

Также and hp_max_team == 0 лишнее

 

я вот пытался hp_max_team сделать на подобии panel.teams_totalhp[current_team], но чет как-то у меня ошибка лезет =_=, hp_max_team[current_team]

 

Какая именно?

 

 

hp_max_team[0] = 0 hp_max_team[1] = 0

 

Так неправильно, нужно

hp_max_team = [0, 0]
global hp_max_team
Edited by wotunion
  • Upvote 1

Share this post


Link to post

Short link
Share on other sites

Так неправильно, нужно hp_max_team = [0, 0]

 

И тут встает вопрос: 1й ноль под каким индексом идет?)

Ибо вот данный код:

##########################################
Max_HP_test = [0, 0]
UniqueID_test = None

@xvm.export('kupnu4.tHP.test')
def tHP_colorteam_test(cur_team):
	global Max_HP_test, UniqueID_test
	arenaUniqueID = BigWorld.player().arenaUniqueID
	if UniqueID_test != arenaUniqueID:
		UniqueID_test = arenaUniqueID
		Max_HP_test[cur_team] = panel.teams_totalhp[cur_team]
	current_hp = panel.teams_totalhp[cur_team] * 100 / Max_HP_test[cur_team]
	if current_hp >= 85:
		return '#60FF00'
	elif current_hp >= 45:
		return '#F8F400'
	elif current_hp >= 15:
		return '#FE7903'
	else:
		return '#FE0E00'
##########################################

 

выдает ошибочку:

2016-06-01 02:39:16: [ERROR] Traceback (most recent call last):

  File "xvm_main/python_macro.py", line 152, in process_python_macro

  File "xvm_main/python_macro.py", line 145, in <lambda>

  File "res_mods/configs/xvm/py_macro\kupnu4_test.py", line 16, in tHP_colorteam_test

    current_hp = panel.teams_totalhp[cur_team] * 100 / Max_HP_test[cur_team]

ZeroDivisionError: integer division or modulo by zero

 

ЗЫ

Вот жеж пень, а про слона то и забыл:

##########################################
Max_HP_test = [0, 0]
UniqueID_test = None

@xvm.export('kupnu4.tHP.test')
def tHP_colorteam_test(cur_team):
	global Max_HP_test, UniqueID_test
	arenaUniqueID = BigWorld.player().arenaUniqueID
	if UniqueID_test != arenaUniqueID:
		UniqueID_test = arenaUniqueID
		Max_HP_test[0] = panel.teams_totalhp[0]
		Max_HP_test[1] = panel.teams_totalhp[1]
	current_hp = panel.teams_totalhp[cur_team] * 100 / Max_HP_test[cur_team]
	if current_hp >= 85:
		return '#60FF00'
	elif current_hp >= 45:
		return '#F8F400'
	elif current_hp >= 15:
		return '#FE7903'
	else:
		return '#FE0E00'
########################################## 

 

Ну все, в койку

Edited by Kupnu4

Share this post


Link to post

Short link
Share on other sites

 

 

И тут встает вопрос: 1й ноль под каким индексом идет?)

Share this post


Link to post

Short link
Share on other sites

c3eec6083dec.png

 

Код:

В конце первого сообщения в теме

 

'Подробнее ...'

 

+ Фоновая подложка и сами значения символов ХП выполнены шрифтом

+ Цвет полос подгружается из системных значений заданных в секции "colors.xc"

+ Заполнение полосы происходит через каждые 5% от отношения:

current_hp - текущее общее значение ХП (для конкретной команды)
max_hp_team - начальное общее значение ХП (для конкретной команды)

100 * current_hp / max_hp_team

+ Поддерживается добавление своих символов в конфиге

Подложка (серая)
Q - код символа

{{py:xvm.max_hp_symbols('Q')}}

0, 1 - индекс команды: союзники, противники
​Q - код символа

{{py:xvm.current_hp_symbols(0, 'Q')}}

Edited by night_dragon_on
  • Upvote 3

Share this post


Link to post

Short link
Share on other sites

@night_dragon_on, а зачем такой огромный код? Можно же так сделать:

return "<font face='xvm'><b>& #x63;</b></font>" * int(round( (current_hp * 20 ) / max_hp_team))
У меня так выглядит:

post-7590-0-24463900-1464805922_thumb.png

Edited by neLeax
  • Upvote 4

Share this post


Link to post

Short link
Share on other sites
@xvm.export('xvm.hp_panel.max_hp_symbols', deterministic=False)
def max_hp_symbols(symbol):
    return "%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s" % (symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol, symbol)

1. deterministic=True, так как функция детерминированная, или лучше вообще его убрать.

2. return str(symbol)*20

3. current_hp_symbols можно в пару строк нарисовать аналогичным способом

как-то так (не проверял):

 

@xvm.export('xvm.hp_panel.current_hp_symbols', deterministic=False)
def current_hp_symbols(current_team, symbol):
    return str(symbol)*int(percent_hp(current_team)/20)

* а вот этот метод недетерминированный, так как при одних и тех же значениях аргументов может выдавать разный результат

Edited by sirmax
  • Upvote 1

Share this post


Link to post

Short link
Share on other sites
@sirmax, не подскажешь, каким способом питоном можно выдернуть количество нанесенного дамага из хит-лога?

Share this post


Link to post

Short link
Share on other sites

@sirmax, не подскажешь, каким способом питоном можно выдернуть количество нанесенного дамага из хит-лога?

никаким, только самому считать, так как хитлог во флеше реализован

  • Upvote 2

Share this post


Link to post

Short link
Share on other sites

никаким, только самому считать, так как хитлог во флеше реализован

а что мешает сделать через питон?

def getVehicleHealth(vehicleId):
    player = BigWorld.player()
    if hasattr(BigWorld.entity(vehicleId), 'health'):
        return BigWorld.entity(vehicleId).health
    else:
        vehicle = player.arena.vehicles.get(vehicleId)
        if player is not None:
            return vehicle['vehicleType'].maxHealth


@hookMethod.registerEvent(Vehicle, 'onEnterWorld')                    
def vehicle_onEnterWorld(self, prereqs):
    self.healthOld = getVehicleHealth(self.id)
        

def show_damage_shot(self, newHealth):
    damage = self.healthOld - newHealth
    self.healthOld = newHealth
    return damage

@hookMethod.registerEvent(Vehicle, 'onHealthChanged')        
def onHealthChanged(self, newHealth, attackerID, attackReasonID):
    damage = show_damage_shot(self, newHealth)
    print damage 

ну а дальше уже определяйте для какой команды нужно....

  • Upvote 1

Share this post


Link to post

Short link
Share on other sites

а что мешает сделать через питон?

я это и имел в виду под "самому считать"

Share this post


Link to post

Short link
Share on other sites

я это и имел в виду под "самому считать"

и это не проблема

def IsLive(vehicleID):
    player = BigWorld.player()
    vehicles = player.arena.vehicles
    return vehicles[vehicleID]['isAlive'] if player is not None else None


def IsFriendly(vehicleID):
    player = BigWorld.player()
    vehicles = player.arena.vehicles
    return vehicles[player.playerVehicleID]['team'] == vehicles[vehicleID]['team'] if player is not None else None
    
    
def getVehicleHealth(vehicleId):
    player = BigWorld.player()
    if hasattr(BigWorld.entity(vehicleId), 'health'):
        return BigWorld.entity(vehicleId).health
    else:
        vehicle = player.arena.vehicles.get(vehicleId)
        if player is not None:
            return vehicle['vehicleType'].maxHealth


@hookMethod.registerEvent(Vehicle, 'onEnterWorld')                    
def vehicle_onEnterWorld(self, prereqs):
    self.healthOld = getVehicleHealth(self.id)

 
def show_damage_shot(self, newHealth):
    damage = self.healthOld - newHealth
    self.healthOld = newHealth
    return damage


@hookMethod.registerEvent(Vehicle, 'onHealthChanged')        
def onHealthChanged(self, newHealth, attackerID, attackReasonID):
    damage = 0
    for vehicleID in BigWorld.entities.values():
        if type(vehicleID) is Vehicle:
            if IsLive(vehicleID.id) and not IsFriendly(vehicleID.id) and attackReasonID == 0:
                 delts_helth = show_damage_shot(self, newHealth)
                 damage += delts_helth
                 print 'my damage total = %s' % damage      
Edited by Ekspoint
  • Upvote 1

Share this post


Link to post

Short link
Share on other sites
и это не проблема

а можно теперь то же самое, но применительно к py_macro (с декораторами @xvm.export)  для использования в конфиге, пжл. 

Edited by Kapany3uk

Share this post


Link to post

Short link
Share on other sites

а можно теперь то же самое, но применительно к py_macro (с декораторами @xvm.export)  для использования в конфиге, пжл. 

а для чего вообще нужно? я в тему не вникал

Share this post


Link to post

Short link
Share on other sites

 

 

а для чего вообще нужно? я в тему не вникал
ну если по аналогии с модами totalHP то не хватает "основного калибра" (для чего и нужен свой дамаг не во флешке) 

Share this post


Link to post

Short link
Share on other sites

ну если по аналогии с модами totalHP то не хватает "основного калибра" (для чего и нужен свой дамаг не во флешке) 

оооооо, для него этого мало :), да и калибр в модах имеет погрешность счета

чуть позже дам черновик

Share this post


Link to post

Short link
Share on other sites

 

 

чуть позже дам черновик
если не трудно. будем ждать :)) 

Share this post


Link to post

Short link
Share on other sites

код дерьмо, но пашет

from constants import VEHICLE_HIT_FLAGS
import BigWorld
from Avatar import PlayerAvatar
from Vehicle import Vehicle
from gui.Scaleform.Battle import Battle

def IsLive(vehicleID):
    player = BigWorld.player()
    vehicles = player.arena.vehicles
    return vehicles[vehicleID]['isAlive'] if player is not None else None


def IsFriendly(vehicleID):
    player = BigWorld.player()
    vehicles = player.arena.vehicles
    return vehicles[player.playerVehicleID]['team'] == vehicles[vehicleID]['team'] if player is not None else None


def get_all_health():
    for vehicleID in BigWorld.entities.values():
        if type(vehicleID) is Vehicle:
            if IsLive(vehicleID.id) and not IsFriendly(vehicleID.id):
                battle_info.enemy_hp[vehicleID.id] = vehicleID.health


def damage_helth(self, newHealth, attackerID, attackReasonID):
    if self.id in battle_info.enemy_hp.keys():
        if attackerID == BigWorld.player().playerVehicleID:
            damage = battle_info.enemy_hp[self.id] - newHealth
            in_arr = False
            for key, value in battle_info.damage_log.items():
                if self.id == value['id']:
                    value['damage'] = value['damage'] + damage
                    in_arr = True

            if not in_arr:
                battle_info.damage_log[len(battle_info.damage_log)] = {'id': self.id, 'damage': damage}
        battle_info.enemy_hp[self.id] = newHealth
    get_all_health()


def damage_helth_team(self, newHealth, attackerID, attackReasonID):
    damaged = []
    if self.id in battle_info.enemy_hp.keys():
        if attackerID in battle_info.total_damag_team.keys():
            battle_info.total_damag_team[attackerID] += battle_info.enemy_hp[self.id] - newHealth
        else:
            battle_info.total_damag_team[attackerID] = battle_info.enemy_hp[self.id] - newHealth
        for vehicleID in BigWorld.entities.values():
            if type(vehicleID) is Vehicle:
                if not attackerID == BigWorld.player().playerVehicleID and IsFriendly(vehicleID.id):
                    for id, total_damag in battle_info.total_damag_team.items():
                        damaged.append(total_damag)
                    in_arr = False
                    for key, value in battle_info.damage_log_team.items():
                        if self.id == value['id']:
                            value['damage'] = max(damaged)
                            in_arr = True

                    if not in_arr:
                        battle_info.damage_log_team[len(battle_info.damage_log_team)] = {'id': self.id, 'damage': max(damaged)}
                        
        battle_info.enemy_hp[self.id] = newHealth
    get_all_health()
    
    
@registerEvent(PlayerAvatar, 'vehicle_onEnterWorld')
def vehicle_onEnterWorld(self, vehicle):
    PlayerAvatar.rezults = []
    get_all_health()


@registerEvent(PlayerAvatar, 'showShotResults')
def showShotResults(self, results):
    PlayerAvatar.rezults = results


@registerEvent(Vehicle, 'onHealthChanged')
def onHealthChanged(self, newHealth, attackerID, attackReasonID):
    damage_helth(self, newHealth, attackerID, attackReasonID)
    damage_helth_team(self, newHealth, attackerID, attackReasonID)
    
    
def total_damage():
    damage = 0
    for key, value in battle_info.damage_log.items():
        damage = damage + value['damage']
    return damage
    

def total_damage_team():
    for key, value in battle_info.damage_log_team.items():
        return value['damage']


class Battle_Info(object):
    
    def __init__(self):
        self.allyDetect = False
        self.enemy_hp = {}
        self.damage_log = {}
        self.damage_log_team = {}
        self.total_damag_team = {}
        
battle_info = Battle_Info()
        
def main_guns(damage, damage_team):
    max_health = 0
    damagedAllies = []
    player = BigWorld.player()
    for vehicle, veh in player.arena.vehicles.iteritems():
        if not veh['team'] == player.team:
            max_health += player.arena.vehicles[vehicle]['vehicleType'].maxHealth

    for r in PlayerAvatar.rezults:
        vehicleID = r & 4294967295L
        flags = r >> 32 & 4294967295L
        if player.team == player.arena.vehicles[vehicleID]['team'] and player.playerVehicleID != vehicleID:
            if flags & (VEHICLE_HIT_FLAGS.IS_ANY_DAMAGE_MASK | VEHICLE_HIT_FLAGS.ATTACK_IS_DIRECT_PROJECTILE):
                damagedAllies.append(vehicleID)
    
    for vehicleID in damagedAllies:
        if player.arena.vehicles[vehicleID]['isAlive']:
            battle_info.allyDetect = True
    result = int(max(round(max_health * 0.2), 1000)) - damage
    if damage_team >= int(max(round(max_health * 0.2), 1000)) - damage:
        result = damage_team - damage
    if result <= 0:
        result = "<img src='img://gui/maps/icons/library/done.png' width='22' height='22' vspace='-3'>"
    return result
                             

def main_gun(damage, damage_team):
    player = BigWorld.player()
    if player.arena.guiType == 1:
        if not battle_info.allyDetect:
            result = main_guns(damage, damage_team)
        else:
            result = "<img src='img://gui/maps/icons/library/errorIcon.png' width='22' height='22' vspace='-4'>"
    else:
        result = "<img src='img://gui/maps/icons/library/errorIcon.png' width='22' height='22' vspace='-4'>"
    return result
    

@registerEvent(Battle, 'beforeDelete')
def beforeDelete(self):
    battle_info.allyDetect = False
    battle_info.enemy_hp.clear()
    battle_info.damage_log.clear()
    battle_info.damage_log_team.clear()
    battle_info.total_damag_team.clear()

    
# в итоге получаем myMAINGUN = main_gun(total_damage(), total_damage_team())

myMAINGUN должен постоянно обновляться в бою, что бы не проседал фпс ставьте 0.5 , тоесть

myMAINGUN = BigWorld.callback(0.5, lambda: main_gun(total_damage(), total_damage_team()))

в работу макросов я не вникал, думаю дойдете сами че куда


если сделаете код более правильным, призовите меня :)

Edited by Ekspoint
  • Upvote 1

Share this post


Link to post

Short link
Share on other sites

И опять у всех в начале полоски HP одинаковой длины хоть в 2 раза изначально разница HP команд будет. Про это я и писал.

"Как-то так:"

import xvm_battle.python.fragCorrelationPanel as panel
import BigWorld

actual_arenaUniqueID = None
max_hp_A = 0
max_hp_B = 0

@xvm.export('thp0', deterministic=False)
def total_hp_string_old():
    global actual_arenaUniqueID, max_hp_A, max_hp_B
    arenaUniqueID = BigWorld.player().arenaUniqueID
    if actual_arenaUniqueID != arenaUniqueID:
      actual_arenaUniqueID = arenaUniqueID
      max_hp_A = panel.teams_totalhp[0]
      max_hp_B = panel.teams_totalhp[1]
    a = panel.teams_totalhp[0]
    b = panel.teams_totalhp[1]
    symA = 'b'
    symB = 'c'
    n = 80.0
    k = n / (max_hp_A + max_hp_B)
    LA = int(k*max_hp_A)
    LB = int(k*max_hp_B)
    la = symA * int(k*a)
    lb = symB * int(k*b)
    lga = symA * (LA - int(k*a))
    lgb = symB * (LB - int(k*b))
    return '<font face="xvm" color="#AAAAAA">'+ lga + '<font color="#55FF00">' + la + '</font> <font color="#FF0000">' + lb + '</font>' + lgb + '</font>'

post-8781-0-54565200-1464810371_thumb.png

Share this post


Link to post

Short link
Share on other sites

Слуште, а можно теперь с помощью питона намутить свою дебаг-панель, с настройкой цветов пинга и фпс?

Share this post


Link to post

Short link
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


  • Recently Browsing   0 members

    No registered users viewing this page.

×
×
  • Create New...