Search and tags look through the Archive, and archived cards say so
A search or a tag filter on the main board, and a tag's own view, now list every note not in Trash (a new `all` board view on the server and in the core), so finished work can still be looked up. Archive and Trash keep a search inside themselves. An archived note met anywhere but the Archive carries an "Archived" chip at the top of its card, on the web and on Android. Task #6315. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -258,6 +258,7 @@ fun BoardScreen(
|
||||
onNoteAction = onCardAction,
|
||||
onConfirmDelete = { confirmingDelete = it },
|
||||
reorderable = state.reorderable,
|
||||
marksArchived = state.marksArchived,
|
||||
onReorder = onReorder,
|
||||
)
|
||||
}
|
||||
@@ -540,6 +541,8 @@ private fun NoteBoard(
|
||||
onConfirmDelete: (Note) -> Unit,
|
||||
/** Whether cards can be dragged into a new order: the plain main board only. */
|
||||
reorderable: Boolean,
|
||||
/** Whether an archived card carries the Archived chip (BoardState.marksArchived). */
|
||||
marksArchived: Boolean,
|
||||
onReorder: (List<String>) -> Unit,
|
||||
) {
|
||||
// The web's breakpoints (NoteGrid.vue: three columns from `lg`, 1024px, four from
|
||||
@@ -635,6 +638,7 @@ private fun NoteBoard(
|
||||
onAction = { onNoteAction(note, it) },
|
||||
onConfirmDelete = { onConfirmDelete(note) },
|
||||
dragging = carried,
|
||||
marksArchived = marksArchived,
|
||||
)
|
||||
}
|
||||
DisposableEffect(note.id) { onDispose { bounds.forget(note.id) } }
|
||||
|
||||
@@ -91,6 +91,14 @@ data class BoardState(
|
||||
* filtered subset, whose order would be renumbered against notes it can't see.
|
||||
*/
|
||||
val reorderable: Boolean get() = filterable && filters.count == 0 && !searching
|
||||
|
||||
/**
|
||||
* Whether an archived card says so: anywhere the Archive is not the whole view. A
|
||||
* search or a tag looks through the Archive as well as the board, so finished
|
||||
* work can still be looked up, and the chip is what keeps it from reading as
|
||||
* current.
|
||||
*/
|
||||
val marksArchived: Boolean get() = destination != Destination.Archive
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -183,15 +191,18 @@ class BoardViewModel(
|
||||
): List<Note> {
|
||||
// Only the main board has filters; every board view takes the search text.
|
||||
val searchOnly = BoardFilters().facets(text)
|
||||
// A search or a tag looks through the Archive too, as on the web; Archive and
|
||||
// Trash keep a search inside themselves.
|
||||
val notesView = if (text.isNotBlank() || filters.labelIds.isNotEmpty()) VIEW_ALL else VIEW_NOTES
|
||||
return when (destination) {
|
||||
Destination.Notes -> core.listNotes(query(VIEW_NOTES, facets = filters.facets(text)))
|
||||
Destination.Notes -> core.listNotes(query(notesView, facets = filters.facets(text)))
|
||||
Destination.Archive -> core.listNotes(query(VIEW_ARCHIVE, facets = searchOnly))
|
||||
Destination.Trash -> core.listNotes(query(VIEW_TRASH, facets = searchOnly))
|
||||
// Not a board view: the core models reminders as its own query, since
|
||||
// "has a reminder" cuts across archived and active alike. `search` moves
|
||||
// a search off this view, so it never has text to apply.
|
||||
Destination.Reminders -> core.reminderNotes()
|
||||
is Destination.WithLabel -> core.listNotes(query(VIEW_NOTES, labelId = destination.id, facets = searchOnly))
|
||||
is Destination.WithLabel -> core.listNotes(query(VIEW_ALL, labelId = destination.id, facets = searchOnly))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -647,6 +658,9 @@ class BoardViewModel(
|
||||
private const val VIEW_ARCHIVE = "archived"
|
||||
private const val VIEW_TRASH = "trash"
|
||||
|
||||
/** The board and the Archive together — everything not in Trash. */
|
||||
private const val VIEW_ALL = "all"
|
||||
|
||||
fun factory(
|
||||
core: Inkwell,
|
||||
readFile: (Uri) -> PickedFile,
|
||||
|
||||
@@ -55,6 +55,8 @@ fun NoteCard(
|
||||
onConfirmDelete: () -> Unit,
|
||||
/** The board is carrying this card (BoardDrag.kt). */
|
||||
dragging: Boolean = false,
|
||||
/** Whether an archived note says so — everywhere but the Archive itself. */
|
||||
marksArchived: Boolean = true,
|
||||
) {
|
||||
val dark = isSystemInDarkTheme()
|
||||
val haptics = LocalHapticFeedback.current
|
||||
@@ -107,7 +109,11 @@ fun NoteCard(
|
||||
.border(1.dp, if (dark) CARD_EDGE_DARK else CARD_EDGE_LIGHT, RoundedCornerShape(CARD_RADIUS))
|
||||
.padding(12.dp),
|
||||
) {
|
||||
CardContents(note = note, onToggleItem = onToggleItem)
|
||||
CardContents(
|
||||
note = note,
|
||||
onToggleItem = onToggleItem,
|
||||
archivedChip = marksArchived && note.archived && !note.trashed,
|
||||
)
|
||||
}
|
||||
|
||||
NoteMenu(
|
||||
@@ -120,12 +126,23 @@ fun NoteCard(
|
||||
}
|
||||
}
|
||||
|
||||
/** What a card shows, top to bottom: tags, body, links, attachments, reminder, sharing. */
|
||||
/**
|
||||
* What a card shows, top to bottom: archived or not, tags, body, links, attachments,
|
||||
* reminder, sharing.
|
||||
*/
|
||||
@Composable
|
||||
private fun CardContents(
|
||||
note: Note,
|
||||
onToggleItem: (Int, Boolean) -> Unit,
|
||||
archivedChip: Boolean,
|
||||
) {
|
||||
// Above everything, tags included: whether a note is put away is the first thing
|
||||
// to know about a search result or a tag's note, before what it says.
|
||||
if (archivedChip) {
|
||||
TintChip(stringResource(R.string.card_archived), "default")
|
||||
Spacer(Modifier.height(8.dp))
|
||||
}
|
||||
|
||||
// TAGS FIRST, on a row of their own above the body: a board is scanned, and
|
||||
// what a note is about should be the first thing the eye lands on. Not beside
|
||||
// the body, whose first line is the note's name.
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
|
||||
<!-- Board -->
|
||||
<string name="board_empty_note">Empty note</string>
|
||||
<string name="card_archived">Archived</string>
|
||||
|
||||
<!-- The long-press menu. Its ITEMS are the editor_* strings, deliberately: a
|
||||
note has one vocabulary of things you can do to it, and a board that said
|
||||
|
||||
Reference in New Issue
Block a user