feat: enable to delete messages

Fixes #2775
This commit is contained in:
Jonathan Rainville 2021-07-26 14:44:25 -04:00 committed by Iuri Matias
parent 552b6e8af9
commit 523e94ae0c
14 changed files with 127 additions and 16 deletions

View File

@ -53,6 +53,9 @@ proc handleChatEvents(self: ChatController) =
# replaced the initial one. That's why we call this proce here in case message with "message.replace" # replaced the initial one. That's why we call this proce here in case message with "message.replace"
# was not deleted. # was not deleted.
discard self.view.deleteMessageWhichReplacedMessageWithId(message.chatId, message.replace) discard self.view.deleteMessageWhichReplacedMessageWithId(message.chatId, message.replace)
if (message.deleted):
self.view.deleteMessage(message.chatId, message.id)
self.view.reactions.push(evArgs.emojiReactions) self.view.reactions.push(evArgs.emojiReactions)
if (evArgs.communities.len > 0): if (evArgs.communities.len > 0):
@ -77,6 +80,10 @@ proc handleChatEvents(self: ChatController) =
self.view.addActivityCenterNotification(evArgs.activityCenterNotifications) self.view.addActivityCenterNotification(evArgs.activityCenterNotifications)
self.view.communities.updateNotifications(evArgs.activityCenterNotifications) self.view.communities.updateNotifications(evArgs.activityCenterNotifications)
if (evArgs.deletedMessages.len > 0):
for messageId in evArgs.deletedMessages:
self.view.deleteMessage(messageId)
self.status.events.on("channelUpdate") do(e: Args): self.status.events.on("channelUpdate") do(e: Args):
var evArgs = ChatUpdateArgs(e) var evArgs = ChatUpdateArgs(e)
self.view.updateChats(evArgs.chats) self.view.updateChats(evArgs.chats)

View File

@ -4,7 +4,7 @@ import
proc handleSignals(self: ChatController) = proc handleSignals(self: ChatController) =
self.status.events.on(SignalType.Message.event) do(e:Args): self.status.events.on(SignalType.Message.event) do(e:Args):
var data = MessageSignal(e) var data = MessageSignal(e)
self.status.chat.update(data.chats, data.messages, data.emojiReactions, data.communities, data.membershipRequests, data.pinnedMessages, data.activityCenterNotification, data.statusUpdates) self.status.chat.update(data.chats, data.messages, data.emojiReactions, data.communities, data.membershipRequests, data.pinnedMessages, data.activityCenterNotification, data.statusUpdates, data.deletedMessages)
self.status.events.on(SignalType.DiscoverySummary.event) do(e:Args): self.status.events.on(SignalType.DiscoverySummary.event) do(e:Args):
## Handle mailserver peers being added and removed ## Handle mailserver peers being added and removed

View File

@ -456,6 +456,13 @@ QtObject:
proc refreshPinnedMessages*(self: ChatsView, pinnedMessages: seq[Message]) = proc refreshPinnedMessages*(self: ChatsView, pinnedMessages: seq[Message]) =
self.messageView.refreshPinnedMessages(pinnedMessages) self.messageView.refreshPinnedMessages(pinnedMessages)
proc deleteMessage*(self: ChatsView, messageId: string) =
let chatId = self.messageView.getChatIdForMessage(messageId)
if (chatId.len == 0):
return
self.deleteMessage(chatId, messageId)
proc clearMessages*(self: ChatsView, id: string) = proc clearMessages*(self: ChatsView, id: string) =
self.messageView.clearMessages(id) self.messageView.clearMessages(id)

View File

@ -161,6 +161,9 @@ QtObject:
else: else:
self.status.chat.editMessage(messageId, m) self.status.chat.editMessage(messageId, m)
proc deleteMessage*(self: MessageView, messageId: string) {.slot.} =
self.status.chat.deleteMessageAndSend(messageId)
proc sendMessage*(self: MessageView, message: string, replyTo: string, contentType: int = ContentType.Message.int, isStatusUpdate: bool = false, contactsString: string = "") {.slot.} = proc sendMessage*(self: MessageView, message: string, replyTo: string, contentType: int = ContentType.Message.int, isStatusUpdate: bool = false, contactsString: string = "") {.slot.} =
self.sendOrEditMessage(message, replyTo, contentType, isStatusUpdate, contactsString, false, "") self.sendOrEditMessage(message, replyTo, contentType, isStatusUpdate, contactsString, false, "")
@ -497,3 +500,10 @@ QtObject:
{ {
ChatViewRoles.MessageList.int:"messages" ChatViewRoles.MessageList.int:"messages"
}.toTable }.toTable
proc getChatIdForMessage*(self: MessageView, messageId: string): string =
for chatId, messageList in self.messageList:
for message in messageList.messages:
if (message.id == messageId):
return chatId

View File

@ -29,6 +29,7 @@ type
communityMembershipRequests*: seq[CommunityMembershipRequest] communityMembershipRequests*: seq[CommunityMembershipRequest]
activityCenterNotifications*: seq[ActivityCenterNotification] activityCenterNotifications*: seq[ActivityCenterNotification]
statusUpdates*: seq[StatusUpdate] statusUpdates*: seq[StatusUpdate]
deletedMessages*: seq[string]
ChatIdArg* = ref object of Args ChatIdArg* = ref object of Args
chatId*: string chatId*: string
@ -91,7 +92,7 @@ proc newChatModel*(events: EventEmitter): ChatModel =
proc delete*(self: ChatModel) = proc delete*(self: ChatModel) =
discard discard
proc update*(self: ChatModel, chats: seq[Chat], messages: seq[Message], emojiReactions: seq[Reaction], communities: seq[Community], communityMembershipRequests: seq[CommunityMembershipRequest], pinnedMessages: seq[Message], activityCenterNotifications: seq[ActivityCenterNotification], statusUpdates: seq[StatusUpdate]) = proc update*(self: ChatModel, chats: seq[Chat], messages: seq[Message], emojiReactions: seq[Reaction], communities: seq[Community], communityMembershipRequests: seq[CommunityMembershipRequest], pinnedMessages: seq[Message], activityCenterNotifications: seq[ActivityCenterNotification], statusUpdates: seq[StatusUpdate], deletedMessages: seq[string]) =
for chat in chats: for chat in chats:
self.channels[chat.id] = chat self.channels[chat.id] = chat
@ -104,7 +105,7 @@ proc update*(self: ChatModel, chats: seq[Chat], messages: seq[Message], emojiRea
if self.lastMessageTimestamps[chatId] > ts: if self.lastMessageTimestamps[chatId] > ts:
self.lastMessageTimestamps[chatId] = ts self.lastMessageTimestamps[chatId] = ts
self.events.emit("chatUpdate", ChatUpdateArgs(messages: messages,chats: chats, contacts: @[], emojiReactions: emojiReactions, communities: communities, communityMembershipRequests: communityMembershipRequests, pinnedMessages: pinnedMessages, activityCenterNotifications: activityCenterNotifications, statusUpdates: statusUpdates)) self.events.emit("chatUpdate", ChatUpdateArgs(messages: messages,chats: chats, contacts: @[], emojiReactions: emojiReactions, communities: communities, communityMembershipRequests: communityMembershipRequests, pinnedMessages: pinnedMessages, activityCenterNotifications: activityCenterNotifications, statusUpdates: statusUpdates, deletedMessages: deletedMessages))=
proc hasChannel*(self: ChatModel, chatId: string): bool = proc hasChannel*(self: ChatModel, chatId: string): bool =
self.channels.hasKey(chatId) self.channels.hasKey(chatId)
@ -253,6 +254,10 @@ proc editMessage*(self: ChatModel, messageId: string, msg: string) =
var response = status_chat.editMessage(messageId, msg) var response = status_chat.editMessage(messageId, msg)
discard self.processMessageUpdateAfterSend(response, false) discard self.processMessageUpdateAfterSend(response, false)
proc deleteMessageAndSend*(self: ChatModel, messageId: string) =
var response = status_chat.deleteMessageAndSend(messageId)
discard self.processMessageUpdateAfterSend(response, false)
proc sendImage*(self: ChatModel, chatId: string, image: string) = proc sendImage*(self: ChatModel, chatId: string, image: string) =
var response = status_chat.sendImageMessage(chatId, image) var response = status_chat.sendImageMessage(chatId, image)
discard self.processMessageUpdateAfterSend(response) discard self.processMessageUpdateAfterSend(response)

View File

@ -75,6 +75,7 @@ type Message* = object
hasMention*: bool hasMention*: bool
isPinned*: bool isPinned*: bool
pinnedBy*: string pinnedBy*: string
deleted*: bool
type Reaction* = object type Reaction* = object
id*: string id*: string

View File

@ -131,6 +131,9 @@ proc editMessage*(messageId: string, msg: string): string =
} }
]) ])
proc deleteMessageAndSend*(messageId: string): string =
callPrivateRPC("deleteMessageAndSend".prefix, %* [messageId])
proc rpcReactions*(chatId: string, cursorVal: JsonNode, limit: int, success: var bool): string = proc rpcReactions*(chatId: string, cursorVal: JsonNode, limit: int, success: var bool): string =
success = true success = true
try: try:

View File

@ -75,6 +75,10 @@ proc fromEvent*(event: JsonNode): Signal =
for jsonCommunity in event["event"]["requestsToJoinCommunity"]: for jsonCommunity in event["event"]["requestsToJoinCommunity"]:
signal.membershipRequests.add(jsonCommunity.toCommunityMembershipRequest) signal.membershipRequests.add(jsonCommunity.toCommunityMembershipRequest)
if event["event"]{"removedMessages"} != nil:
for messageId in event["event"]["removedMessages"]:
signal.deletedMessages.add(messageId.getStr)
if event["event"]{"activityCenterNotifications"} != nil: if event["event"]{"activityCenterNotifications"} != nil:
for jsonNotification in event["event"]["activityCenterNotifications"]: for jsonNotification in event["event"]["activityCenterNotifications"]:
signal.activityCenterNotification.add(jsonNotification.toActivityCenterNotification()) signal.activityCenterNotification.add(jsonNotification.toActivityCenterNotification())
@ -347,6 +351,7 @@ proc toMessage*(jsonMsg: JsonNode): Message =
audio: $jsonMsg{"audio"}.getStr, audio: $jsonMsg{"audio"}.getStr,
communityId: $jsonMsg{"communityId"}.getStr, communityId: $jsonMsg{"communityId"}.getStr,
audioDurationMs: jsonMsg{"audioDurationMs"}.getInt, audioDurationMs: jsonMsg{"audioDurationMs"}.getInt,
deleted: jsonMsg{"deleted"}.getBool,
hasMention: false hasMention: false
) )

View File

@ -38,6 +38,7 @@ type MessageSignal* = ref object of Signal
membershipRequests*: seq[CommunityMembershipRequest] membershipRequests*: seq[CommunityMembershipRequest]
activityCenterNotification*: seq[ActivityCenterNotification] activityCenterNotification*: seq[ActivityCenterNotification]
statusUpdates*: seq[StatusUpdate] statusUpdates*: seq[StatusUpdate]
deletedMessages*: seq[string]
type CommunitySignal* = ref object of Signal type CommunitySignal* = ref object of Signal
community*: Community community*: Community

View File

@ -205,6 +205,8 @@ Item {
messageContextMenu.messageId = root.messageId; messageContextMenu.messageId = root.messageId;
messageContextMenu.linkUrls = root.linkUrls; messageContextMenu.linkUrls = root.linkUrls;
messageContextMenu.isProfile = !!isProfileClick; messageContextMenu.isProfile = !!isProfileClick;
messageContextMenu.isCurrentUser = root.isCurrentUser
messageContextMenu.isText = root.isText
messageContextMenu.isSticker = isSticker; messageContextMenu.isSticker = isSticker;
messageContextMenu.emojiOnly = emojiOnly; messageContextMenu.emojiOnly = emojiOnly;
messageContextMenu.hideEmojiPicker = hideEmojiPicker; messageContextMenu.hideEmojiPicker = hideEmojiPicker;

View File

@ -250,7 +250,7 @@ PopupMenu {
onTriggered: { onTriggered: {
onClickEdit(); onClickEdit();
} }
icon.source: "../../../img/profileActive.svg" icon.source: "../../../img/edit-message.svg"
icon.width: 16 icon.width: 16
icon.height: 16 icon.height: 16
enabled: isCurrentUser && isText enabled: isCurrentUser && isText
@ -290,4 +290,33 @@ PopupMenu {
icon.height: 16 icon.height: 16
enabled: messageContextMenu.pinnedMessage && messageContextMenu.showJumpTo enabled: messageContextMenu.pinnedMessage && messageContextMenu.showJumpTo
} }
Action {
id: deleteMessageAction
text: qsTr("Delete message")
onTriggered: {
if (!appSettings.showDeleteMessageWarning) {
return chatsModel.messageView.deleteMessage(messageId)
}
let confirmationDialog = openPopup(genericConfirmationDialog, {
title: qsTr("Confirm deleting this message"),
confirmationText: qsTr("Are you sure you want to delete this message? Be aware that other clients are not garanteed to delete the message as well."),
height: 260,
"checkbox.visible": true,
executeConfirm: function () {
if (confirmationDialog.checkbox.checked) {
appSettings.showDeleteMessageWarning = false
}
confirmationDialog.close()
chatsModel.messageView.deleteMessage(messageId)
}
})
}
icon.source: "../../../img/delete.svg"
icon.width: 16
icon.height: 16
enabled: isCurrentUser
}
} }

View File

@ -370,6 +370,7 @@ StatusAppLayout {
property bool onlyShowContactsProfilePics: true property bool onlyShowContactsProfilePics: true
property bool quitOnClose: false property bool quitOnClose: false
property string skinColor: "" property string skinColor: ""
property bool showDeleteMessageWarning: true
// Browser settings // Browser settings
property bool showBrowserSelector: true property bool showBrowserSelector: true
@ -556,6 +557,17 @@ StatusAppLayout {
} }
} }
Component {
id: genericConfirmationDialog
ConfirmationDialog {
onClosed: {
destroy()
}
}
}
ToastMessage { ToastMessage {
id: toastMessage id: toastMessage
} }

View File

@ -11,6 +11,7 @@ ModalPopup {
property Popup parentPopup property Popup parentPopup
property string btnType: "warn" property string btnType: "warn"
property bool showCancelButton: false property bool showCancelButton: false
property alias checkbox: checkbox
height: 186 height: 186
@ -31,15 +32,32 @@ ModalPopup {
signal confirmButtonClicked() signal confirmButtonClicked()
signal cancelButtonClicked() signal cancelButtonClicked()
StyledText { property var executeConfirm
id: innerText property var executeCancel
text: confirmationDialog.confirmationText
font.pixelSize: 15 Item {
anchors.left: parent.left anchors.fill: parent
anchors.right: parent.right
wrapMode: Text.WordWrap StyledText {
id: innerText
text: confirmationDialog.confirmationText
font.pixelSize: 15
anchors.left: parent.left
anchors.right: parent.right
wrapMode: Text.WordWrap
}
StatusCheckBox {
id: checkbox
visible: false
anchors.top: innerText.bottom
anchors.topMargin: Style.current.halfPadding
Layout.preferredWidth: parent.width
text: qsTr("Do not show this again")
}
} }
footer: Item { footer: Item {
id: footerContainer id: footerContainer
width: parent.width width: parent.width
@ -48,11 +66,17 @@ ModalPopup {
StatusButton { StatusButton {
id: confirmButton id: confirmButton
type: confirmationDialog.btnType type: confirmationDialog.btnType
anchors.right: cancelButton.left anchors.right: cancelButton.visible ? cancelButton.left : parent.right
anchors.rightMargin: Style.current.smallPadding anchors.rightMargin: cancelButton.visible ? Style.current.smallPadding : 0
text: confirmationDialog.confirmButtonLabel text: confirmationDialog.confirmButtonLabel
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
onClicked: confirmationDialog.confirmButtonClicked() onClicked: {
if (executeConfirm && typeof executeConfirm === "function") {
executeConfirm()
}
confirmationDialog.confirmButtonClicked()
}
} }
StatusButton { StatusButton {
@ -62,7 +86,12 @@ ModalPopup {
anchors.rightMargin: Style.current.smallPadding anchors.rightMargin: Style.current.smallPadding
text: confirmationDialog.cancelButtonLabel text: confirmationDialog.cancelButtonLabel
anchors.bottom: parent.bottom anchors.bottom: parent.bottom
onClicked: confirmationDialog.cancelButtonClicked() onClicked: {
if (executeConfirm && typeof executeConfirm === "function") {
executeConfirm()
}
confirmationDialog.cancelButtonClicked()
}
} }
} }
} }

2
vendor/status-go vendored

@ -1 +1 @@
Subproject commit 026fcb09a4b45c7764eb6c38f76c3cc10a9dba39 Subproject commit d45535fecbe66d1cabc6384fb357ffa1de4d7a49