From a665eac9b7aa1a23122dbe1d93a2a672647ccdfd Mon Sep 17 00:00:00 2001 From: psavarmattas Date: Fri, 14 Aug 2026 02:18:58 +0100 Subject: [PATCH] feat(collections): show loading spinner during stale-content reloads MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Document reader and collection document list only showed a spinner on first load — refetching over already-visible content (reopening a document, remote-changes refresh) had no loading indicator at all. --- .../Features/Collections/CollectionOverviewView.swift | 10 ++++++++++ Outpost/Features/Collections/DocumentReaderView.swift | 11 +++++++++++ 2 files changed, 21 insertions(+) diff --git a/Outpost/Features/Collections/CollectionOverviewView.swift b/Outpost/Features/Collections/CollectionOverviewView.swift index d23e014..2436a06 100644 --- a/Outpost/Features/Collections/CollectionOverviewView.swift +++ b/Outpost/Features/Collections/CollectionOverviewView.swift @@ -65,6 +65,16 @@ struct CollectionOverviewView: View { } } .frame(maxWidth: .infinity, maxHeight: .infinity, alignment: .topLeading) + // Corner spinner for reloads with stale data already on screen + // (remote-changes refresh, tab switch after the first load) — + // `documentList`'s own spinner only covers the empty-state case. + .overlay(alignment: .topTrailing) { + if viewModel.isLoading && !viewModel.documents.isEmpty { + ProgressView() + .controlSize(.small) + .padding(12) + } + } } // No `.navigationTitle` here — it renders its own native title bubble, // duplicating the leading toolbar item `ContentView_macOS` already diff --git a/Outpost/Features/Collections/DocumentReaderView.swift b/Outpost/Features/Collections/DocumentReaderView.swift index 89fc1af..803c141 100644 --- a/Outpost/Features/Collections/DocumentReaderView.swift +++ b/Outpost/Features/Collections/DocumentReaderView.swift @@ -49,6 +49,17 @@ struct DocumentReaderView: View { .padding() } // No `.navigationTitle` here either — same reason as CollectionOverviewView. + // Corner spinner, not gated on `text.isEmpty`: `viewModel.text` starts + // pre-filled from the list/summary copy of the doc, so the full-page + // spinner above rarely fires on open — without this, the re-fetch in + // `loadFullContent()` looked like nothing was happening. + .overlay(alignment: .topTrailing) { + if viewModel.isLoading && !viewModel.text.isEmpty { + ProgressView() + .controlSize(.small) + .padding(12) + } + } .task { await viewModel.loadFullContent() } }