add/modify grid without reload

This commit is contained in:
Robert McRackan 2022-05-04 13:37:25 -04:00
parent 0bde86ebfd
commit 128facec21
3 changed files with 61 additions and 26 deletions

View File

@ -176,6 +176,7 @@ namespace ApplicationServices
int qtyChanges = saveChanges(context); int qtyChanges = saveChanges(context);
logTime("importIntoDbAsync -- post SaveChanges"); logTime("importIntoDbAsync -- post SaveChanges");
// this is any changes at all to the database, not just new books
if (qtyChanges > 0) if (qtyChanges > 0)
await Task.Run(() => finalizeLibrarySizeChange()); await Task.Run(() => finalizeLibrarySizeChange());
logTime("importIntoDbAsync -- post finalizeLibrarySizeChange"); logTime("importIntoDbAsync -- post finalizeLibrarySizeChange");

View File

@ -75,16 +75,22 @@ namespace LibationWinForms
{ {
SuspendLayout(); SuspendLayout();
{ {
if (productsGrid != null) // previous non-null grid with zero-count removes columns. remove/re-add grid to get columns back
if (productsGrid?.Count == 0)
{ {
gridPanel.Controls.Remove(productsGrid); gridPanel.Controls.Remove(productsGrid);
productsGrid.VisibleCountChanged -= setVisibleCount; productsGrid.VisibleCountChanged -= setVisibleCount;
productsGrid.Dispose(); productsGrid.Dispose();
productsGrid = null;
} }
if (productsGrid is null)
{
productsGrid = new ProductsGrid { Dock = DockStyle.Fill }; productsGrid = new ProductsGrid { Dock = DockStyle.Fill };
productsGrid.VisibleCountChanged += setVisibleCount; productsGrid.VisibleCountChanged += setVisibleCount;
gridPanel.UIThreadSync(() => gridPanel.Controls.Add(productsGrid)); gridPanel.UIThreadSync(() => gridPanel.Controls.Add(productsGrid));
}
productsGrid.Display(); productsGrid.Display();
} }
ResumeLayout(); ResumeLayout();

View File

@ -1,4 +1,5 @@
using System; using System;
using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Threading.Tasks; using System.Threading.Tasks;
using System.Windows.Forms; using System.Windows.Forms;
@ -107,25 +108,18 @@ namespace LibationWinForms
#endregion #endregion
private SortableBindingList<GridEntry> bindingList;
/// <summary>Insert ad hoc library books to top of grid</summary>
public void AddToTop(DataLayer.LibraryBook libraryBook) => bindingList.Insert(0, toGridEntry(libraryBook));
#region UI display functions #region UI display functions
private bool hasBeenDisplayed = false; public int Count { get; private set; }
private SortableBindingList<GridEntry> bindingList;
public void Display() public void Display()
{ {
if (hasBeenDisplayed)
return;
hasBeenDisplayed = true;
//
// transform into sorted GridEntry.s BEFORE binding
//
var lib = DbContexts.GetLibrary_Flat_NoTracking(); var lib = DbContexts.GetLibrary_Flat_NoTracking();
Count = lib.Count;
// if no data. hide all columns. return // if no data. hide all columns. return
if (!lib.Any()) if (!lib.Any())
{ {
@ -134,24 +128,58 @@ namespace LibationWinForms
return; return;
} }
var orderedGridEntries = lib var orderedBooks = lib
.Select(lb => toGridEntry(lb))
// default load order // default load order
.OrderByDescending(ge => (DateTime)ge.GetMemberValue(nameof(ge.PurchaseDate))) .OrderByDescending(lb => lb.DateAdded)
//// more advanced example: sort by author, then series, then title //// more advanced example: sort by author, then series, then title
//.OrderBy(ge => ge.Authors) //.OrderBy(lb => lb.Book.AuthorNames)
// .ThenBy(ge => ge.Series) // .ThenBy(lb => lb.Book.SeriesSortable)
// .ThenBy(ge => ge.Title) // .ThenBy(lb => lb.Book.TitleSortable)
.ToList(); .ToList();
// BIND // BIND
bindingList = new SortableBindingList<GridEntry>(orderedGridEntries); if (bindingList is null)
gridEntryBindingSource.DataSource = bindingList; bindToGrid(orderedBooks);
else
updateGrid(orderedBooks);
// FILTER // FILTER
Filter(); Filter();
} }
private void bindToGrid(List<DataLayer.LibraryBook> orderedBooks)
{
bindingList = new SortableBindingList<GridEntry>(orderedBooks.Select(lb => toGridEntry(lb)));
gridEntryBindingSource.DataSource = bindingList;
}
private void updateGrid(List<DataLayer.LibraryBook> orderedBooks)
{
for (var i = orderedBooks.Count - 1; i >= 0; i--)
{
var libraryBook = orderedBooks[i];
var existingItem = bindingList.FirstOrDefault(i => i.AudibleProductId == libraryBook.Book.AudibleProductId);
// add new to top
if (existingItem is null)
bindingList.Insert(0, toGridEntry(libraryBook));
// update existing
else
existingItem.UpdateLibraryBook(libraryBook);
}
// remove deleted from grid. note: actual deletion from db must still occur via the RemoveBook feature. deleting from audible will not trigger this
var oldIds = bindingList.Select(ge => ge.AudibleProductId).ToList();
var newIds = orderedBooks.Select(lb => lb.Book.AudibleProductId).ToList();
var remove = oldIds.Except(newIds).ToList();
foreach (var id in remove)
{
var oldItem = bindingList.FirstOrDefault(ge => ge.AudibleProductId == id);
if (oldItem is not null)
bindingList.Remove(oldItem);
}
}
private GridEntry toGridEntry(DataLayer.LibraryBook libraryBook) private GridEntry toGridEntry(DataLayer.LibraryBook libraryBook)
{ {
var entry = new GridEntry(libraryBook); var entry = new GridEntry(libraryBook);