找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
热搜: 文档 工具 设计
查看: 503|回复: 0

分享】女朋友被杀戮尖塔气哭了?我只好写个修改器了

[复制链接]

2万

主题

1249

回帖

2万

积分

超级版主

教育辅助界扛把子

附加身份标识
精华
1
热心
7
听众
1
威望
48
贡献
14307
违规
0
书币
49981
注册时间
2020-4-8

论坛元老灌水之王

发表于 2024-1-19 23:32 | 显示全部楼层 |阅读模式
本帖最后由 csx 于 2024-1-19 23:33 编辑

简介
  • 语言 : python
  • 游戏 : 蒸汽- 杀戮尖塔
女朋友说杀戮尖塔她就没打通过, 太难了, 商店的东西也买不起, 牌组还总是凑不齐就寄了, 非常生气, 于是我写了一款修改器帮她爽一下
修改器
  • 因为我比较懒, 没有去创建ui
  • 使用方法:
    • 关键文件列表 [ 游戏自己的autosave文档, 游戏的卡组json文件, 游戏的遗物json文件]
    • autosave通常在\SlayTheSpire\saves\*.autosave 这个路径里面
    • 所有卡组和遗物的json在\SlayTheSpire\desktop-1.0.jar 可以得到
    • 有需要成品,后面再发吧

使用方法
  • 运行程序后, 选择对应的.autosave 游戏存档载入程序
  • 根据弹出的功能列表输入功能ID
  • 修改后请执行保存
  • 进游戏实现效果
代码:
[Python] 纯文本查看 复制代码
# _*_encoding:UTF-8_*_
# .autosave 是保存的文件

from tkinter.filedialog import askopenfilename
from base64 import b64decode, b64encode
from time import sleep
import json
from ast import literal_eval

'''
--功能列表 : 
1. 修改血量上限 1
2. 查看当前血量上限 1
3. 修改能量点上限1
4. 查看当前已有卡组及其说明1
6. 添加卡组1
7. 查看当前遗物 1
9. 增加指定遗物1
10. 获取所有遗物 1
11. 查看当前金币 1
12. 修改金币    1
13. 修改手牌上限 1
14. 一键清空所有卡组1
15. 一键清空所有遗物1
16. 保存存档1
16. 导入常用的流派, 并保存 None
17. 支持调用流派 None
5. 删除卡组 1
8. 删除指定遗物 1
'''

class SlayAid:
    """
    杀戮尖塔辅助器
    """

    def __init__(self) -> None:
        # 玩家存档
        self.user_card_data = None
        # 游戏卡组
        self.original_cards = None
        # 游戏遗物
        self.original_relics = None
        # autosave_path 自动存档的路径
        self.autosave_path = None
        # menu
        self.menu_list = {
            0: ['展示基础信息', self.show_player_status],
            1: ['修改血量上限', self.modify_blood],
            2: ['修改能量点上限', self.modify_red],
            3: ['修改金币', self.modify_gold],
            4: ['修改手牌上限', self.modify_hand_size],
            5: ['加牌', self.add_one_card],
            6: ['删除指定牌', self.del_one_card],
            7: ['加遗物', self.add_one_relic],
            8: ['删除一个遗物:', self.del_one_relic],
            9: ['一键清空遗物', self.clear_all_relics],
            10: ['一键清空牌组', self.clear_all_crads],
            66: ['保存修改到存档', self.save_to_game],
            88: ['退出程序', self.stop]
        }

    def select_storage_file(self):
        storage_file_path = askopenfilename(title="请选择autosave文件", filetypes=[('游戏存档', '.autosave')])
        if not storage_file_path:
            print(f"用户未选择任何文件, 3s后程序自动退出...")
            sleep(3)
            exit()
        else:
            print(f"文件载入中,{storage_file_path}")
            self.autosave_path = storage_file_path
            with open(storage_file_path, mode="rb") as f:
                data = f.read()
                # 解密文件会return一个json
                self.decode_encryption(data=data)

    # 解密存档
    def decode_encryption(self, data):
        # 定义密钥
        key = "key"
        # Base64解码
        data = b64decode(data)
        # 解密数据
        result = ''.join(chr(byte ^ ord(key[index % len(key)])) for index, byte in enumerate(data))
        # 解析JSON
        json_result = json.loads(result)
        # 存储原始存档信息到实例属性
        self.user_card_data = json_result

    # 获取当前手牌
    def get_cards(self):
        try:
            with open('cards.json', 'r', encoding='utf-8') as f:
                original_data = json.load(f)
                self.original_cards = original_data
        except Exception as e:
            print(f"文件原始卡组信息导入失败, 错误信息:{e}")
        else:
            card_data = self.user_card_data['cards']
            # 把原始数据original_data映射到user_card_data
            card_data_cn = [
                {**item, 'misc': original_data[item['id']]['DESCRIPTION'], 'id': original_data[item['id']]['NAME']} for
                item in card_data]
            return card_data_cn

    # 获取当前遗物
    def get_relics(self):
        try:
            with open('./relics.json', mode='r', encoding='utf-8') as f:
                original_relic = json.load(f)
                self.original_relics = original_relic
        except Exception as e:
            print(f"遗物原始卡组导入失败! 错误信息:{e}")
        else:
            tran_relic = self.user_card_data['relics']
            # 原始relics遗物映射到user_card_data
            tran_relic_name_cn = [{original_relic[key]['NAME']: original_relic[key]['DESCRIPTIONS']} for key in
                                  tran_relic if key in original_relic]
            return tran_relic_name_cn

    # 展示玩家存档信息
    def show_player_status(self):
        # 调用实例方法
        current_cards_cn = self.get_cards()
        current_relic_cn = self.get_relics()
        # 展示当前血量上限
        print(f"玩家血量上限:{self.user_card_data['max_health']}")
        # 展示玩家手牌上限
        print(f"玩家当前手牌上限:{self.user_card_data['hand_size']}")
        # 展示当前金币数
        print(f"玩家金币:{self.user_card_data['gold']} 元")
        # 展示玩家遗物组
        print(f"玩家当前遗物:{current_relic_cn}")
        # 展示玩家当前牌组
        print(f"玩家当前牌组:{current_cards_cn}")

    # 修改血量
    def modify_blood(self):
        """
        修改血量上限
        """
        wanna_blood = input("输入你需要修改到的血量上限(int):")
        try:
            wanna_blood_num = int(wanna_blood)
            if wanna_blood_num > 0:
                print("验证数字成功, 修改存档...")
                # change max_blood
                self.user_card_data['max_health'] = wanna_blood_num
            else:
                print("请校验你的输入是否为正整数!!!")
        except Exception as e:
            print(f"血量上限修改异常,错误信息{e}")

    # 修改手牌上限
    def modify_hand_size(self):
        """
        修改手牌上限
        """
        wanna_size = input("输入你需要修改到的手牌上限(int):")
        try:
            wanna_size_num = int(wanna_size)
            if wanna_size_num >= 5:
                print("验证数字成功, 修改存档...")
                # change max_blood
                self.user_card_data['hand_size'] = wanna_size_num
            else:
                print("请校验你的输入是否为正整数,不少于5!!!")
        except Exception as e:
            print(f"修改手牌上限异常,错误信息{e}")

    # 修改能量点上限
    def modify_red(self):
        """
        修改能量点上限
        """
        wanna_red = input("输入你需要修改到的能量点上限(int):")
        try:
            wanna_red_num = int(wanna_red)
            if wanna_red_num >= 3:
                print("验证数字成功, 修改存档...")
                # change max_blood
                self.user_card_data['red'] = wanna_red_num
            else:
                print("请校验你的输入是否为正整数,不少于3!!!")
        except Exception as e:
            print(f"能量点输入异常,错误信息:{e}")

    # 修改金币
    def modify_gold(self):
        """
        修改金币
        """
        wanna_gold = input("输入你需要修改的金币数:(int):")
        try:
            wanna_gold_num = int(wanna_gold)
            if wanna_gold_num >= 0:
                print("验证数字成功, 修改存档...")
                # change max_blood
                self.user_card_data['gold'] = wanna_gold_num
            else:
                print("请校验你的输入是否为正整数!!!")
        except Exception as e:
            print(f"修改金币失败,错误信息:{e}")

    # 一键清空牌组
    def clear_all_crads(self):
        self.user_card_data["cards"] = []  # 清空卡组列表

    # 一键清空遗物
    def clear_all_relics(self):
        self.user_card_data["relics"] = []  # 清空遗物列表

    # 添加指定卡片
    def add_one_card(self):
        wanna_card = input("输入你需要的卡片('中文名',等级=0或1,张数>=1):")
        try:
            # 第一步把输入的内容转换为元组
            wanna_card_tuple = literal_eval(wanna_card)
            if isinstance(wanna_card_tuple, tuple):
                if isinstance(wanna_card_tuple[0], str) and isinstance(wanna_card_tuple[1], int) and 0 <= \
                        wanna_card_tuple[1] <= 1 and wanna_card_tuple[2] >= 1:
                    for key, sub_dict in self.original_cards.items():
                        if sub_dict.get('NAME') == wanna_card_tuple[0]:
                            print(f"您需要添加的卡组{key}")
                            _ = 0
                            card_template = {
                                'upgrades': wanna_card_tuple[1],
                                'misc': 0,
                                'id': key
                            }
                            while _ < wanna_card_tuple[2]:
                                self.user_card_data['cards'].append(card_template)
                                _ += 1
                            break
                    else:
                        print("你输入的卡组也许不存在,请检查")
                else:
                    print(f"{wanna_card[0]}卡片非中文字符串,或卡片等级不合理...")
            else:
                print("请输入元组,例如('壁垒',1)")
        except Exception as e:
            print(f"输入异常,请输入元组格式,错误信息:{e}")

    # 添加指定遗物
    def add_one_relic(self):
        wanna_relic = input("请输入你需要的遗物:")
        for key, sub_set in self.original_relics.items():
            if sub_set.get('NAME') == wanna_relic:
                # 添加到遗物列表
                self.user_card_data['relics'].append(key)
                break
        else:
            print("你输入的遗物不存在,请检查")

    # 删除指定卡片
    def del_one_card(self):
        wanna_del_card = input('请输入你需要删除的卡名称("中文名",张数):')
        wanna_del_card_tuple = literal_eval(wanna_del_card)
        if isinstance(wanna_del_card_tuple, tuple):
            if isinstance(wanna_del_card_tuple[0], str) and isinstance(wanna_del_card_tuple[1], int):
                for key, sub_dict in self.original_cards.items():
                    if sub_dict.get("NAME") == wanna_del_card_tuple[0]:
                        print(f"你需要删除的卡片:{key}")
                        _ = 0
                        while _ < wanna_del_card_tuple[1]:
                            for i, d in enumerate(self.user_card_data['cards']):
                                if d.get('id') == key:
                                    del self.user_card_data['cards'][i]
                                    break
                            _ += 1
                        print("删除完毕")
                else:
                    print("未能找到你需要删除的卡片,请检查卡片名称是否存在于卡组中...")
            else:
                print("用户输入不合理,请输入元组形式(卡片名,张),例如('打击',3)")
        else:
            print("用户输入非元组格式,请检查,例如('打击',3)")

    # 删除指定遗物
    def del_one_relic(self):
        del_relic = input("请输入你想删除的遗物:")
        for key, sub_set in self.original_relics.items():
            if sub_set.get('NAME') == del_relic:
                self.user_card_data['relics'] = [_ for _ in self.user_card_data['relics'] if _ != del_relic]
                print("删除成功...")
                break
        else:
            print("你输入的遗物不存在,请检查")

    # 重新加密
    def encode_save_file(self):
        encrytion_data = json.dumps(self.user_card_data)
        result = ""
        key = "key"
        for index, i in enumerate(encrytion_data.encode()):
            result += chr(i ^ ord(key[index % len(key)]))
        result = b64encode(result.encode()).decode()
        return result

    # 保存存档
    def save_to_game(self):
        if self.user_card_data is not None:
            try:
                result = self.encode_save_file()
                with open(self.autosave_path, 'w') as f:
                    f.write(result)
                    print("保存成功...")
            except Exception as e:
                print(f"用户自定义数据异常,覆写游戏存档失败:{e}")
        else:
            print("用户自定义为空,不主张覆写游戏存档")

    # show_menu
    def show_menu(self):
        print("_" * 30)
        print("〖Welcome〗v0.0.1杀戮尖塔修改器")
        self.show_player_status()
        print("_" * 30)
        for k, v in self.menu_list.items():
            print(f"{k}:{v[0]}")
        print("*" * 30)
        user_func_select = input("你好,请输入功能id:")
        try:
            user_funcn = int(user_func_select)
            if user_funcn in self.menu_list:
                fun = self.menu_list.get(user_funcn)[1]
                return fun()  # 这里不用加self
        except Exception as e:
            print(f"输入错误或功能暂未开发,错误信息{e}")

    # get_start
    def start(self):
        while True:
            self.show_menu()
            sleep(3)

    # 退出程序
    @staticmethod
    def stop():
        check_save = input("如果你已经修改某些参数,请先执行保存,是否继续退出(y/n)")
        if check_save == 'y':
            print("3s后自动退出本程序")
            sleep(3)
            exit()

if __name__ == "__main__":
    slayaid = SlayAid()
    slayaid.select_storage_file()
    slayaid.start()


Great works are not done by strength, but by persistence! 历尽艰辛的飞升者,成了围剿孙悟空的十万天兵之一。
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则 需要先绑定手机号


免责声明:
本站所发布的第三方软件及资源(包括但不仅限于文字/图片/音频/视频等仅限用于学习和研究目的;不得将上述内容用于商业或者非法用途,否则,一切后果请用户自负。本站信息来自网络,版权争议与本站无关。您必须在下载后的24个小时之内,从您的电脑中彻底删除上述内容。如果您喜欢某程序或某个资源,请支持正版软件及版权方利益,注册或购买,得到更好的正版服务。如有侵权请邮件与我们联系处理。

Mail To: admin@cdsy.xyz

QQ|Archiver|手机版|小黑屋|城东书院 ( 湘ICP备19021508号-1|湘公网安备 43102202000103号 )

GMT+8, 2024-11-21 16:35 , Processed in 0.036443 second(s), 28 queries .

Powered by Discuz! CDSY.XYZ

Copyright © 2019-2023, Tencent Cloud.

快速回复 返回顶部 返回列表