PaiGram/model/apihelper/playercards.py

158 lines
7.5 KiB
Python

from typing import Union, Optional
import httpx
import os
import ujson
from .helpers import get_headers
from model.base import GameItem
from model.game.artifact import ArtifactInfo
from model.game.character import CharacterInfo, CharacterValueInfo
from model.game.fetter import FetterInfo
from model.game.skill import Skill
from model.game.talent import Talent
from model.game.weapon import WeaponInfo
class PlayerCardsAPI:
UI_URL = "https://enka.shinshin.moe/ui/"
def __init__(self):
self.client = httpx.AsyncClient(headers=get_headers())
project_path = os.path.dirname(__file__)
characters_map_file = os.path.join(project_path, "metadata", "CharactersMap.json")
name_text_map_hash_file = os.path.join(project_path, "metadata", "NameTextMapHash.json")
reliquary_name_map_file = os.path.join(project_path, "metadata", "ReliquaryNameMap.json")
with open(characters_map_file, "r", encoding="utf-8") as f:
self._characters_map_json: dict = ujson.load(f)
with open(name_text_map_hash_file, "r", encoding="utf-8") as f:
self._name_text_map_hash_json: dict = ujson.load(f)
with open(reliquary_name_map_file, "r", encoding="utf-8") as f:
self._reliquary_name_map_json: dict = ujson.load(f)
def get_characters_name(self, item_id: Union[int, str]) -> str:
if isinstance(item_id, int):
item_id = str(item_id)
characters = self.get_characters(item_id)
name_text_map_hash = characters.get("NameTextMapHash", "-1")
return self.get_text(str(name_text_map_hash))
def get_characters(self, item_id: Union[int, str]) -> dict:
if isinstance(item_id, int):
item_id = str(item_id)
return self._characters_map_json.get(item_id, {})
def get_text(self, hash_value: Union[int, str]) -> str:
if isinstance(hash_value, int):
hash_value = str(hash_value)
return self._name_text_map_hash_json.get(hash_value, "")
def get_reliquary_name(self, reliquary: str) -> str:
return self._reliquary_name_map_json[reliquary]
async def get_data(self, uid: Union[str, int]):
url = f"https://enka.shinshin.moe/u/{uid}/__data.json"
response = await self.client.get(url)
return response
def data_handler(self, avatar_data: dict, avatar_id: int) -> CharacterInfo:
artifact_list = []
weapon_info: Optional[WeaponInfo] = None
equip_list = avatar_data["equipList"] # 圣遗物和武器相关
fetter_info = avatar_data["fetterInfo"] # 好感等级
fight_prop_map = avatar_data["fightPropMap"] # 属性
# inherent_proud_skill_list = avatar_data["inherentProudSkillList"] # 不知道
prop_map = avatar_data["propMap"] # 角色等级 其他信息
# proud_skill_extra_level_map = avatar_data["proudSkillExtraLevelMap"] # 不知道
# skill_depot_id = avatar_data["skillDepotId"] # 不知道
skill_level_map = avatar_data["skillLevelMap"] # 技能等级
# 角色等级
character_level = prop_map['4001']['val']
# 角色姓名
character_name = self.get_characters_name(avatar_id)
characters_data = self.get_characters(avatar_id)
# 圣遗物和武器
for equip in equip_list:
if "reliquary" in equip: # 圣遗物
flat = equip["flat"]
reliquary = equip["reliquary"]
reliquary_main_stat = flat["reliquaryMainstat"]
reliquary_sub_stats = flat['reliquarySubstats']
sub_item = []
for reliquary_sub in reliquary_sub_stats:
sub_item.append(GameItem(name=self.get_reliquary_name(reliquary_sub["appendPropId"]),
item_type=reliquary_sub["appendPropId"], value=reliquary_sub["statValue"]))
main_item = GameItem(name=self.get_reliquary_name(reliquary_main_stat["mainPropId"]),
item_type=reliquary_main_stat["mainPropId"],
value=reliquary_main_stat["statValue"])
name = self.get_text(flat["nameTextMapHash"])
artifact_list.append(ArtifactInfo(item_id=equip["itemId"], name=name, star=flat["rankLevel"],
level=reliquary["level"] - 1, main_item=main_item, sub_item=sub_item))
if "weapon" in equip: # 武器
flat = equip["flat"]
weapon_data = equip["weapon"]
# 防止未精炼
if 'promoteLevel' in weapon_data:
weapon_level = weapon_data['promoteLevel'] - 1
else:
weapon_level = 0
if 'affixMap' in weapon_data:
affix = list(weapon_data['affixMap'].values())[0] + 1
else:
affix = 1
reliquary_main_stat = flat["weaponStats"][0]
reliquary_sub_stats = flat['weaponStats'][1]
sub_item = GameItem(name=self.get_reliquary_name(reliquary_main_stat["appendPropId"]),
item_type=reliquary_sub_stats["appendPropId"],
value=reliquary_sub_stats["statValue"])
main_item = GameItem(name=self.get_reliquary_name(reliquary_main_stat["appendPropId"]),
item_type=reliquary_main_stat["appendPropId"],
value=reliquary_main_stat["statValue"])
weapon_name = self.get_text(flat["nameTextMapHash"])
weapon_info = WeaponInfo(item_id=equip["itemId"], name=weapon_name, star=flat["rankLevel"],
level=weapon_level, main_item=main_item, sub_item=sub_item, affix=affix)
# 好感度
fetter = FetterInfo(fetter_info["expLevel"])
# 基础数值处理
for i in range(40, 47):
if fight_prop_map[str(i)] > 0:
dmg_bonus = fight_prop_map[str(i)]
break
else:
dmg_bonus = 0
base_value = CharacterValueInfo(fight_prop_map["2000"], fight_prop_map["1"], fight_prop_map["2001"],
fight_prop_map["4"], fight_prop_map["2002"], fight_prop_map["7"],
fight_prop_map["28"], fight_prop_map["20"], fight_prop_map["22"],
fight_prop_map["23"], fight_prop_map["26"], fight_prop_map["27"],
fight_prop_map["29"], fight_prop_map["30"], dmg_bonus)
# 技能处理
skill_list = []
skills = characters_data["Skills"]
for skill_id in skill_level_map:
skill_list.append(Skill(skill_id, name=skill_level_map[skill_id], icon=skills[skill_id]))
# 命座处理
talent_list = []
consts = characters_data["Consts"]
if 'talentIdList' in avatar_data:
talent_id_list = avatar_data["talentIdList"]
for index, value in enumerate(talent_id_list):
talent_list.append(Talent(talent_id_list[index], icon=consts[index]))
element = characters_data["Element"]
icon = characters_data["SideIconName"]
character_info = CharacterInfo(character_name, element, character_level, fetter, base_value, weapon_info,
artifact_list, skill_list, talent_list, icon)
return character_info