3 Commits
main ... v1

Author SHA1 Message Date
6ff17cf9aa Agregar mantenimiento de Concepto y TipoMovimiento 2025-09-13 21:10:34 -06:00
985351f6a8 Mejoras 2025-09-13 20:34:08 -06:00
598b2c2936 Nueva rama 2025-09-13 18:25:57 -06:00
16 changed files with 579 additions and 96 deletions

View File

@@ -5,7 +5,9 @@
<map> <map>
<entry key="AdminFinanceRCA/App.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" /> <entry key="AdminFinanceRCA/App.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
<entry key="AdminFinanceRCA/Views/MainWindow.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" /> <entry key="AdminFinanceRCA/Views/MainWindow.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
<entry key="AdminFinanceRCA/Views/Mantenimiento_Concepto.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
<entry key="AdminFinanceRCA/Views/Mantenimiento_DepartTrabajo.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" /> <entry key="AdminFinanceRCA/Views/Mantenimiento_DepartTrabajo.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
<entry key="AdminFinanceRCA/Views/Mantenimiento_TipoMovimiento.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
<entry key="AdminFinanceRCA/Views/MovimientoWindow.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" /> <entry key="AdminFinanceRCA/Views/MovimientoWindow.axaml" value="AdminFinanceRCA/AdminFinanceRCA.csproj" />
</map> </map>
</option> </option>

View File

@@ -25,8 +25,6 @@
</PackageReference> </PackageReference>
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.2.1" /> <PackageReference Include="CommunityToolkit.Mvvm" Version="8.2.1" />
<PackageReference Include="Dapper" Version="2.1.66" /> <PackageReference Include="Dapper" Version="2.1.66" />
<PackageReference Include="Material.Avalonia" Version="3.13.0" />
<PackageReference Include="Material.Avalonia.Dialogs" Version="3.13.0" />
<PackageReference Include="MessageBox.Avalonia" Version="3.2.0" /> <PackageReference Include="MessageBox.Avalonia" Version="3.2.0" />
<PackageReference Include="Microsoft.Data.Sqlite" Version="9.0.8" /> <PackageReference Include="Microsoft.Data.Sqlite" Version="9.0.8" />
<PackageReference Include="Microsoft.Extensions.Configuration" Version="10.0.0-preview.7.25380.108" /> <PackageReference Include="Microsoft.Extensions.Configuration" Version="10.0.0-preview.7.25380.108" />
@@ -40,4 +38,15 @@
<CopyToOutputDirectory>Always</CopyToOutputDirectory> <CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None> </None>
</ItemGroup> </ItemGroup>
<ItemGroup>
<Compile Update="Views\Mantenimiento_Concepto.axaml.cs">
<DependentUpon>Mantenimiento_Concepto.axaml</DependentUpon>
<SubType>Code</SubType>
</Compile>
<Compile Update="Views\Mantenimiento_TipoMovimiento.axaml.cs">
<DependentUpon>Mantenimiento_TipoMovimiento.axaml</DependentUpon>
<SubType>Code</SubType>
</Compile>
</ItemGroup>
</Project> </Project>

View File

@@ -2,16 +2,14 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
x:Class="AdminFinanceRCA.App" x:Class="AdminFinanceRCA.App"
xmlns:local="using:AdminFinanceRCA" xmlns:local="using:AdminFinanceRCA"
RequestedThemeVariant="Default" RequestedThemeVariant="Default">
xmlns:themes="clr-namespace:Material.Styles.Themes;assembly=Material.Styles"
>
<Application.DataTemplates> <Application.DataTemplates>
<local:ViewLocator/> <local:ViewLocator/>
</Application.DataTemplates> </Application.DataTemplates>
<Application.Styles> <Application.Styles>
<FluentTheme /> <FluentTheme />
<themes:MaterialTheme BaseTheme="Dark" PrimaryColor="Purple" SecondaryColor="Lime" /> <!-- <themes:MaterialTheme BaseTheme="Dark" PrimaryColor="Purple" SecondaryColor="Lime" /> -->
<StyleInclude Source="avares://Avalonia.Controls.DataGrid/Themes/Fluent.xaml"/> <StyleInclude Source="avares://Avalonia.Controls.DataGrid/Themes/Fluent.xaml"/>
</Application.Styles> </Application.Styles>
</Application> </Application>

View File

@@ -3,13 +3,12 @@ using System.IO;
using System.Text; using System.Text;
using System.Threading.Tasks; using System.Threading.Tasks;
using AdminFinanceRCA.Models; using AdminFinanceRCA.Models;
namespace AdminFinanceRCA;
using System.Data; using System.Data;
using Dapper; using Dapper;
using Microsoft.Data.Sqlite; using Microsoft.Data.Sqlite;
namespace AdminFinanceRCA;
public class FinanzasRepository public class FinanzasRepository
{ {
private readonly string _connectionString; private readonly string _connectionString;
@@ -20,7 +19,6 @@ public class FinanzasRepository
_connectionString = config.GetConnectionString(); _connectionString = config.GetConnectionString();
InitializeDatabase(); InitializeDatabase();
} }
// Constructor alternativo para testing
public FinanzasRepository(string connectionString) public FinanzasRepository(string connectionString)
{ {
_connectionString = connectionString; _connectionString = connectionString;
@@ -42,7 +40,8 @@ public class FinanzasRepository
connection.Execute(@" connection.Execute(@"
CREATE TABLE IF NOT EXISTS DepartTrabajo ( CREATE TABLE IF NOT EXISTS DepartTrabajo (
Id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, Id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
Nombre TEXT NOT NULL Nombre TEXT NOT NULL,
Descripcion TEXT NULL
)"); )");
connection.Execute(@" connection.Execute(@"
@@ -69,40 +68,6 @@ public class FinanzasRepository
// Crear índice // Crear índice
connection.Execute(@" connection.Execute(@"
CREATE INDEX IF NOT EXISTS Mov ON Movimientos (Concepto ASC, TipoMov ASC)"); CREATE INDEX IF NOT EXISTS Mov ON Movimientos (Concepto ASC, TipoMov ASC)");
// Insertar datos básicos si las tablas están vacías
InsertarDatosBasicos(connection);
}
}
private void InsertarDatosBasicos(SqliteConnection connection)
{
// Verificar si TipoMovimiento está vacío
var countTipos = connection.ExecuteScalar<int>("SELECT COUNT(*) FROM TipoMovimiento");
if (countTipos == 0)
{
connection.Execute("INSERT INTO TipoMovimiento (Nombre) VALUES ('Ingreso')");
connection.Execute("INSERT INTO TipoMovimiento (Nombre) VALUES ('Egreso')");
}
// Verificar si Concepto está vacío
var countConceptos = connection.ExecuteScalar<int>("SELECT COUNT(*) FROM Concepto");
if (countConceptos == 0)
{
connection.Execute("INSERT INTO Concepto (Nombre) VALUES ('Ventas')");
connection.Execute("INSERT INTO Concepto (Nombre) VALUES ('Compras')");
connection.Execute("INSERT INTO Concepto (Nombre) VALUES ('Nómina')");
connection.Execute("INSERT INTO Concepto (Nombre) VALUES ('Servicios')");
}
// Verificar si DepartTrabajo está vacío
var countDeptos = connection.ExecuteScalar<int>("SELECT COUNT(*) FROM DepartTrabajo");
if (countDeptos == 0)
{
connection.Execute("INSERT INTO DepartTrabajo (Nombre) VALUES ('Administración')");
connection.Execute("INSERT INTO DepartTrabajo (Nombre) VALUES ('Ventas')");
connection.Execute("INSERT INTO DepartTrabajo (Nombre) VALUES ('Producción')");
connection.Execute("INSERT INTO DepartTrabajo (Nombre) VALUES ('Logística')");
} }
} }
@@ -215,10 +180,22 @@ public class FinanzasRepository
} }
} }
public async Task<bool> UpdateConceptoAsync(Concepto concepto)
{
using (var connection = GetConnection())
{
var sql = @"UPDATE Concepto
SET Nombre = @Nombre
WHERE Id = @Id;";
var rowsAffected = await connection.ExecuteAsync(sql, concepto);
return rowsAffected > 0;
}
}
#endregion #endregion
#region Operaciones para DepartTrabajo #region Operaciones para DepartTrabajo
public async Task<IEnumerable<DepartTrabajo>> GetAllDepartamentosAsync() public async Task<IEnumerable<DepartTrabajo>> GetAllDepartamentosAsync()
{ {
using (var connection = GetConnection()) using (var connection = GetConnection())
@@ -249,7 +226,6 @@ public class FinanzasRepository
return rowsAffected > 0; return rowsAffected > 0;
} }
} }
#endregion #endregion
#region Operaciones para TipoMovimiento #region Operaciones para TipoMovimiento
@@ -272,6 +248,19 @@ public class FinanzasRepository
} }
} }
public async Task<bool> UpdateTipoMovimientoAsync(TipoMovimiento tipomov)
{
using (var connection = GetConnection())
{
var sql = @"UPDATE Concepto
SET Nombre = @Nombre
WHERE Id = @Id;";
var rowsAffected = await connection.ExecuteAsync(sql, tipomov);
return rowsAffected > 0;
}
}
#endregion #endregion
#region Métodos de exportación #region Métodos de exportación

View File

@@ -5,9 +5,7 @@ using System.Diagnostics;
using System.Threading.Tasks; using System.Threading.Tasks;
using AdminFinanceRCA.Models; using AdminFinanceRCA.Models;
using AdminFinanceRCA.Views; using AdminFinanceRCA.Views;
using Avalonia;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Controls.ApplicationLifetimes;
using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input; using CommunityToolkit.Mvvm.Input;
@@ -41,16 +39,49 @@ public partial class MainWindowViewModel : ViewModelBase
departTrabajo.ShowDialog(GetCurrentWindow<MainWindow>()); departTrabajo.ShowDialog(GetCurrentWindow<MainWindow>());
} }
[RelayCommand]
public void AgregarConcepto()
{
Mantenimiento_ConceptoViewModel mantenimiento = new Mantenimiento_ConceptoViewModel();
Mantenimiento_Concepto conceptoWindow = new Mantenimiento_Concepto()
{
DataContext = mantenimiento
};
conceptoWindow.ShowDialog(GetCurrentWindow<MainWindow>());
}
[RelayCommand]
public void AgregarTipoMovimiento()
{
Mantenimiento_TipoMovViewModel mantenimiento = new Mantenimiento_TipoMovViewModel();
Mantenimiento_TipoMovimiento conceptoWindow = new Mantenimiento_TipoMovimiento()
{
DataContext = mantenimiento
};
conceptoWindow.ShowDialog(GetCurrentWindow<MainWindow>());
}
[RelayCommand] [RelayCommand]
public void AgregarMovimiento() public void AgregarMovimiento()
{ {
MovimientoWindowViewModel mwvm = new MovimientoWindowViewModel(); MovimientoWindowViewModel mwvm = new MovimientoWindowViewModel();
mwvm.ReloadEvent+= MwvmOnReloadEvent;
MovimientoWindow mw = new MovimientoWindow(); MovimientoWindow mw = new MovimientoWindow()
{
Width = 600,
Height = 450,
};
mw.DataContext = mwvm; mw.DataContext = mwvm;
mw.ShowDialog(GetCurrentWindow<MainWindow>()); mw.ShowDialog(GetCurrentWindow<MainWindow>());
} }
private async void MwvmOnReloadEvent(object? sender, EventArgs e)
{
var movimientosTask = _repository.GetAllMovimientosCompletosAsync();
Movimientos = new ObservableCollection<MovimientoCompleto>(await movimientosTask);
}
[RelayCommand] [RelayCommand]
public void Salir() public void Salir()
{ {

View File

@@ -0,0 +1,97 @@
using System;
using System.Collections.ObjectModel;
using System.Threading.Tasks;
using AdminFinanceRCA.Models;
using AdminFinanceRCA.Views;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using MsBox.Avalonia;
using MsBox.Avalonia.Enums;
namespace AdminFinanceRCA.ViewModels;
public partial class Mantenimiento_ConceptoViewModel : ViewModelBase
{
private readonly FinanzasRepository _conceptoService;
public event EventHandler? ReloadEvent;
[ObservableProperty] private ObservableCollection<Concepto> _conceptos;
[ObservableProperty] private Concepto _conceptoSeleccionado;
[ObservableProperty] private Concepto _conceptoEditando;
[ObservableProperty] private bool _estaEditando;
[ObservableProperty] private string _nombre;
// [ObservableProperty] private string _descripcion;
public Mantenimiento_ConceptoViewModel()
{
_conceptoService = new FinanzasRepository();
_ = CargarDatosAsync();
}
async Task CargarDatosAsync()
{
var dt = await _conceptoService.GetAllConceptosAsync();
Conceptos = new ObservableCollection<Concepto>(dt);
}
[RelayCommand]
private void NuevoConcepto()
{
Nombre = string.Empty;
// Descripcion = string.Empty;
EstaEditando = false;
}
[RelayCommand]
private async Task GuardarRegistros()
{
string[] mensaje = {"", string.Empty};
if (EstaEditando)
{
try
{
ConceptoSeleccionado.Nombre = Nombre;
// GrupoSeleccionado.Descripcion = Descripcion;
await _conceptoService.UpdateConceptoAsync(ConceptoSeleccionado);
mensaje = new[] { "Exito", "Registro actualizado con exito" };
}
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
}
else
{
try
{
if(string.IsNullOrEmpty(Nombre))
return;
Concepto concept = new Concepto(Nombre);
await _conceptoService.CreateConceptoAsync(concept);
Nombre = string.Empty;
// Descripcion = string.Empty;
mensaje = new[] { "Exito", "Registro agregado con exito" };
}
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
}
var dt = MessageBoxManager.GetMessageBoxStandard(mensaje[0], mensaje[1], ButtonEnum.Ok);
await dt.ShowAsPopupAsync(GetCurrentWindow<Mantenimiento_Concepto>());
OnReloadEvent();
await CargarDatosAsync();
}
[RelayCommand]
private void Cancelar()
{
this.GetCurrentWindow<Mantenimiento_Concepto>().Close();
}
protected virtual void OnReloadEvent()
{
ReloadEvent?.Invoke(this, EventArgs.Empty);
}
}

View File

@@ -1,18 +1,19 @@
using System;
using System.Collections.ObjectModel; using System.Collections.ObjectModel;
using System.Runtime.Serialization;
using System.Threading.Tasks; using System.Threading.Tasks;
using AdminFinanceRCA.Models; using AdminFinanceRCA.Models;
using AdminFinanceRCA.Views; using AdminFinanceRCA.Views;
using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input; using CommunityToolkit.Mvvm.Input;
using Material.Dialog.Views; using MsBox.Avalonia;
using MsBox.Avalonia.Enums;
namespace AdminFinanceRCA.ViewModels; namespace AdminFinanceRCA.ViewModels;
public partial class Mantenimiento_DepartTrabajoViewModel : ViewModelBase public partial class Mantenimiento_DepartTrabajoViewModel : ViewModelBase
{ {
private readonly FinanzasRepository _departTrabajoService; private readonly FinanzasRepository _departTrabajoService;
public event EventHandler? ReloadEvent;
[ObservableProperty] private ObservableCollection<DepartTrabajo> _gruposTrabajo; [ObservableProperty] private ObservableCollection<DepartTrabajo> _gruposTrabajo;
[ObservableProperty] private DepartTrabajo _grupoSeleccionado; [ObservableProperty] private DepartTrabajo _grupoSeleccionado;
[ObservableProperty] private DepartTrabajo _grupoEditando; [ObservableProperty] private DepartTrabajo _grupoEditando;
@@ -43,14 +44,24 @@ public partial class Mantenimiento_DepartTrabajoViewModel : ViewModelBase
[RelayCommand] [RelayCommand]
private async Task GuardarRegistros() private async Task GuardarRegistros()
{ {
string[] mensaje = {"", string.Empty};
if (EstaEditando) if (EstaEditando)
{
try
{ {
GrupoSeleccionado.Nombre = Nombre; GrupoSeleccionado.Nombre = Nombre;
GrupoSeleccionado.Descripcion = Descripcion; GrupoSeleccionado.Descripcion = Descripcion;
_departTrabajoService.UpdateDepartamentoAsync(GrupoSeleccionado); _departTrabajoService.UpdateDepartamentoAsync(GrupoSeleccionado);
mensaje = new[] { "Exito", "Registro actualizado con exito" };
}
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
} }
else else
{
try
{ {
if(string.IsNullOrEmpty(Nombre)) if(string.IsNullOrEmpty(Nombre))
return; return;
@@ -59,10 +70,28 @@ public partial class Mantenimiento_DepartTrabajoViewModel : ViewModelBase
await _departTrabajoService.CreateDepartamentoAsync(depart); await _departTrabajoService.CreateDepartamentoAsync(depart);
Nombre = string.Empty; Nombre = string.Empty;
Descripcion = string.Empty; Descripcion = string.Empty;
AlertDialog ad = new AlertDialog();
ad.Title = "Exito"; mensaje = new[] { "Exito", "Registro agregado con exito" };
ad.Content = "Registro agregado con exito";
ad.Show(GetCurrentWindow<Mantenimiento_DepartTrabajo>());
} }
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
}
var dt = MessageBoxManager.GetMessageBoxStandard(mensaje[0], mensaje[1], ButtonEnum.Ok);
await dt.ShowAsPopupAsync(GetCurrentWindow<Mantenimiento_DepartTrabajo>());
OnReloadEvent();
await CargarDatosAsync();
}
[RelayCommand]
private void Cancelar()
{
this.GetCurrentWindow<Mantenimiento_DepartTrabajo>().Close();
}
protected virtual void OnReloadEvent()
{
ReloadEvent?.Invoke(this, EventArgs.Empty);
} }
} }

View File

@@ -0,0 +1,97 @@
using System;
using System.Collections.ObjectModel;
using System.Threading.Tasks;
using AdminFinanceRCA.Models;
using AdminFinanceRCA.Views;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using MsBox.Avalonia;
using MsBox.Avalonia.Enums;
namespace AdminFinanceRCA.ViewModels;
public partial class Mantenimiento_TipoMovViewModel : ViewModelBase
{
private readonly FinanzasRepository _repositoryService;
public event EventHandler? ReloadEvent;
[ObservableProperty] private ObservableCollection<TipoMovimiento> _tipoMovimientos;
[ObservableProperty] private TipoMovimiento _tipoMovSeleccionado;
[ObservableProperty] private TipoMovimiento _tipoMovEditando;
[ObservableProperty] private bool _estaEditando;
[ObservableProperty] private string _nombre;
// [ObservableProperty] private string _descripcion;
public Mantenimiento_TipoMovViewModel()
{
_repositoryService = new FinanzasRepository();
_ = CargarDatosAsync();
}
async Task CargarDatosAsync()
{
var dt = await _repositoryService.GetAllTiposMovimientoAsync();
TipoMovimientos = new ObservableCollection<TipoMovimiento>(dt);
}
[RelayCommand]
private void NuevoTipoMov()
{
Nombre = string.Empty;
// Descripcion = string.Empty;
EstaEditando = false;
}
[RelayCommand]
private async Task GuardarRegistros()
{
string[] mensaje = {"", string.Empty};
if (EstaEditando)
{
try
{
TipoMovSeleccionado.Nombre = Nombre;
// GrupoSeleccionado.Descripcion = Descripcion;
await _repositoryService.UpdateTipoMovimientoAsync(TipoMovSeleccionado);
mensaje = new[] { "Exito", "Registro actualizado con exito" };
}
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
}
else
{
try
{
if(string.IsNullOrEmpty(Nombre))
return;
TipoMovimiento tipomov = new TipoMovimiento(Nombre);
await _repositoryService.CreateTipoMovimientoAsync(tipomov);
Nombre = string.Empty;
// Descripcion = string.Empty;
mensaje = new[] { "Exito", "Registro agregado con exito" };
}
catch (Exception ex)
{
mensaje = new[] { "Error", ex.Message };
}
}
var dt = MessageBoxManager.GetMessageBoxStandard(mensaje[0], mensaje[1], ButtonEnum.Ok);
await dt.ShowAsPopupAsync(GetCurrentWindow<Mantenimiento_TipoMovimiento>());
OnReloadEvent();
await CargarDatosAsync();
}
[RelayCommand]
private void Cancelar()
{
this.GetCurrentWindow<Mantenimiento_TipoMovimiento>().Close();
}
protected virtual void OnReloadEvent()
{
ReloadEvent?.Invoke(this, EventArgs.Empty);
}
}

View File

@@ -1,11 +1,11 @@
using System; using System;
using System.Collections.Generic;
using System.Collections.ObjectModel; using System.Collections.ObjectModel;
using System.Threading.Tasks; using System.Threading.Tasks;
using AdminFinanceRCA.Models; using AdminFinanceRCA.Models;
using AdminFinanceRCA.Views; using AdminFinanceRCA.Views;
using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input; using CommunityToolkit.Mvvm.Input;
using Material.Dialog.Views;
using MsBox.Avalonia; using MsBox.Avalonia;
using MsBox.Avalonia.Enums; using MsBox.Avalonia.Enums;
@@ -14,11 +14,11 @@ namespace AdminFinanceRCA.ViewModels;
public partial class MovimientoWindowViewModel : ViewModelBase public partial class MovimientoWindowViewModel : ViewModelBase
{ {
private readonly FinanzasRepository _finanzasRepository; private readonly FinanzasRepository _finanzasRepository;
public event EventHandler? ReloadEvent;
[ObservableProperty] private ObservableCollection<DepartTrabajo> _departTrabajos; [ObservableProperty] private ObservableCollection<DepartTrabajo> _departTrabajos;
[ObservableProperty] private ObservableCollection<TipoMovimiento> _tipoMovimientos; [ObservableProperty] private ObservableCollection<TipoMovimiento> _tipoMovimientos;
[ObservableProperty] private ObservableCollection<Concepto> _conceptos; [ObservableProperty] private ObservableCollection<Concepto> _conceptos;
[ObservableProperty] private DateTime _fechaMov; [ObservableProperty] private DateTimeOffset _fechaMov;
[ObservableProperty] private decimal _montoDecimal; [ObservableProperty] private decimal _montoDecimal;
[ObservableProperty] private string _descripcion; [ObservableProperty] private string _descripcion;
[ObservableProperty] private TipoMovimiento _tipoMovimientoSelecionado; [ObservableProperty] private TipoMovimiento _tipoMovimientoSelecionado;
@@ -27,7 +27,7 @@ public partial class MovimientoWindowViewModel : ViewModelBase
public MovimientoWindowViewModel() public MovimientoWindowViewModel()
{ {
_fechaMov = DateTime.Now; _fechaMov = DateTimeOffset.Now;
_finanzasRepository = new FinanzasRepository(); _finanzasRepository = new FinanzasRepository();
_ = CargarDatosAsync(); _ = CargarDatosAsync();
} }
@@ -36,22 +36,90 @@ public partial class MovimientoWindowViewModel : ViewModelBase
{ {
var dt = await _finanzasRepository.GetAllDepartamentosAsync(); var dt = await _finanzasRepository.GetAllDepartamentosAsync();
DepartTrabajos = new ObservableCollection<DepartTrabajo>(dt); DepartTrabajos = new ObservableCollection<DepartTrabajo>(dt);
var tm = await _finanzasRepository.GetAllTiposMovimientoAsync(); var tm = await _finanzasRepository.GetAllTiposMovimientoAsync();
TipoMovimientos = new ObservableCollection<TipoMovimiento>(tm); TipoMovimientos = new ObservableCollection<TipoMovimiento>(tm);
var cpt = await _finanzasRepository.GetAllConceptosAsync(); var cpt = await _finanzasRepository.GetAllConceptosAsync();
Conceptos = new ObservableCollection<Concepto>(cpt); Conceptos = new ObservableCollection<Concepto>(cpt);
DepartaDepartTrabajoSeleccionado = DepartTrabajos[0];
TipoMovimientoSelecionado = TipoMovimientos[0];
ConceptoSeleccionado = Conceptos[0];
} }
[RelayCommand] [RelayCommand]
public async void GuardarDatosAsync() public async void GuardarDatosAsync()
{ {
try
{
// Validar campos obligatorios
if (!ValidarCamposObligatorios())
{
return; // Detener ejecución si hay campos inválidos
}
Movimiento mv = new Movimiento(MontoDecimal, TipoMovimientoSelecionado.ID, DepartaDepartTrabajoSeleccionado.Id, Movimiento mv = new Movimiento(MontoDecimal, TipoMovimientoSelecionado.ID, DepartaDepartTrabajoSeleccionado.Id,
FechaMov, ConceptoSeleccionado.ID, Descripcion); DateTime.Parse(FechaMov.ToString("yyyy-MM-dd")), ConceptoSeleccionado.ID, Descripcion);
await _finanzasRepository.CreateMovimientoAsync(mv); await _finanzasRepository.CreateMovimientoAsync(mv);
var dt = MessageBoxManager.GetMessageBoxStandard("", "Se guardo con exito", ButtonEnum.Ok); var dt = MessageBoxManager.GetMessageBoxStandard("", "Se guardo con exito", ButtonEnum.Ok);
await dt.ShowAsPopupAsync(GetCurrentWindow<MovimientoWindow>()); await dt.ShowAsPopupAsync(GetCurrentWindow<MovimientoWindow>());
MontoDecimal = 0;
Descripcion = "";
OnReloadEvent();
}catch(Exception ex){
var errorMsg = MessageBoxManager.GetMessageBoxStandard("Error", $"Ocurrió un error: {ex.Message}", ButtonEnum.Ok);
await errorMsg.ShowAsPopupAsync(GetCurrentWindow<MovimientoWindow>());
}
}
private bool ValidarCamposObligatorios()
{
var mensajesError = new List<string>();
// Validar MontoDecimal
if (MontoDecimal <= 0)
{
mensajesError.Add("• Debe agregar un monto válido (mayor a 0)");
}
// Validar TipoMovimientoSelecionado
if (TipoMovimientoSelecionado == null || TipoMovimientoSelecionado.ID <= 0)
{
mensajesError.Add("• Debe seleccionar un tipo de movimiento");
}
// Validar DepartaDepartTrabajoSeleccionado
if (DepartaDepartTrabajoSeleccionado == null || DepartaDepartTrabajoSeleccionado.Id <= 0)
{
mensajesError.Add("• Debe seleccionar un departamento/trabajo");
}
// Validar FechaMov
if (FechaMov == default(DateTime) || FechaMov > DateTime.Now)
{
mensajesError.Add("• Debe seleccionar una fecha válida (no puede ser futura)");
}
// Validar ConceptoSeleccionado
if (ConceptoSeleccionado == null || ConceptoSeleccionado.ID <= 0)
{
mensajesError.Add("• Debe seleccionar un concepto");
}
// Si hay errores, mostrar mensaje
if (mensajesError.Count > 0)
{
var mensajeCompleto = "Por favor, complete los siguientes campos:\n\n" + string.Join("\n", mensajesError);
var errorMsg = MessageBoxManager.GetMessageBoxStandard("Campos requeridos", mensajeCompleto, ButtonEnum.Ok);
errorMsg.ShowAsPopupAsync(GetCurrentWindow<MovimientoWindow>());
return false;
}
return true;
}
protected virtual void OnReloadEvent()
{
ReloadEvent?.Invoke(this, EventArgs.Empty);
} }
[RelayCommand] [RelayCommand]

View File

@@ -30,8 +30,8 @@
<!-- Menú Herramientas --> <!-- Menú Herramientas -->
<MenuItem Header="Herramientas"> <MenuItem Header="Herramientas">
<MenuItem Header="Departamentos" Command="{Binding AgregarDepartamentoCommand}" /> <MenuItem Header="Departamentos" Command="{Binding AgregarDepartamentoCommand}" />
<MenuItem Header="Tipos de Movimiento" /> <MenuItem Header="Tipos de Movimiento" Command="{Binding AgregarTipoMovimientoCommand}" />
<MenuItem Header="Conceptos"/> <MenuItem Header="Conceptos" Command="{Binding AgregarConceptoCommand}"/>
</MenuItem> </MenuItem>
</Menu> </Menu>

View File

@@ -0,0 +1,55 @@
<Window xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:vm="using:AdminFinanceRCA.ViewModels"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="350" CanResize="False"
Width="800" Height="350"
WindowStartupLocation="CenterScreen"
x:DataType="vm:Mantenimiento_ConceptoViewModel"
x:Class="AdminFinanceRCA.Views.Mantenimiento_Concepto"
Title="Mantenimiento de Concepto">
<Design.DataContext>
<vm:Mantenimiento_ConceptoViewModel/>
</Design.DataContext>
<DockPanel Margin="10">
<!-- Barra de herramientas -->
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal" Margin="0,0,0,10" Spacing="5">
<Button Content="Nuevo" Background="DarkBlue" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding NuevoConceptoCommand}" />
<Button Content="Guardar" Background="DarkGreen" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding GuardarRegistrosCommand}"/>
<Button Content="Cancelar" Background="DarkRed" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding CancelarCommand}" />
</StackPanel>
<Grid ColumnDefinitions="*,2*" Margin="0,10,0,0" ShowGridLines="False">
<!-- Lista de grupos -->
<StackPanel Grid.Column="0" Margin="0,0,10,0">
<TextBlock Text="Conceptos" FontWeight="Bold" Margin="0,0,0,5"/>
<ListBox ItemsSource="{Binding Conceptos}" DoubleTapped="OnListBoxDoubleTapped"
Height="250">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Vertical" Margin="5">
<TextBlock Text="{Binding Nombre}" VerticalAlignment="Center" />
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</StackPanel>
<!-- Formulario de edición -->
<Border Grid.Column="1" Margin="0 0 0 0" BorderBrush="LightGray" BorderThickness="3" Padding="10" Height="250" Width="500">
<StackPanel Spacing="10">
<TextBlock Text="Editar Concepto" FontSize="16" FontWeight="Bold"/>
<StackPanel>
<TextBlock Text="Nombre *" Margin="0,0,0,2"/>
<TextBox Watermark="Ingrese el nombre" Text="{Binding Nombre}"/>
</StackPanel>
</StackPanel>
</Border>
</Grid>
</DockPanel>
</Window>

View File

@@ -0,0 +1,29 @@
using AdminFinanceRCA.Models;
using AdminFinanceRCA.ViewModels;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Input;
using Avalonia.Markup.Xaml;
namespace AdminFinanceRCA.Views;
public partial class Mantenimiento_Concepto : Window
{
public Mantenimiento_Concepto()
{
InitializeComponent();
}
private void OnListBoxDoubleTapped(object sender, TappedEventArgs e)
{
if (DataContext is Mantenimiento_ConceptoViewModel viewModel &&
sender is ListBox listBox &&
listBox.SelectedItem is Concepto selected)
{
viewModel.ConceptoSeleccionado = selected;
viewModel.Nombre = selected.Nombre;
// viewModel.Descripcion = selected.Descripcion;
viewModel.EstaEditando = true;
}
}
}

View File

@@ -17,9 +17,9 @@
<DockPanel Margin="10"> <DockPanel Margin="10">
<!-- Barra de herramientas --> <!-- Barra de herramientas -->
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal" Margin="0,0,0,10" Spacing="5"> <StackPanel DockPanel.Dock="Top" Orientation="Horizontal" Margin="0,0,0,10" Spacing="5">
<Button Content="Nuevo" Width="90" Command="{Binding NuevoDepartTrabajoCommand}" /> <Button Content="Nuevo" Background="DarkBlue" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding NuevoDepartTrabajoCommand}" />
<Button Content="Guardar" Width="90" Command="{Binding GuardarRegistrosCommand}"/> <Button Content="Guardar" Background="DarkGreen" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding GuardarRegistrosCommand}"/>
<Button Content="Cancelar" Width="90" /> <Button Content="Cancelar" Background="DarkRed" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding CancelarCommand}" />
</StackPanel> </StackPanel>
<Grid ColumnDefinitions="*,2*" Margin="0,10,0,0" ShowGridLines="False"> <Grid ColumnDefinitions="*,2*" Margin="0,10,0,0" ShowGridLines="False">
@@ -27,15 +27,12 @@
<StackPanel Grid.Column="0" Margin="0,0,10,0"> <StackPanel Grid.Column="0" Margin="0,0,10,0">
<TextBlock Text="Grupos de Trabajo" FontWeight="Bold" Margin="0,0,0,5"/> <TextBlock Text="Grupos de Trabajo" FontWeight="Bold" Margin="0,0,0,5"/>
<ListBox ItemsSource="{Binding GruposTrabajo}" DoubleTapped="OnListBoxDoubleTapped" <ListBox ItemsSource="{Binding GruposTrabajo}" DoubleTapped="OnListBoxDoubleTapped"
Height="200"> Height="250">
<ListBox.ItemTemplate> <ListBox.ItemTemplate>
<DataTemplate> <DataTemplate>
<StackPanel Orientation="Vertical" Margin="5"> <StackPanel Orientation="Vertical" Margin="5">
<TextBlock FontWeight="Bold"/> <TextBlock Text="{Binding Nombre}" VerticalAlignment="Center" />
<TextBlock Foreground="Gray" Text="{Binding Nombre}"
TextTrimming="CharacterEllipsis"/>
<TextBlock />
</StackPanel> </StackPanel>
</DataTemplate> </DataTemplate>
</ListBox.ItemTemplate> </ListBox.ItemTemplate>

View File

@@ -0,0 +1,55 @@
<Window xmlns="https://github.com/avaloniaui"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:vm="using:AdminFinanceRCA.ViewModels"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="350" CanResize="False"
Width="800" Height="350"
WindowStartupLocation="CenterScreen"
x:DataType="vm:Mantenimiento_TipoMovViewModel"
x:Class="AdminFinanceRCA.Views.Mantenimiento_TipoMovimiento"
Title="Mantenimiento de Tipo de Movimiento">
<Design.DataContext>
<vm:Mantenimiento_TipoMovViewModel/>
</Design.DataContext>
<DockPanel Margin="10">
<!-- Barra de herramientas -->
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal" Margin="0,0,0,10" Spacing="5">
<Button Content="Nuevo" Background="DarkBlue" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding NuevoTipoMovCommand}" />
<Button Content="Guardar" Background="DarkGreen" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding GuardarRegistrosCommand}"/>
<Button Content="Cancelar" Background="DarkRed" Foreground="White" HorizontalContentAlignment="Center" Width="90" Command="{Binding CancelarCommand}" />
</StackPanel>
<Grid ColumnDefinitions="*,2*" Margin="0,10,0,0" ShowGridLines="False">
<!-- Lista de grupos -->
<StackPanel Grid.Column="0" Margin="0,0,10,0">
<TextBlock Text="Tipo de Movimientos" FontWeight="Bold" Margin="0,0,0,5"/>
<ListBox ItemsSource="{Binding TipoMovimientos}" DoubleTapped="OnListBoxDoubleTapped"
Height="250">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Vertical" Margin="5">
<TextBlock Text="{Binding Nombre}" VerticalAlignment="Center" />
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</StackPanel>
<!-- Formulario de edición -->
<Border Grid.Column="1" Margin="0 0 0 0" BorderBrush="LightGray" BorderThickness="3" Padding="10" Height="250" Width="500">
<StackPanel Spacing="10">
<TextBlock Text="Editar Tipo de Movimiento" FontSize="16" FontWeight="Bold"/>
<StackPanel>
<TextBlock Text="Nombre *" Margin="0,0,0,2"/>
<TextBox Watermark="Ingrese el nombre" Text="{Binding Nombre}"/>
</StackPanel>
</StackPanel>
</Border>
</Grid>
</DockPanel>
</Window>

View File

@@ -0,0 +1,27 @@
using AdminFinanceRCA.Models;
using AdminFinanceRCA.ViewModels;
using Avalonia.Controls;
using Avalonia.Input;
namespace AdminFinanceRCA.Views;
public partial class Mantenimiento_TipoMovimiento : Window
{
public Mantenimiento_TipoMovimiento()
{
InitializeComponent();
}
private void OnListBoxDoubleTapped(object sender, TappedEventArgs e)
{
if (DataContext is Mantenimiento_TipoMovViewModel viewModel &&
sender is ListBox listBox &&
listBox.SelectedItem is TipoMovimiento selected)
{
viewModel.TipoMovSeleccionado = selected;
viewModel.Nombre = selected.Nombre;
// viewModel.Descripcion = selected.Descripcion;
viewModel.EstaEditando = true;
}
}
}

View File

@@ -41,7 +41,7 @@
<!-- Departamento de Trabajo --> <!-- Departamento de Trabajo -->
<TextBlock Grid.Row="1" Grid.Column="0" Text="Departamento:" VerticalAlignment="Center" Margin="0 5"/> <TextBlock Grid.Row="1" Grid.Column="0" Text="Departamento:" VerticalAlignment="Center" Margin="0 5"/>
<ComboBox Grid.Row="1" Grid.Column="1" ItemsSource="{Binding DepartTrabajos}" SelectedItem="{Binding DepartaDepartTrabajoSeleccionado}"> <ComboBox Grid.Row="1" Grid.Column="1" Width="250" ItemsSource="{Binding DepartTrabajos}" SelectedItem="{Binding DepartaDepartTrabajoSeleccionado}">
<ComboBox.ItemTemplate> <ComboBox.ItemTemplate>
<DataTemplate> <DataTemplate>
<TextBlock Text="{Binding Nombre}" /> <TextBlock Text="{Binding Nombre}" />
@@ -51,7 +51,7 @@
<!-- Tipo de Movimiento --> <!-- Tipo de Movimiento -->
<TextBlock Grid.Row="2" Grid.Column="0" Text="Tipo Movimiento:" VerticalAlignment="Center" Margin="0 5"/> <TextBlock Grid.Row="2" Grid.Column="0" Text="Tipo Movimiento:" VerticalAlignment="Center" Margin="0 5"/>
<ComboBox Grid.Row="2" Grid.Column="1" Margin="0 5" ItemsSource="{Binding TipoMovimientos}" SelectedItem="{Binding TipoMovimientoSelecionado}"> <ComboBox Grid.Row="2" Grid.Column="1" Width="250" Margin="0 5" ItemsSource="{Binding TipoMovimientos}" SelectedItem="{Binding TipoMovimientoSelecionado}">
<ComboBox.ItemTemplate> <ComboBox.ItemTemplate>
<DataTemplate> <DataTemplate>
<TextBlock Text="{Binding Nombre}" /> <TextBlock Text="{Binding Nombre}" />
@@ -61,7 +61,7 @@
<!-- Concepto --> <!-- Concepto -->
<TextBlock Grid.Row="3" Grid.Column="0" Text="Concepto:" VerticalAlignment="Center" Margin="0 5"/> <TextBlock Grid.Row="3" Grid.Column="0" Text="Concepto:" VerticalAlignment="Center" Margin="0 5"/>
<ComboBox Grid.Row="3" Grid.Column="1" Margin="0 0" ItemsSource="{Binding Conceptos}" SelectedItem="{Binding ConceptoSeleccionado}"> <ComboBox Grid.Row="3" Grid.Column="1" Width="250" Margin="0 0" ItemsSource="{Binding Conceptos}" SelectedItem="{Binding ConceptoSeleccionado}">
<ComboBox.ItemTemplate> <ComboBox.ItemTemplate>
<DataTemplate> <DataTemplate>
<TextBlock Text="{Binding Nombre}" /> <TextBlock Text="{Binding Nombre}" />
@@ -71,11 +71,11 @@
<!-- Monto --> <!-- Monto -->
<TextBlock Grid.Row="4" Grid.Column="0" Text="Monto:" VerticalAlignment="Center" Margin="0 5" FontSize="14"/> <TextBlock Grid.Row="4" Grid.Column="0" Text="Monto:" VerticalAlignment="Center" Margin="0 5" FontSize="14"/>
<TextBox Grid.Row="4" Grid.Column="1" Margin="0 5" Height="35" Watermark="Ingrese el monto" Text="{Binding MontoDecimal, StringFormat='{}{0:0.00}'}" FontSize="14"/> <TextBox Grid.Row="4" Grid.Column="1" Margin="0 5" Width="70" HorizontalAlignment="Left" Height="35" Watermark="Ingrese el monto" Text="{Binding MontoDecimal, StringFormat='{}{0:0.00}'}" FontSize="14"/>
<!-- Fecha de Movimiento --> <!-- Fecha de Movimiento -->
<TextBlock Grid.Row="5" Grid.Column="0" Text="Fecha Movimiento:" VerticalAlignment="Center" Margin="0 5"/> <TextBlock Grid.Row="5" Grid.Column="0" Text="Fecha Movimiento:" VerticalAlignment="Center" Margin="0 5"/>
<DatePicker Grid.Row="5" Grid.Column="1" Margin="0 5" Height="35" SelectedDate="{Binding FechaMov}" DayFormat="dd/MM/yyyy"/> <DatePicker Grid.Row="5" Grid.Column="1" Margin="0 5" Height="35" SelectedDate="{Binding FechaMov}"/>
<!-- Descripción --> <!-- Descripción -->
<TextBlock Grid.Row="6" Grid.Column="0" Text="Descripción:" VerticalAlignment="Top" Margin="0 10 0 5"/> <TextBlock Grid.Row="6" Grid.Column="0" Text="Descripción:" VerticalAlignment="Top" Margin="0 10 0 5"/>
@@ -85,9 +85,9 @@
<StackPanel Grid.Row="7" Grid.ColumnSpan="2" Orientation="Horizontal" <StackPanel Grid.Row="7" Grid.ColumnSpan="2" Orientation="Horizontal"
HorizontalAlignment="Right" Margin="0 20 0 0"> HorizontalAlignment="Right" Margin="0 20 0 0">
<Button Content="Cancelar" Width="100" Height="35" Margin="0 0 10 0" <Button Content="Cancelar" Width="100" Height="35" Margin="0 0 10 0"
Background="#E74C3C" Foreground="White" Command="{Binding SalirCommand}"/> Background="#E74C3C" Foreground="White" Command="{Binding SalirCommand}" HorizontalContentAlignment="Center" VerticalContentAlignment="Center"/>
<Button Content="Guardar" Width="100" Height="35" <Button Content="Guardar" Width="100" Height="35"
Background="#27AE60" Foreground="White" FontWeight="Bold" Command="{Binding GuardarDatosAsyncCommand}"/> Background="#27AE60" Foreground="White" FontWeight="Bold" Command="{Binding GuardarDatosAsyncCommand}" HorizontalContentAlignment="Center" VerticalContentAlignment="Center"/>
</StackPanel> </StackPanel>
</Grid> </Grid>
</Window> </Window>