using System; using System.Diagnostics; using System.Runtime.Serialization; using System.Runtime.Serialization.Formatters.Binary; using System.Windows.Input; using Life.Automaton; using Life.Misc; using Microsoft.Win32; namespace Life.ViewModel { public class AutomatonViewModel : BaseViewModel { private int _size; private int _separation; private int _width; private int _height; private int _steps; private string _rule = "3/23"; private IAutomaton _automaton; private IFormatter _formatter = new BinaryFormatter(); public AutomatonViewModel() { PropertyChanged += (sender, args) => { if (args.PropertyName == nameof(Field)) { Width = Field.Size.Width; Height = Field.Size.Height; } }; } public string Rule { get => _rule; set { _rule = value; var split = value.Split("/"); Automaton.Rule = new GameOfLife.StandardRule(split[0], split[1] ?? "23"); OnPropertyChanged(nameof(Rule)); } } public int Size { get => _size; set { _size = value; OnPropertyChanged(nameof(Size)); } } public int Separation { get => _separation; set { _separation = value; OnPropertyChanged(nameof(Separation)); } } public int Width { get => _width; set { _width = value; OnPropertyChanged(nameof(Width)); } } public int Height { get => _height; set { _height = value; OnPropertyChanged(nameof(Height)); } } public IAutomaton Automaton { get => _automaton; set { _automaton = value; OnPropertyChanged(nameof(Field)); OnPropertyChanged(nameof(Iteration)); Rule = Automaton.Rule.ToString(); } } public int Steps { get => _steps; set { _steps = value; OnPropertyChanged(nameof(Steps)); } } public IField Field => Automaton.Field; public int Iteration => Automaton.Iteration; public ICommand CellClicked => new DelegateCommand { Action = HandleCellClick }; public ICommand ChangeSizeCommand => new DelegateCommand { Action = HandleSizeChange }; public ICommand LoadCommand => new DelegateCommand { Action = HandleLoadCommand }; public ICommand ResetCommand => new DelegateCommand { Action = HandleResetCommand }; public ICommand SaveCommand => new DelegateCommand { Action = HandleSaveCommand }; public ICommand StepCommand => new DelegateCommand { Action = Step }; private void Step(int param) { for (int i = 0; i < param; i++) Automaton.Advance(); OnPropertyChanged(nameof(Iteration)); } private void HandleCellClick(Position position) { Field[position.X, position.Y].IsAlive = !Field[position.X, position.Y].IsAlive; Field.Notify(); } private void HandleSizeChange(object obj) { Field.Resize(Width, Height); OnPropertyChanged(nameof(Field)); } private void HandleLoadCommand(object _) { OpenFileDialog dialog = new OpenFileDialog(); if (dialog.ShowDialog() == true) { using var file = dialog.OpenFile(); Automaton = _formatter.Deserialize(file) as IAutomaton; } } private void HandleSaveCommand(object _) { SaveFileDialog dialog = new SaveFileDialog(); if (dialog.ShowDialog() == true) { using var file = dialog.OpenFile(); _formatter.Serialize(file, Automaton); } } private void HandleResetCommand(object _) { Automaton.Reset(); OnPropertyChanged(nameof(Iteration)); } } }