565 lines
20 KiB
QML
565 lines
20 KiB
QML
import QtQuick 2.15
|
|
import QtQuick.Layouts 1.15
|
|
import QtQuick.Dialogs 1.3
|
|
import QtQml.Models 2.15
|
|
import QtQml 2.15
|
|
|
|
import StatusQ.Core 0.1
|
|
import StatusQ.Controls 0.1
|
|
import StatusQ.Components 0.1
|
|
import StatusQ.Popups 0.1
|
|
|
|
import AppLayouts.Chat.popups 1.0
|
|
import AppLayouts.Profile.popups 1.0
|
|
import AppLayouts.Communities.popups 1.0
|
|
|
|
import shared.popups 1.0
|
|
import shared.status 1.0
|
|
|
|
import utils 1.0
|
|
|
|
QtObject {
|
|
id: root
|
|
|
|
required property var popupParent
|
|
required property var rootStore
|
|
property var communitiesStore
|
|
property bool isDevBuild
|
|
|
|
property var activePopupComponents: []
|
|
|
|
Component.onCompleted: {
|
|
Global.openSendIDRequestPopup.connect(openSendIDRequestPopup)
|
|
Global.openOutgoingIDRequestPopup.connect(openOutgoingIDRequestPopup)
|
|
Global.openIncomingIDRequestPopup.connect(openIncomingIDRequestPopup)
|
|
Global.openInviteFriendsToCommunityPopup.connect(openInviteFriendsToCommunityPopup)
|
|
Global.openContactRequestPopup.connect(openContactRequestPopup)
|
|
Global.openChooseBrowserPopup.connect(openChooseBrowserPopup)
|
|
Global.openDownloadModalRequested.connect(openDownloadModal)
|
|
Global.openImagePopup.connect(openImagePopup)
|
|
Global.openProfilePopupRequested.connect(openProfilePopup)
|
|
Global.openNicknamePopupRequested.connect(openNicknamePopup)
|
|
Global.blockContactRequested.connect(openBlockContactPopup)
|
|
Global.unblockContactRequested.connect(openUnblockContactPopup)
|
|
Global.openChangeProfilePicPopup.connect(openChangeProfilePicPopup)
|
|
Global.openBackUpSeedPopup.connect(openBackUpSeedPopup)
|
|
Global.openEditDisplayNamePopup.connect(openEditDisplayNamePopup)
|
|
Global.openPinnedMessagesPopupRequested.connect(openPinnedMessagesPopup)
|
|
Global.openCommunityProfilePopupRequested.connect(openCommunityProfilePopup)
|
|
Global.createCommunityPopupRequested.connect(openCreateCommunityPopup)
|
|
Global.importCommunityPopupRequested.connect(openImportCommunityPopup)
|
|
Global.removeContactRequested.connect(openRemoveContactConfirmationPopup)
|
|
Global.openPopupRequested.connect(openPopup)
|
|
Global.closePopupRequested.connect(closePopup)
|
|
Global.openDeleteMessagePopup.connect(openDeleteMessagePopup)
|
|
Global.openDownloadImageDialog.connect(openDownloadImageDialog)
|
|
Global.leaveCommunityRequested.connect(openLeaveCommunityPopup)
|
|
}
|
|
|
|
property var currentPopup
|
|
function openPopup(popupComponent, params = {}, cb = null) {
|
|
if (activePopupComponents.includes(popupComponent)) {
|
|
return
|
|
}
|
|
|
|
root.currentPopup = popupComponent.createObject(popupParent, params)
|
|
root.currentPopup.open();
|
|
if (cb)
|
|
cb(root.currentPopup)
|
|
|
|
activePopupComponents.push(popupComponent)
|
|
|
|
root.currentPopup.closed.connect(() => {
|
|
const removeIndex = activePopupComponents.indexOf(popupComponent)
|
|
if (removeIndex !== -1) {
|
|
activePopupComponents.splice(removeIndex, 1)
|
|
}
|
|
})
|
|
}
|
|
|
|
function closePopup() {
|
|
if (!!root.currentPopup)
|
|
root.currentPopup.close();
|
|
}
|
|
|
|
function openChooseBrowserPopup(link: string) {
|
|
openPopup(chooseBrowserPopupComponent, {link: link})
|
|
}
|
|
|
|
function openDownloadModal(available: bool, version: string, url: string) {
|
|
const popupProperties = {
|
|
newVersionAvailable: available,
|
|
downloadURL: url,
|
|
currentVersion: rootStore.profileSectionStore.getCurrentVersion(),
|
|
newVersion: version
|
|
}
|
|
openPopup(downloadPageComponent, popupProperties)
|
|
}
|
|
|
|
function openImagePopup(image) {
|
|
var popup = imagePopupComponent.createObject(popupParent)
|
|
popup.openPopup(image)
|
|
}
|
|
|
|
function openProfilePopup(publicKey: string, parentPopup, cb) {
|
|
openPopup(profilePopupComponent, {publicKey: publicKey, parentPopup: parentPopup}, cb)
|
|
}
|
|
|
|
function openNicknamePopup(publicKey: string, nickname: string, subtitle: string) {
|
|
openPopup(nicknamePopupComponent, {publicKey: publicKey, nickname: nickname, "headerSettings.subTitle": subtitle})
|
|
}
|
|
|
|
function openBlockContactPopup(publicKey: string, contactName: string) {
|
|
openPopup(blockContactConfirmationComponent, {contactName: contactName, contactAddress: publicKey})
|
|
}
|
|
|
|
function openUnblockContactPopup(publicKey: string, contactName: string) {
|
|
openPopup(unblockContactConfirmationComponent, {contactName: contactName, contactAddress: publicKey})
|
|
}
|
|
|
|
function openChangeProfilePicPopup(cb) {
|
|
var popup = changeProfilePicComponent.createObject(popupParent, {callback: cb});
|
|
popup.chooseImageToCrop()
|
|
}
|
|
|
|
function openBackUpSeedPopup() {
|
|
openPopup(backupSeedModalComponent)
|
|
}
|
|
|
|
function openEditDisplayNamePopup() {
|
|
openPopup(displayNamePopupComponent)
|
|
}
|
|
|
|
function openCommunityProfilePopup(store, community, communitySectionModule) {
|
|
openPopup(communityProfilePopup, { store: store, community: community, communitySectionModule: communitySectionModule})
|
|
}
|
|
|
|
function openSendIDRequestPopup(publicKey, cb) {
|
|
const contactDetails = Utils.getContactDetailsAsJson(publicKey, false)
|
|
openPopup(sendIDRequestPopupComponent, {
|
|
userPublicKey: publicKey,
|
|
userDisplayName: contactDetails.displayName,
|
|
userIcon: contactDetails.largeImage,
|
|
userIsEnsVerified: contactDetails.ensVerified,
|
|
"headerSettings.title": qsTr("Verify %1's Identity").arg(contactDetails.displayName),
|
|
challengeText: qsTr("Ask a question that only the real %1 will be able to answer e.g. a question about a shared experience, or ask %1 to enter a code or phrase you have sent to them via a different communication channel (phone, post, etc...).").arg(contactDetails.displayName),
|
|
buttonText: qsTr("Send verification request")
|
|
}, cb)
|
|
}
|
|
|
|
function openOutgoingIDRequestPopup(publicKey, cb) {
|
|
try {
|
|
const verificationDetails = root.rootStore.profileSectionStore.contactsStore.getSentVerificationDetailsAsJson(publicKey)
|
|
const popupProperties = {
|
|
userPublicKey: publicKey,
|
|
verificationStatus: verificationDetails.requestStatus,
|
|
verificationChallenge: verificationDetails.challenge,
|
|
verificationResponse: verificationDetails.response,
|
|
verificationResponseDisplayName: verificationDetails.displayName,
|
|
verificationResponseIcon: verificationDetails.icon,
|
|
verificationRequestedAt: verificationDetails.requestedAt,
|
|
verificationRepliedAt: verificationDetails.repliedAt
|
|
}
|
|
openPopup(contactOutgoingVerificationRequestPopupComponent, popupProperties, cb)
|
|
} catch (e) {
|
|
console.error("Error getting or parsing verification data", e)
|
|
}
|
|
}
|
|
|
|
function openIncomingIDRequestPopup(publicKey, cb) {
|
|
const popupProperties = {
|
|
contactsStore: root.rootStore.profileSectionStore.contactsStore,
|
|
publicKey: publicKey
|
|
}
|
|
|
|
openPopup(contactVerificationRequestPopupComponent, popupProperties, cb)
|
|
}
|
|
|
|
function openInviteFriendsToCommunityPopup(community, communitySectionModule, cb) {
|
|
openPopup(inviteFriendsToCommunityPopup, { community: community, communitySectionModule: communitySectionModule }, cb)
|
|
}
|
|
|
|
function openContactRequestPopup(publicKey, cb) {
|
|
const contactDetails = Utils.getContactDetailsAsJson(publicKey, false)
|
|
const popupProperties = {
|
|
userPublicKey: publicKey,
|
|
userDisplayName: contactDetails.displayName,
|
|
userIcon: contactDetails.largeImage,
|
|
userIsEnsVerified: contactDetails.ensVerified
|
|
}
|
|
|
|
openPopup(sendContactRequestPopupComponent, popupProperties, cb)
|
|
}
|
|
|
|
function openPinnedMessagesPopup(store, messageStore, pinnedMessagesModel, messageToPin, chatId) {
|
|
openPopup(pinnedMessagesPopup, {
|
|
store: store,
|
|
messageStore: messageStore,
|
|
pinnedMessagesModel: pinnedMessagesModel,
|
|
messageToPin: messageToPin,
|
|
chatId: chatId
|
|
})
|
|
}
|
|
|
|
function openCommunityPopup(store, community, chatCommunitySectionModule) {
|
|
openPopup(communityProfilePopup, {store: store, community: community, chatCommunitySectionModule: chatCommunitySectionModule})
|
|
}
|
|
|
|
function openCreateCommunityPopup(isDiscordImport) {
|
|
openPopup(createCommunitiesPopupComponent, {isDiscordImport: isDiscordImport})
|
|
}
|
|
|
|
function openImportCommunityPopup() {
|
|
openPopup(importCommunitiesPopupComponent)
|
|
}
|
|
|
|
function openDiscordImportProgressPopup() {
|
|
openPopup(discordImportProgressDialog)
|
|
}
|
|
|
|
function openRemoveContactConfirmationPopup(displayName, publicKey) {
|
|
openPopup(removeContactConfirmationDialog, {
|
|
displayName: displayName,
|
|
publicKey: publicKey
|
|
})
|
|
}
|
|
|
|
function openDeleteMessagePopup(messageId, messageStore) {
|
|
openPopup(deleteMessageConfirmationDialogComponent,
|
|
{
|
|
messageId,
|
|
messageStore
|
|
})
|
|
}
|
|
|
|
function openDownloadImageDialog(imageSource) {
|
|
// We don't use `openPopup`, because there's no `FileDialog::closed` signal.
|
|
const popup = downloadImageDialogComponent.createObject(popupParent, { imageSource })
|
|
popup.open()
|
|
}
|
|
|
|
function openLeaveCommunityPopup(community, communityId, outroMessage) {
|
|
openPopup(leaveCommunityPopupComponent, {community, communityId, outroMessage})
|
|
}
|
|
|
|
readonly property list<Component> _components: [
|
|
Component {
|
|
id: removeContactConfirmationDialog
|
|
ConfirmationDialog {
|
|
property string displayName
|
|
property string publicKey
|
|
headerSettings.title: qsTr("Remove '%1' as a contact").arg(displayName)
|
|
confirmationText: qsTr("This will mean that you and '%1' will no longer be able to send direct messages to each other. You will need to send them a new Contact Request in order to message again. All previous direct messages between you and '%1' will be retained in read-only mode.").arg(displayName)
|
|
showCancelButton: true
|
|
cancelBtnType: ""
|
|
onConfirmButtonClicked: {
|
|
rootStore.contactStore.removeContact(publicKey);
|
|
close();
|
|
}
|
|
onCancelButtonClicked: {
|
|
close();
|
|
}
|
|
onClosed: { destroy(); }
|
|
}
|
|
},
|
|
Component {
|
|
id: contactVerificationRequestPopupComponent
|
|
ContactVerificationRequestPopup {
|
|
onResponseSent: {
|
|
root.rootStore.profileSectionStore.contactsStore.acceptVerificationRequest(senderPublicKey, response)
|
|
}
|
|
onVerificationRefused: {
|
|
root.rootStore.profileSectionStore.contactsStore.declineVerificationRequest(senderPublicKey)
|
|
}
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: contactOutgoingVerificationRequestPopupComponent
|
|
OutgoingContactVerificationRequestPopup {
|
|
onVerificationRequestCanceled: {
|
|
root.rootStore.profileSectionStore.contactsStore.cancelVerificationRequest(userPublicKey)
|
|
}
|
|
onUntrustworthyVerified: {
|
|
root.rootStore.profileSectionStore.contactsStore.verifiedUntrustworthy(userPublicKey)
|
|
}
|
|
onTrustedVerified: {
|
|
root.rootStore.profileSectionStore.contactsStore.verifiedTrusted(userPublicKey)
|
|
}
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: sendIDRequestPopupComponent
|
|
SendContactRequestModal {
|
|
rootStore: root.rootStore
|
|
onAccepted: root.rootStore.profileSectionStore.contactsStore.sendVerificationRequest(userPublicKey, message)
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: inviteFriendsToCommunityPopup
|
|
|
|
InviteFriendsToCommunityPopup {
|
|
rootStore: root.rootStore
|
|
contactsStore: root.rootStore.contactStore
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: sendContactRequestPopupComponent
|
|
|
|
SendContactRequestModal {
|
|
rootStore: root.rootStore
|
|
onAccepted: root.rootStore.profileSectionStore.contactsStore.sendContactRequest(userPublicKey, message)
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: backupSeedModalComponent
|
|
BackupSeedModal {
|
|
privacyStore: rootStore.profileSectionStore.privacyStore
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: displayNamePopupComponent
|
|
DisplayNamePopup {
|
|
profileStore: rootStore.profileSectionStore.profileStore
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: downloadPageComponent
|
|
DownloadPage {
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: imagePopupComponent
|
|
StatusImageModal {
|
|
id: imagePopup
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: profilePopupComponent
|
|
ProfileDialog {
|
|
id: profilePopup
|
|
profileStore: rootStore.profileSectionStore.profileStore
|
|
contactsStore: rootStore.profileSectionStore.contactsStore
|
|
communitiesModel: rootStore.profileSectionStore.communitiesList
|
|
|
|
onClosed: {
|
|
if (profilePopup.parentPopup) {
|
|
profilePopup.parentPopup.close()
|
|
}
|
|
destroy()
|
|
}
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: changeProfilePicComponent
|
|
ImageCropWorkflow {
|
|
title: qsTr("Profile Picture")
|
|
acceptButtonText: qsTr("Make this my Profile Pic")
|
|
onImageCropped: {
|
|
if (callback) {
|
|
callback(image,
|
|
cropRect.x.toFixed(),
|
|
cropRect.y.toFixed(),
|
|
(cropRect.x + cropRect.width).toFixed(),
|
|
(cropRect.y + cropRect.height).toFixed())
|
|
return
|
|
}
|
|
|
|
rootStore.profileSectionStore.profileStore.uploadImage(image,
|
|
cropRect.x.toFixed(),
|
|
cropRect.y.toFixed(),
|
|
(cropRect.x + cropRect.width).toFixed(),
|
|
(cropRect.y + cropRect.height).toFixed());
|
|
}
|
|
onDone: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: chooseBrowserPopupComponent
|
|
ChooseBrowserPopup {
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: communityProfilePopup
|
|
|
|
CommunityProfilePopup {
|
|
contactsStore: rootStore.contactStore
|
|
hasAddedContacts: rootStore.hasAddedContacts
|
|
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: pinnedMessagesPopup
|
|
PinnedMessagesPopup {
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: nicknamePopupComponent
|
|
NicknamePopup {
|
|
onEditDone: {
|
|
if (nickname !== newNickname) {
|
|
rootStore.contactStore.changeContactNickname(publicKey, newNickname)
|
|
Global.contactRenamed(publicKey)
|
|
}
|
|
close()
|
|
}
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: unblockContactConfirmationComponent
|
|
UnblockContactConfirmationDialog {
|
|
onUnblockButtonClicked: {
|
|
rootStore.contactStore.unblockContact(contactAddress)
|
|
close()
|
|
}
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: blockContactConfirmationComponent
|
|
BlockContactConfirmationDialog {
|
|
onBlockButtonClicked: {
|
|
rootStore.contactStore.blockContact(contactAddress)
|
|
close()
|
|
}
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: importCommunitiesPopupComponent
|
|
ImportCommunityPopup {
|
|
store: root.communitiesStore
|
|
onClosed: {
|
|
destroy()
|
|
}
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: createCommunitiesPopupComponent
|
|
CreateCommunityPopup {
|
|
store: root.communitiesStore
|
|
isDevBuild: root.isDevBuild
|
|
onClosed: {
|
|
destroy()
|
|
}
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: discordImportProgressDialog
|
|
DiscordImportProgressDialog {
|
|
store: root.communitiesStore
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: deleteMessageConfirmationDialogComponent
|
|
DeleteMessageConfirmationPopup {
|
|
onClosed: destroy()
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: downloadImageDialogComponent
|
|
FileDialog {
|
|
property string imageSource
|
|
title: qsTr("Please choose a directory")
|
|
selectFolder: true
|
|
selectExisting: true
|
|
selectMultiple: false
|
|
modality: Qt.NonModal
|
|
onAccepted: {
|
|
Utils.downloadImageByUrl(imageSource, fileUrl)
|
|
destroy()
|
|
}
|
|
onRejected: {
|
|
destroy()
|
|
}
|
|
}
|
|
},
|
|
|
|
Component {
|
|
id: leaveCommunityPopupComponent
|
|
StatusModal {
|
|
id: leavePopup
|
|
|
|
property string community
|
|
property string communityId
|
|
property string outroMessage
|
|
|
|
headerSettings.title: qsTr("Are you sure want to leave '%1'?").arg(community)
|
|
padding: 16
|
|
width: 640
|
|
contentItem: ColumnLayout {
|
|
spacing: 16
|
|
StatusBaseText {
|
|
id: outroMessage
|
|
Layout.fillWidth: true
|
|
wrapMode: Text.WrapAtWordBoundaryOrAnywhere
|
|
text: leavePopup.outroMessage
|
|
visible: !!text
|
|
}
|
|
StatusMenuSeparator {
|
|
Layout.fillWidth: true
|
|
visible: outroMessage.visible
|
|
}
|
|
StatusBaseText {
|
|
Layout.fillWidth: true
|
|
wrapMode: Text.WrapAtWordBoundaryOrAnywhere
|
|
font.pixelSize: 13
|
|
text: qsTr("You will need to request to join if you want to become a member again in the future. If you joined the Community via public key ensure you have a copy of it before you go.")
|
|
}
|
|
}
|
|
|
|
rightButtons: [
|
|
StatusFlatButton {
|
|
text: qsTr("Cancel")
|
|
onClicked: leavePopup.close()
|
|
},
|
|
StatusButton {
|
|
objectName: "CommunitiesListPanel_leaveCommunityButtonInPopup"
|
|
type: StatusBaseButton.Type.Danger
|
|
text: qsTr("Leave %1").arg(leavePopup.community)
|
|
onClicked: {
|
|
leavePopup.close()
|
|
root.rootStore.profileSectionStore.communitiesProfileModule.leaveCommunity(leavePopup.communityId)
|
|
}
|
|
}
|
|
]
|
|
|
|
onClosed: destroy()
|
|
}
|
|
}
|
|
]
|
|
}
|