can now update basic info on a critter
This commit is contained in:
@@ -28,7 +28,7 @@ public partial class ProfileButton : UserControl
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Console.WriteLine(e);
|
||||
//Console.WriteLine(e);
|
||||
}
|
||||
|
||||
ProfileNameLabel.Content = string.IsNullOrEmpty(critter.Name) ? "New Critter" : critter.Name ;
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
<UserControl xmlns="https://github.com/avaloniaui"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
|
||||
x:Class="CritterFolio.Pages.CritterPage">
|
||||
<ScrollViewer HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
|
||||
<StackPanel Spacing="10">
|
||||
<Label Classes="heading1">Info</Label>
|
||||
<StackPanel HorizontalAlignment="Stretch">
|
||||
<Label VerticalAlignment="Center">Name: </Label>
|
||||
<TextBox x:Name="NameBox" />
|
||||
</StackPanel>
|
||||
<StackPanel HorizontalAlignment="Stretch">
|
||||
<Label VerticalAlignment="Center">Gender: </Label>
|
||||
<ComboBox x:Name="GenderOption" />
|
||||
</StackPanel>
|
||||
<StackPanel HorizontalAlignment="Stretch">
|
||||
<Label VerticalAlignment="Center">Birthday: </Label>
|
||||
<DatePicker x:Name="BirthdayPicker" />
|
||||
</StackPanel>
|
||||
<StackPanel HorizontalAlignment="Stretch">
|
||||
<Label VerticalAlignment="Center">Mother: </Label>
|
||||
<ComboBox x:Name="MotherPicker" />
|
||||
</StackPanel>
|
||||
<StackPanel HorizontalAlignment="Stretch">
|
||||
<Label VerticalAlignment="Center">Father: </Label>
|
||||
<ComboBox x:Name="FatherPicker" />
|
||||
</StackPanel>
|
||||
<!-- <Button x:Name="AddButton" Classes="icon" HorizontalAlignment="Stretch"></Button> -->
|
||||
</StackPanel>
|
||||
</ScrollViewer>
|
||||
</UserControl>
|
||||
@@ -0,0 +1,190 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Avalonia;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Interactivity;
|
||||
using Avalonia.Markup.Xaml;
|
||||
using Avalonia.Media;
|
||||
using Avalonia.Threading;
|
||||
using CritterFolio.DataModels;
|
||||
using CritterFolio.Services;
|
||||
|
||||
namespace CritterFolio.Pages;
|
||||
|
||||
public partial class CritterPage : Page
|
||||
{
|
||||
private Critter? _critter;
|
||||
|
||||
public CritterPage()
|
||||
{
|
||||
InitializeComponent();
|
||||
}
|
||||
|
||||
public void Init(Critter critter)
|
||||
{
|
||||
_critter = critter;
|
||||
|
||||
UpdateInfo();
|
||||
}
|
||||
|
||||
public override void Refresh()
|
||||
{
|
||||
base.Refresh();
|
||||
CreateHeaderButtons();
|
||||
GenderOption.ItemsSource = Enum.GetNames(typeof(Gender));
|
||||
|
||||
LoadComboItemsAsync();
|
||||
}
|
||||
|
||||
private async void LoadComboItemsAsync()
|
||||
{
|
||||
try
|
||||
{
|
||||
var allCritters = await DatabaseService.GetAllCritters();
|
||||
var allCritterIds = allCritters.Select(c => c.Id).ToList();
|
||||
|
||||
await Dispatcher.UIThread.InvokeAsync(() =>
|
||||
{
|
||||
FatherPicker.ItemsSource = allCritterIds;
|
||||
MotherPicker.ItemsSource = allCritterIds;
|
||||
|
||||
UpdateInfo();
|
||||
});
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.LogToFile($"Error loading critters: {ex}");
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateInfo()
|
||||
{
|
||||
Sys.Navigation?.SetTitle(_critter.Name);
|
||||
|
||||
NameBox.Text = _critter.Name;
|
||||
GenderOption.SelectedItem = Enum.GetName(typeof(Gender), _critter.Gender);
|
||||
BirthdayPicker.SelectedDate = _critter.DateOfBirth;
|
||||
MotherPicker.SelectedItem = _critter.FatherId;
|
||||
FatherPicker.SelectedItem = _critter.FatherId;
|
||||
}
|
||||
|
||||
private void CreateHeaderButtons()
|
||||
{
|
||||
var saveBttn = new Button()
|
||||
{
|
||||
Classes = { "headerBttn" },
|
||||
Content = "\ue248"
|
||||
};
|
||||
|
||||
saveBttn.Click += SaveButtonClicked;
|
||||
Sys.Navigation?.AddHeaderButton(saveBttn);
|
||||
|
||||
var delBttn = new Button()
|
||||
{
|
||||
Classes = { "headerBttn" },
|
||||
Content = "\ue4a6"
|
||||
};
|
||||
delBttn.Foreground = new SolidColorBrush(Colors.DarkRed);
|
||||
delBttn.Click += DeleteButtonClicked;
|
||||
Sys.Navigation?.AddHeaderButton(delBttn);
|
||||
}
|
||||
|
||||
private async void DeleteButtonClicked(object? sender, RoutedEventArgs args)
|
||||
{
|
||||
|
||||
try
|
||||
{
|
||||
var result = await DialogHelper.ShowConfirmationDialog("Are you sure you want to delete this critter?");
|
||||
if (!result) return;
|
||||
await DatabaseService.DeleteCritter(_critter);
|
||||
Sys.Navigation?.PopPage();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Logger.LogToFile(e.ToString());
|
||||
await DialogHelper.ShowMessage($"Error: {e.Message}");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private async void SaveButtonClicked(object? sender, RoutedEventArgs args)
|
||||
{
|
||||
if (_critter is null) return;
|
||||
try
|
||||
{
|
||||
var result = await DialogHelper.ShowConfirmationDialog("Are you sure you want to save this critter?");
|
||||
if (!result) return;
|
||||
|
||||
var validationResult = await TryValidateAndSave();
|
||||
if (!validationResult.isValid)
|
||||
{
|
||||
await DialogHelper.ShowMessage($"Validation error:\n{validationResult.errors}");
|
||||
return;
|
||||
}
|
||||
|
||||
await DatabaseService.UpdateCritter(_critter);
|
||||
UpdateInfo();
|
||||
|
||||
await DialogHelper.ShowMessage($"Critter '{_critter.Name}' saved!");
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Logger.LogToFile(e.ToString());
|
||||
await DialogHelper.ShowMessage($"Error: {e.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
private async Task<(bool isValid, string errors)> TryValidateAndSave()
|
||||
{
|
||||
var errString = "";
|
||||
|
||||
if (_critter is null) return (false, "Critter is null somehow. Please report this to the developer");
|
||||
|
||||
_critter.Name = NameBox.Text!;
|
||||
|
||||
// Gender validation
|
||||
if (Enum.TryParse<Gender>(GenderOption.SelectedItem?.ToString(), true, out var gender))
|
||||
{
|
||||
_critter.Gender = gender;
|
||||
}
|
||||
else
|
||||
{
|
||||
errString += "Invalid gender somehow. Please report this to the developer\n";
|
||||
}
|
||||
|
||||
// Birthday validation
|
||||
if (BirthdayPicker.SelectedDate is not null)
|
||||
{
|
||||
_critter.DateOfBirth = BirthdayPicker.SelectedDate.Value.DateTime;
|
||||
}
|
||||
else
|
||||
{
|
||||
errString += "Birthday is null somehow. Please report this to the developer\n";
|
||||
}
|
||||
|
||||
// Father ID validation
|
||||
if (FatherPicker.SelectedItem is int fatherId)
|
||||
{
|
||||
_critter.FatherId = fatherId;
|
||||
}
|
||||
else
|
||||
{
|
||||
errString += "FatherId is null or invalid somehow. Please report this to the developer\n";
|
||||
}
|
||||
|
||||
// Mother ID validation
|
||||
if (MotherPicker.SelectedItem is int motherId)
|
||||
{
|
||||
_critter.MotherId = motherId;
|
||||
}
|
||||
else
|
||||
{
|
||||
errString += "MotherId is null or invalid somehow. Please report this to the developer\n";
|
||||
}
|
||||
|
||||
return errString != "" ? (false, errString) : (true, errString);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -66,31 +66,23 @@ public partial class HomePage : Page
|
||||
}
|
||||
}
|
||||
|
||||
private async void AddProfileButton(Critter critter)
|
||||
private void AddProfileButton(Critter critter)
|
||||
{
|
||||
var newProfButton = new ProfileButton();
|
||||
newProfButton.Init(critter);
|
||||
CritterStack.Children.Add(newProfButton);
|
||||
|
||||
|
||||
|
||||
newProfButton.Clicked += async (sender, args) =>
|
||||
newProfButton.Clicked += (sender, args) =>
|
||||
{
|
||||
await ProfileButtonClicked(critter);
|
||||
ProfileButtonClicked(critter);
|
||||
};
|
||||
}
|
||||
|
||||
private async Task ProfileButtonClicked(Critter critter)
|
||||
private void ProfileButtonClicked(Critter critter)
|
||||
{
|
||||
try
|
||||
{
|
||||
await DialogHelper.ShowMessage($"{critter.Name} was clicked");
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Console.WriteLine(e);
|
||||
Logger.LogToFile(e.ToString());
|
||||
}
|
||||
var critterPage = new CritterPage();
|
||||
critterPage.Init(critter);
|
||||
Sys.Navigation?.PushPage(critterPage);
|
||||
}
|
||||
|
||||
private async void AddButtonClicked(object? sender, RoutedEventArgs e)
|
||||
|
||||
@@ -72,5 +72,11 @@ public static class DatabaseService
|
||||
return result ?? [];
|
||||
}
|
||||
|
||||
public static async Task<Critter?> GetCritter(int id)
|
||||
{
|
||||
await Init();
|
||||
return _db?.GetAsync<Critter>(id).Result;
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
@@ -21,4 +21,15 @@ public static class DialogHelper
|
||||
Console.WriteLine(e);
|
||||
}
|
||||
}
|
||||
|
||||
public static async Task<bool> ShowConfirmationDialog(string message)
|
||||
{
|
||||
TwofoldDialog dialog = new()
|
||||
{
|
||||
Message = message,
|
||||
PositiveText = "Yes",
|
||||
NegativeText = "Cancel"
|
||||
};
|
||||
return (await dialog.ShowAsync()).GetValueOrDefault();
|
||||
}
|
||||
}
|
||||
@@ -9,7 +9,5 @@
|
||||
x:Class="CritterFolio.Views.MainWindow"
|
||||
Icon="/Assets/icon.ico"
|
||||
Title="CritterFolio">
|
||||
<dialogs:ReactiveDialogHost CloseOnClickAway="True">
|
||||
<views:MainView />
|
||||
</dialogs:ReactiveDialogHost>
|
||||
<views:MainView />
|
||||
</Window>
|
||||
|
||||
Reference in New Issue
Block a user