From 2086336efc944cb375cbd7bdc9140855cbbd9fbe Mon Sep 17 00:00:00 2001 From: reddivision Date: Sat, 30 Jul 2016 00:01:33 -0700 Subject: [PATCH] Added nickname templating, worker for naming on startup --- configs/config.json.example | 2 + pokecli.py | 11 ++++ pokemongo_bot/__init__.py | 1 + pokemongo_bot/cell_workers/__init__.py | 1 + .../cell_workers/incubate_eggs_worker.py | 15 ++--- .../cell_workers/nickname_all_worker.py | 45 +++++++++++++++ .../cell_workers/pokemon_catch_worker.py | 19 +++++-- pokemongo_bot/cell_workers/utils.py | 55 +++++++++++++++++++ 8 files changed, 138 insertions(+), 11 deletions(-) create mode 100644 pokemongo_bot/cell_workers/nickname_all_worker.py diff --git a/configs/config.json.example b/configs/config.json.example index 2e7cd45433..23d475b0f9 100644 --- a/configs/config.json.example +++ b/configs/config.json.example @@ -35,6 +35,8 @@ "use_lucky_egg": false, "hatch_eggs": true, "longer_eggs_first": true, + "nickname_template": "{name}_{iv_pct}", + "nickname_on_startup": false, "evolve_captured": "NONE", "release_pokemon": true, "catch_randomize_reticle_factor": 1.0, diff --git a/pokecli.py b/pokecli.py index 45520c0e21..f942dcf984 100755 --- a/pokecli.py +++ b/pokecli.py @@ -354,6 +354,14 @@ def init_config(): type=float, default=1.0 ) + add_config( + parser, + load, + long_flag="--nickname_template", + help="Provide a template to be used for naming captured/hatched pokemon", + type=str, + default="{name}" + ) # Start to parse other attrs config = parser.parse_args() @@ -411,6 +419,9 @@ def init_config(): if config.evolve_captured and isinstance(config.evolve_captured, str): config.evolve_captured = [str(pokemon_name) for pokemon_name in config.evolve_captured.split(',')] + if config.nickname_template=="": + config.nickname_template="{name}" + fix_nested_config(config) return config diff --git a/pokemongo_bot/__init__.py b/pokemongo_bot/__init__.py index a67d829a80..693a028702 100644 --- a/pokemongo_bot/__init__.py +++ b/pokemongo_bot/__init__.py @@ -280,6 +280,7 @@ def _setup_api(self): def _setup_workers(self): self.workers = [ cell_workers.SoftBanWorker(self), + cell_workers.NicknameAllWorker(self), cell_workers.IncubateEggsWorker(self), cell_workers.PokemonTransferWorker(self), cell_workers.EvolveAllWorker(self), diff --git a/pokemongo_bot/cell_workers/__init__.py b/pokemongo_bot/cell_workers/__init__.py index 4aaa8ee52e..5dc238c56b 100644 --- a/pokemongo_bot/cell_workers/__init__.py +++ b/pokemongo_bot/cell_workers/__init__.py @@ -5,6 +5,7 @@ from evolve_all_worker import EvolveAllWorker from incubate_eggs_worker import IncubateEggsWorker from move_to_fort_worker import MoveToFortWorker +from nickname_all_worker import NicknameAllWorker from pokemon_catch_worker import PokemonCatchWorker from pokemon_transfer_worker import PokemonTransferWorker from recycle_items_worker import RecycleItemsWorker diff --git a/pokemongo_bot/cell_workers/incubate_eggs_worker.py b/pokemongo_bot/cell_workers/incubate_eggs_worker.py index dd3654b510..a3d47de205 100644 --- a/pokemongo_bot/cell_workers/incubate_eggs_worker.py +++ b/pokemongo_bot/cell_workers/incubate_eggs_worker.py @@ -1,6 +1,6 @@ from pokemongo_bot import logger from pokemongo_bot.human_behaviour import sleep - +from utils import nickname_pokemon class IncubateEggsWorker(object): last_km_walked = 0 @@ -98,15 +98,13 @@ def _check_inventory(self, lookup_ids=[]): "used": False }) elif 'is_egg' not in pokemon and pokemon['id'] in lookup_ids: - matched_pokemon.append({ - "pokemon_id": pokemon.get('pokemon_id', -1), - "cp": pokemon.get('cp', -1), + matched_pokemon.append(pokemon.update({ "iv": [ pokemon.get('individual_attack', -1), pokemon.get('individual_stamina', -1), pokemon.get('individual_defense', -1) ] - }) + })) continue if "player_stats" in inv_data: self.km_walked = inv_data.get("player_stats", {}).get("km_walked", 0) @@ -133,15 +131,18 @@ def _hatch_eggs(self): pass # just proceed with what we have for pokemon in pokemon_data: # pokemon ids seem to be offset by one - pokemon['name'] = self.bot.pokemon_list[(pokemon['pokemon_id']-1)]['Name'] + pokemon['name'] = self.bot.pokemon_list[(pokemon.get('pokemon_id',0)-1)]['Name'] logger.log("-"*30, log_color) logger.log("[!] {} eggs hatched! Received:".format(len(pokemon_data)), log_color) for i in range(len(pokemon_data)): logger.log("-"*30,log_color) logger.log("[!] Pokemon: {}".format(pokemon_data[i]['name']), log_color) - logger.log("[!] CP: {}".format(pokemon_data[i]['cp']), log_color) + logger.log("[!] CP: {}".format(pokemon_data[i].get('cp',0)), log_color) logger.log("[!] IV: {}".format("/".join(map(str, pokemon_data[i]['iv']))), log_color) logger.log("[!] XP: {}".format(xp[i]), log_color) logger.log("[!] Stardust: {}".format(stardust[i]), log_color) logger.log("[!] Candy: {}".format(candy[i]), log_color) logger.log("-"*30, log_color) + if self.bot.config.nickname_template: + for pokemon in pokemon_data: + nickname_pokemon(self.bot,pokemon) \ No newline at end of file diff --git a/pokemongo_bot/cell_workers/nickname_all_worker.py b/pokemongo_bot/cell_workers/nickname_all_worker.py new file mode 100644 index 0000000000..c6dbaa5542 --- /dev/null +++ b/pokemongo_bot/cell_workers/nickname_all_worker.py @@ -0,0 +1,45 @@ +from pokemongo_bot import logger +from pokemongo_bot.human_behaviour import sleep +from utils import nickname_pokemon + +class NicknameAllWorker(object): + def __init__(self,bot): + self.bot = bot + + def work(self): + if not self._should_run(): + return + + try: + inventory = reduce(dict.__getitem__, ["responses", "GET_INVENTORY", "inventory_delta", "inventory_items"], self.bot.get_inventory()) + except KeyError: + pass + else: + template = self.bot.config.nickname_template + logger.log("Nicknaming all pokemon in inventory with template {}".format(template),'yellow') + pokemon_data = self._get_inventory_pokemon(inventory) + for pokemon in pokemon_data: + nickname_pokemon(self.bot,pokemon) + sleep(1.2) + logger.log("Finished renaming all pokemon.",'green') + + def _should_run(self): + if not self.bot.config.nickname_template: + return False + + if self.bot.tick_count > 1: + return False + + return True + + def _get_inventory_pokemon(self,inventory_dict): + pokemon_data = [] + for inv_data in inventory_dict: + try: + pokemon = reduce(dict.__getitem__,['inventory_item_data','pokemon_data'],inv_data) + except KeyError: + pass + else: + if not pokemon.get('is_egg',False): + pokemon_data.append(pokemon) + return pokemon_data \ No newline at end of file diff --git a/pokemongo_bot/cell_workers/pokemon_catch_worker.py b/pokemongo_bot/cell_workers/pokemon_catch_worker.py index b2f57b5032..c7042a6658 100644 --- a/pokemongo_bot/cell_workers/pokemon_catch_worker.py +++ b/pokemongo_bot/cell_workers/pokemon_catch_worker.py @@ -1,10 +1,10 @@ # -*- coding: utf-8 -*- import time - from pokemongo_bot import logger from pokemongo_bot.human_behaviour import (normalized_reticle_size, sleep, spin_modifier) +from utils import nickname_pokemon class PokemonCatchWorker(object): @@ -199,13 +199,14 @@ def work(self): sum(response_dict['responses']['CATCH_POKEMON']['capture_award']['xp']) ), 'blue') self.bot.softban = False + + id_list2 = self.count_pokemon_inventory() + # No need to capture this even for metrics, player stats includes it. + pokemon_to_transfer = list(set(id_list2) - set(id_list1)) if (self.config.evolve_captured and (self.config.evolve_captured[0] == 'all' or pokemon_name in self.config.evolve_captured)): - id_list2 = self.count_pokemon_inventory() - # No need to capture this even for metrics, player stats includes it. - pokemon_to_transfer = list(set(id_list2) - set(id_list1)) # TODO dont throw RuntimeError, do something better if len(pokemon_to_transfer) == 0: @@ -217,9 +218,19 @@ def work(self): if status == 1: logger.log( '{} has been evolved!'.format(pokemon_name), 'green') + pokemon_data['evolved'] = True else: logger.log( 'Failed to evolve {}!'.format(pokemon_name)) + if pokemon_to_transfer and self.config.nickname_template: + pokemon_data['id'] = pokemon_to_transfer[0] + # let's pretend to be a little human + if pokemon_data.get('evolved',False): + sleep(10) #evolution animation + pokemon_data['id'] += 1 + else: + sleep(1.2) + nickname_pokemon(self.bot,pokemon_data) break time.sleep(5) diff --git a/pokemongo_bot/cell_workers/utils.py b/pokemongo_bot/cell_workers/utils.py index 507ae19583..f55ebf2340 100644 --- a/pokemongo_bot/cell_workers/utils.py +++ b/pokemongo_bot/cell_workers/utils.py @@ -2,6 +2,7 @@ import struct from math import asin, cos, sqrt +from pokemongo_bot import logger from colorama import init @@ -144,3 +145,57 @@ def print_yellow(message): def print_red(message): print(u'\033[91m' + message.decode('utf-8') + '\033[0m') + +def nickname_pokemon(bot,pokemon): + """This requies a pokemon object containing all the standard fields: id, ivs, cp, etc""" + template = bot.config.nickname_template.lower() + if template == "{name}": + return # no point in wasting api call + new_name = "" + instance_id = pokemon.get('id',0) + if not instance_id: + logger.log("Pokemon instance id returned 0. Can't rename.",'red') + return + id = pokemon.get('pokemon_id',0)-1 + name = bot.pokemon_list[id]['Name'] + cp = pokemon.get('cp',0) + iv_attack = pokemon.get('individual_attack',0) + iv_defense = pokemon.get('individual_defense',0) + iv_stamina = pokemon.get('individual_stamina',0) + iv_list = [iv_attack,iv_defense,iv_stamina] + iv_ads = "/".join(map(str,iv_list)) + iv_sum = sum(iv_list) + iv_pct = "{:.2f}".format(iv_sum/45.0) + log_color = 'red' + try: + new_name = template.format(name=name, + id=id, + cp=cp, + iv_attack=iv_attack, + iv_defense=iv_defense, + iv_stamina=iv_stamina, + iv_ads=iv_ads, + iv_sum=iv_sum, + iv_pct=iv_pct)[:12] + except KeyError as bad_key: + logger.log("Unable to nickname {} due to bad template ({})".format(name,bad_key),log_color) + bot.api.nickname_pokemon(pokemon_id=instance_id,nickname=new_name) + response = bot.api.call() + try: + result = reduce(dict.__getitem__, ["responses", "NICKNAME_POKEMON"], response) + except KeyError: + logger.log("Attempt to nickname received bad response.",log_color) + if bot.config.debug: + logger.log(response,log_color) + return + result = result['result'] + output = { + 0: 'Nickname unset', + 1: 'Nickname set successfully! {} is now {}'.format(name,new_name), + 2: 'Invalid nickname! ({})'.format(new_name), + 3: 'Pokemon not found.', + 4: 'Pokemon is egg' + }[result] + if result==1: + log_color='green' + logger.log(output,log_color) \ No newline at end of file