feat: Re-enabled multiple selection on mobile, with improved UI (#2609)

This commit is contained in:
Aman Harwara
2023-10-27 17:54:51 +05:30
committed by GitHub
parent 66a6c61ffa
commit c8dec9bfec
7 changed files with 172 additions and 31 deletions

View File

@@ -101,6 +101,8 @@ export class ItemListController
selectedUuids: Set<UuidString> = observable(new Set<UuidString>())
selectedItems: Record<UuidString, ListableContentItem> = {}
isMultipleSelectionMode = false
override deinit() {
super.deinit()
;(this.noteFilterText as unknown) = undefined
@@ -169,6 +171,10 @@ export class ItemListController
setSelectedItems: action,
hydrateFromPersistedValue: action,
isMultipleSelectionMode: observable,
enableMultipleSelectionMode: action,
cancelMultipleSelection: action,
})
eventBus.addEventHandler(this, CrossControllerEvent.TagChanged)
@@ -257,6 +263,17 @@ export class ItemListController
),
)
this.disposers.push(
reaction(
() => this.selectedItemsCount,
() => {
if (this.selectedItemsCount === 0) {
this.cancelMultipleSelection()
}
},
),
)
window.onresize = () => {
this.resetPagination(true)
}
@@ -1079,6 +1096,9 @@ export class ItemListController
runInAction(() => {
this.setSelectedUuids(this.selectedUuids.add(item.uuid))
this.lastSelectedItem = item
if (this.selectedItemsCount > 1 && !this.isMultipleSelectionMode) {
this.enableMultipleSelectionMode()
}
})
}
}
@@ -1086,6 +1106,8 @@ export class ItemListController
cancelMultipleSelection = () => {
this.keyboardService.cancelAllKeyboardModifiers()
this.isMultipleSelectionMode = false
const firstSelectedItem = this.firstSelectedItem
if (firstSelectedItem) {
@@ -1095,7 +1117,7 @@ export class ItemListController
}
}
private replaceSelection = (item: ListableContentItem): void => {
replaceSelection = (item: ListableContentItem): void => {
this.deselectAll()
runInAction(() => this.setSelectedUuids(this.selectedUuids.add(item.uuid)))
@@ -1103,10 +1125,11 @@ export class ItemListController
}
selectAll = () => {
void this.selectItemsRange({
startingIndex: 0,
endingIndex: this.listLength - 1,
})
const allItems = this.items.filter((item) => !item.protected)
const lastItem = allItems[allItems.length - 1]
this.setSelectedUuids(new Set(Uuids(allItems)))
this.lastSelectedItem = lastItem
this.enableMultipleSelectionMode()
}
deselectAll = (): void => {
@@ -1136,6 +1159,10 @@ export class ItemListController
}
}
enableMultipleSelectionMode = () => {
this.isMultipleSelectionMode = true
}
selectItem = async (
uuid: UuidString,
userTriggered?: boolean,
@@ -1152,14 +1179,13 @@ export class ItemListController
log(LoggingDomain.Selection, 'Select item', item.uuid)
const supportsMultipleSelection = this.options.allowMultipleSelection
const hasMeta = this.keyboardService.activeModifiers.has(KeyboardModifier.Meta)
const hasCtrl = this.keyboardService.activeModifiers.has(KeyboardModifier.Ctrl)
const hasShift = this.keyboardService.activeModifiers.has(KeyboardModifier.Shift)
const hasMoreThanOneSelected = this.selectedItemsCount > 1
const isAuthorizedForAccess = await this.protections.authorizeItemAccess(item)
if (supportsMultipleSelection && userTriggered && (hasMeta || hasCtrl)) {
if (userTriggered && hasShift) {
await this.selectItemsRange({ selectedItem: item })
} else if (userTriggered && this.isMultipleSelectionMode) {
if (this.selectedUuids.has(uuid) && hasMoreThanOneSelected) {
this.removeSelectedItem(uuid)
} else if (isAuthorizedForAccess) {
@@ -1167,17 +1193,17 @@ export class ItemListController
this.setSelectedUuids(this.selectedUuids)
this.lastSelectedItem = item
}
} else if (supportsMultipleSelection && userTriggered && hasShift) {
await this.selectItemsRange({ selectedItem: item })
if (this.selectedItemsCount === 1) {
this.cancelMultipleSelection()
}
} else {
const shouldSelectNote = hasMoreThanOneSelected || !this.selectedUuids.has(uuid)
if (shouldSelectNote && isAuthorizedForAccess) {
this.replaceSelection(item)
await this.openSingleSelectedItem({ userTriggered: userTriggered ?? false })
}
}
await this.openSingleSelectedItem({ userTriggered: userTriggered ?? false })
return {
didSelect: this.selectedUuids.has(uuid),
}

View File

@@ -293,6 +293,17 @@ export class NotesController
})
}
async toggleArchiveSelectedNotes(): Promise<void> {
const notes = this.selectedNotes
const archived = notes.some((note) => note.archived)
if (!archived) {
await this.setArchiveSelectedNotes(true)
} else {
await this.setArchiveSelectedNotes(false)
}
}
async setProtectSelectedNotes(protect: boolean): Promise<void> {
const selectedNotes = this.getSelectedNotesList()
if (protect) {