refactor(communities): allow removing items from import file list

There was a requested design change where no longer wanted to have
checkboxes to decide which files will be included for a discord import,
but rather have an "X" button that enables users to remove items.

This commit implements this refactor.

In addition, it ensures that the already loaded discord categories and
channels that have been extracted from validation, are kept in sync as
well.

Meaning, if a user removes a file from the file list, the corresponding
channel will be removed as well.

If there's not channel in a given category, the category will be removed
as well.

Closes #8125 #8126
This commit is contained in:
Pascal Precht 2022-11-08 15:07:14 +01:00 committed by r4bbit.eth
parent 15891295e9
commit 8d90204e0a
6 changed files with 100 additions and 9 deletions

View File

@ -73,6 +73,19 @@ QtObject:
return i
return -1
proc removeItem*(self: DiscordCategoriesModel, id: string) =
let idx = self.findIndexById(id)
if(idx == -1):
return
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete
self.beginRemoveRows(parentModelIndex, idx, idx)
self.items.delete(idx)
self.endRemoveRows()
self.countChanged()
proc addItem*(self: DiscordCategoriesModel, item: DiscordCategoryItem) =
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete

View File

@ -1,4 +1,4 @@
import NimQml, Tables
import NimQml, Tables, strutils
import discord_channel_item
type
@ -116,6 +116,13 @@ QtObject:
return i
return -1
proc findIndicesByFilePath(self: DiscordChannelsModel, filePath: string): seq[int] =
var indices: seq[int] = @[]
for i in 0 ..< self.items.len:
if(self.items[i].getFilePath() == filePath):
indices.add(i)
return indices
proc getItem*(self: DiscordChannelsModel, id: string): DiscordChannelItem =
for i in 0 ..< self.items.len:
if(self.items[i].getId() == id):
@ -129,6 +136,12 @@ QtObject:
break
return allUnselected
proc hasItemsWithCategoryId*(self: DiscordChannelsModel, categoryId: string): bool =
for i in 0 ..< self.items.len:
if(self.items[i].getCategoryId() == categoryId):
return true
return false
proc getHasSelectedItems*(self: DiscordChannelsModel): bool {.slot.} =
for i in 0 ..< self.items.len:
if self.items[i].getSelected():
@ -139,6 +152,18 @@ QtObject:
read = getHasSelectedItems
notify = hasSelectedItemsChanged
proc removeItemsByFilePath*(self: DiscordChannelsModel, filePath: string) =
let indices = self.findIndicesByFilePath(filePath)
for i in 0 ..< indices.len:
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete
self.beginRemoveRows(parentModelIndex, indices[i], indices[i])
self.items.delete(indices[i])
self.endRemoveRows()
self.countChanged()
proc addItem*(self: DiscordChannelsModel, item: DiscordChannelItem) =
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete
@ -163,6 +188,12 @@ QtObject:
self.dataChanged(index, index, @[ModelRole.Selected.int])
self.hasSelectedItemsChanged()
proc getChannelCategoryIdByFilePath*(self: DiscordChannelsModel, filePath: string): string =
for i in 0 ..< self.items.len:
if(self.items[i].getFilePath() == filePath):
return self.items[i].getCategoryId()
return ""
proc getSelectedItems*(self: DiscordChannelsModel): seq[DiscordChannelItem] =
for i in 0 ..< self.items.len:
if self.items[i].getSelected():

View File

@ -132,6 +132,19 @@ QtObject:
return i
return -1
proc removeItem*(self: DiscordFileListModel, filePath: string) =
let idx = self.findIndexByFilePath(filePath)
if(idx == -1):
return
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete
self.beginRemoveRows(parentModelIndex, idx, idx)
self.items.delete(idx)
self.endRemoveRows()
self.countChanged()
proc addItem*(self: DiscordFileListModel, item: DiscordFileItem) =
let parentModelIndex = newQModelIndex()
defer: parentModelIndex.delete

View File

@ -462,6 +462,20 @@ QtObject:
return false
return sectionItem.hasMember(pubKey)
proc removeFileListItem*(self: View, filePath: string) {.slot.} =
var path = filePath
if path.startsWith("file://"):
path = replace(path, "file://", "")
let categoryId = self.discordChannelsModel.getChannelCategoryIdByFilePath(path)
# file list still uses full path, so relying on `filePath` here
self.discordFileListModel.removeItem(filePath)
self.discordChannelsModel.removeItemsByFilePath(path)
if categoryId != "" and not self.discordChannelsModel.hasItemsWithCategoryId(categoryId):
self.discordCategoriesModel.removeItem(categoryId)
proc setFileListItems*(self: View, filePaths: string) {.slot.} =
let filePaths = filePaths.split(',')
var fileItems: seq[DiscordFileItem] = @[]

View File

@ -200,18 +200,35 @@ StatusStackModal {
model: fileListView.fileListModel
delegate: ColumnLayout {
width: ListView.view.width
StatusCheckBox {
id: fileCheckBox
RowLayout {
spacing: 20
Layout.fillWidth: true
text: model.filePath
font.pixelSize: 13
checked: model.selected
enabled: model.errorMessage === "" // TODO distinguish between error/warning
onToggled: model.selected = checked
Layout.topMargin: 8
StatusBaseText {
Layout.fillWidth: true
text: model.filePath
font.pixelSize: 13
elide: Text.ElideRight
wrapMode: Text.WordWrap
maximumLineCount: 2
}
StatusFlatRoundButton {
id: removeButton
Layout.preferredWidth: 32
Layout.preferredHeight: 32
type: StatusFlatRoundButton.Type.Secondary
icon.name: "close"
icon.color: Theme.palette.directColor1
icon.width: 24
icon.height: 24
onClicked: root.store.removeFileListItem(model.filePath)
}
}
StatusBaseText {
Layout.fillWidth: true
Layout.leftMargin: fileCheckBox.leftPadding + fileCheckBox.spacing + fileCheckBox.indicator.width
text: "%1 %2".arg("⚠").arg(model.errorMessage)
visible: model.errorMessage
font.pixelSize: 13

View File

@ -93,6 +93,9 @@ QtObject {
root.communitiesModuleInst.navigateToCommunity(communityId)
}
function removeFileListItem(filePath) {
root.communitiesModuleInst.removeFileListItem(filePath)
}
function setFileListItems(filePaths) {
root.communitiesModuleInst.setFileListItems(filePaths)
}