WinForms跨窗体保存获胜Hero信息的C#实现求助
实现RPG子窗体Hero信息保存到主窗体二进制存档的方案
首先确保你的Hero类支持二进制序列化——因为主窗体用的是二进制存档,必须给类加上[Serializable]特性:
[Serializable] public class Hero { // 自定义Hero属性示例 public string Name { get; set; } public int Level { get; set; } public int Attack { get; set; } // 其他业务属性... }
以下是几种低耦合的实现方法:
方法一:使用事件传递(推荐,解耦主/子窗体)
1. 在子窗体定义获胜事件
在RPG子窗体中定义事件,当Hero获胜时触发并传递Hero实例:
public partial class RPGSubForm : Form { // 定义事件,参数为获胜的Hero对象 public event Action<Hero> HeroWon; // 战斗胜利后的触发逻辑示例 private void OnBattleWin() { // 实例化或获取当前获胜的Hero Hero wonHero = new Hero { Name = "狂战", Level = 5, Attack = 110 }; // 触发事件通知主窗体 HeroWon?.Invoke(wonHero); // 关闭子窗体(按需选择) this.Close(); } }
2. 主窗体订阅事件并更新存档
主窗体打开子窗体时订阅事件,拿到Hero后更新存档数据,调用已有保存方法:
public partial class MainForm : Form { // 主窗体存档数据结构,需新增Hero存储属性 [Serializable] public class GameSaveData { // 主窗体原有存档字段 public int TotalScore { get; set; } public string PlayerNickname { get; set; } // 新增存储获胜Hero的集合 public List<Hero> UnlockedHeroes { get; set; } = new List<Hero>(); } private GameSaveData _currentSave = new GameSaveData(); // 打开RPG子窗体的方法 private void OpenRPGSubForm() { RPGSubForm subForm = new RPGSubForm(); // 订阅子窗体的获胜事件 subForm.HeroWon += SubForm_HeroWon; subForm.ShowDialog(); } // 事件处理:接收Hero并更新存档 private void SubForm_HeroWon(Hero hero) { _currentSave.UnlockedHeroes.Add(hero); // 调用主窗体已有的保存方法 SaveCurrentGame(); } // 主窗体原有二进制保存方法(示例) private void SaveCurrentGame() { using (FileStream fs = new FileStream("game_save.bin", FileMode.Create)) { BinaryFormatter formatter = new BinaryFormatter(); formatter.Serialize(fs, _currentSave); } } }
方法二:通过子窗体公开属性传递
如果不想用事件,可以在子窗体中公开属性,主窗体在子窗体关闭后读取:
1. 子窗体添加公开属性
public partial class RPGSubForm : Form { // 公开获胜Hero的只读属性 public Hero WonHero { get; private set; } private void OnBattleWin() { WonHero = new Hero { Name = "冰法", Level = 6, Attack = 130 }; this.DialogResult = DialogResult.OK; this.Close(); } }
2. 主窗体读取属性并保存
private void OpenRPGSubForm() { RPGSubForm subForm = new RPGSubForm(); if (subForm.ShowDialog() == DialogResult.OK) { if (subForm.WonHero != null) { _currentSave.UnlockedHeroes.Add(subForm.WonHero); SaveCurrentGame(); } } }
注意事项
- 所有需要序列化的类(
GameSaveData、Hero)必须标记[Serializable],否则二进制序列化会失败;若有不需要序列化的字段,用[NonSerialized]标记。 - 若使用.NET Core/.NET 5+,
BinaryFormatter已被标记为过时,可改用System.Text.Json(需配置序列化选项支持类对象)或Protobuf替代;.NET Framework项目可正常使用BinaryFormatter。
内容的提问来源于stack exchange,提问作者LookingforHelp
相关产品推荐
相关产品推荐

