mirror of
https://gitlab.opencode.de/bwi/bundesmessenger/clients/bundesmessenger-ios.git
synced 2026-04-17 23:18:27 +02:00
Add EventMenuBuilder to manage ordering on event menu actions
This commit is contained in:
50
Riot/Modules/Room/EventMenu/EventMenuBuilder.swift
Normal file
50
Riot/Modules/Room/EventMenu/EventMenuBuilder.swift
Normal file
@@ -0,0 +1,50 @@
|
||||
//
|
||||
// Copyright 2021 New Vector Ltd
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
/// Class to build an event menu.
|
||||
@objcMembers
|
||||
class EventMenuBuilder: NSObject {
|
||||
|
||||
private var items: [EventMenuItemType: UIAlertAction] = [:]
|
||||
|
||||
/// Returns true if no items or only one item with the type `EventMenuItemType.cancel`.
|
||||
var isEmpty: Bool {
|
||||
return items.isEmpty || (items.count == 1 && items.first?.key == .cancel)
|
||||
}
|
||||
|
||||
/// Add a menu item.
|
||||
/// - Parameters:
|
||||
/// - type: item type
|
||||
/// - action: alert action
|
||||
func addItem(withType type: EventMenuItemType,
|
||||
action: UIAlertAction) {
|
||||
items[type] = action
|
||||
}
|
||||
|
||||
/// Builds the action menu items.
|
||||
/// - Returns: alert actions. Sorted by item types.
|
||||
func build() -> [UIAlertAction] {
|
||||
items.sorted(by: { $0.key < $1.key }).map { $1 }
|
||||
}
|
||||
|
||||
/// Reset the builder. Builder will be empty after this method call.
|
||||
func reset() {
|
||||
items.removeAll()
|
||||
}
|
||||
|
||||
}
|
||||
49
Riot/Modules/Room/EventMenu/EventMenuItemType.swift
Normal file
49
Riot/Modules/Room/EventMenu/EventMenuItemType.swift
Normal file
@@ -0,0 +1,49 @@
|
||||
//
|
||||
// Copyright 2021 New Vector Ltd
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
/// Type of an event menu item. Ordering of the cases is important. See `EventMenuBuilder`.
|
||||
@objc
|
||||
enum EventMenuItemType: Int {
|
||||
case viewInRoom
|
||||
case copy
|
||||
case retrySending
|
||||
case cancelSending
|
||||
case cancelDownloading
|
||||
case saveMedia
|
||||
case quote
|
||||
case forward
|
||||
case permalink
|
||||
case share
|
||||
case removePoll
|
||||
case endPoll
|
||||
case reactionHistory
|
||||
case viewSource
|
||||
case viewDecryptedSource
|
||||
case viewEncryption
|
||||
case report
|
||||
case remove
|
||||
case cancel
|
||||
}
|
||||
|
||||
extension EventMenuItemType: Comparable {
|
||||
|
||||
static func < (lhs: EventMenuItemType, rhs: EventMenuItemType) -> Bool {
|
||||
return lhs.rawValue < rhs.rawValue
|
||||
}
|
||||
|
||||
}
|
||||
@@ -254,6 +254,7 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
@property (nonatomic, strong) SpaceDetailPresenter *spaceDetailPresenter;
|
||||
|
||||
@property (nonatomic, strong) ShareManager *shareManager;
|
||||
@property (nonatomic, strong) EventMenuBuilder *eventMenuBuilder;
|
||||
|
||||
@property (nonatomic, strong) UserSuggestionCoordinatorBridge *userSuggestionCoordinator;
|
||||
@property (nonatomic, weak) IBOutlet UIView *userSuggestionContainerView;
|
||||
@@ -345,6 +346,7 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
self.enableBarTintColorStatusChange = NO;
|
||||
self.rageShakeManager = [RageShakeManager sharedManager];
|
||||
formattedBodyParser = [FormattedBodyParser new];
|
||||
self.eventMenuBuilder = [EventMenuBuilder new];
|
||||
|
||||
_showMissedDiscussionsBadge = YES;
|
||||
_scrollToBottomHidden = YES;
|
||||
@@ -3249,17 +3251,19 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
currentAlert = nil;
|
||||
}
|
||||
|
||||
[self.eventMenuBuilder reset];
|
||||
|
||||
MXWeakify(self);
|
||||
UIAlertController *actionsMenu = [UIAlertController alertControllerWithTitle:nil message:nil preferredStyle:UIAlertControllerStyleActionSheet];
|
||||
|
||||
BOOL showThreadOption = RiotSettings.shared.enableThreads
|
||||
&& !self.roomDataSource.threadId
|
||||
&& !selectedEvent.threadId;
|
||||
&& !self.roomDataSource.threadId
|
||||
&& !selectedEvent.threadId;
|
||||
if (showThreadOption && [self canCopyEvent:selectedEvent andCell:cell])
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCopy]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeCopy
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCopy]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3271,9 +3275,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
// Add actions for a failed event
|
||||
if (selectedEvent.sentState == MXEventSentStateFailed)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n retry]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeRetrySending
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n retry]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3282,9 +3287,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
[self.roomDataSource resendEventWithEventId:selectedEvent.eventId success:nil failure:nil];
|
||||
}]];
|
||||
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionDelete]
|
||||
style:UIAlertActionStyleDestructive
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeRemove
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionDelete]
|
||||
style:UIAlertActionStyleDestructive
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3298,9 +3304,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
{
|
||||
// if in the thread and selected event is the root event
|
||||
// add "View in room" action
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewInRoom]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeViewInRoom
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewInRoom]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
[self.delegate roomViewController:self
|
||||
showRoomWithId:self.roomDataSource.roomId
|
||||
@@ -3329,9 +3336,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
selectedEvent.sentState == MXEventSentStateEncrypting ||
|
||||
selectedEvent.sentState == MXEventSentStateSending)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelSend]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeCancelSending
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelSend]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
self->currentAlert = nil;
|
||||
@@ -3346,9 +3354,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (!isJitsiCallEvent && selectedEvent.eventType != MXEventTypePollStart)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionQuote]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeQuote
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionQuote]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3363,9 +3372,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (selectedEvent.sentState == MXEventSentStateSent && selectedEvent.eventType != MXEventTypePollStart)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionForward]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeForward
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionForward]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
[self presentEventForwardingDialogForSelectedEvent:selectedEvent];
|
||||
}]];
|
||||
@@ -3373,9 +3383,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (!isJitsiCallEvent && BuildSettings.messageDetailsAllowShare && selectedEvent.eventType != MXEventTypePollStart)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionShare]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeShare
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionShare]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3402,9 +3413,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
attachment.type == MXKAttachmentTypeImage ||
|
||||
attachment.type == MXKAttachmentTypeVideo ||
|
||||
attachment.type == MXKAttachmentTypeVoiceMessage)) {
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionForward]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeForward
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionForward]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
[self presentEventForwardingDialogForSelectedEvent:selectedEvent];
|
||||
}]];
|
||||
@@ -3414,9 +3426,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
{
|
||||
if (attachment.type == MXKAttachmentTypeImage || attachment.type == MXKAttachmentTypeVideo)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionSave]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeSaveMedia
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionSave]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3451,9 +3464,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
NSString *uploadId = roomBubbleTableViewCell.bubbleData.attachment.contentURL;
|
||||
if ([MXMediaManager existingUploaderWithId:uploadId])
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelSend]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeCancelSending
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelSend]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
@@ -3485,9 +3499,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
{
|
||||
if (BuildSettings.messageDetailsAllowShare)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionShare]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeShare
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionShare]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3532,9 +3547,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
NSString *downloadId = roomBubbleTableViewCell.bubbleData.attachment.downloadId;
|
||||
if ([MXMediaManager existingDownloaderWithIdentifier:downloadId])
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelDownload]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeCancelDownloading
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionCancelDownload]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3553,9 +3569,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (BuildSettings.messageDetailsAllowPermalink)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionPermalink]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypePermalink
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionPermalink]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3581,9 +3598,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (BuildSettings.messageDetailsAllowViewSource)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewSource]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeViewSource
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewSource]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3596,9 +3614,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
// Add "View Decrypted Source" for e2ee event we can decrypt
|
||||
if (selectedEvent.isEncrypted && selectedEvent.clearEvent)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewDecryptedSource]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeViewDecryptedSource
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewDecryptedSource]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3608,26 +3627,31 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
}]];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Do not allow to redact the event that enabled encryption (m.room.encryption)
|
||||
// because it breaks everything
|
||||
if (selectedEvent.eventType != MXEventTypeRoomEncryption)
|
||||
{
|
||||
NSString *title;
|
||||
UIAlertActionStyle style = UIAlertActionStyleDefault;
|
||||
UIAlertActionStyle style;
|
||||
EventMenuItemType itemType;
|
||||
if (selectedEvent.eventType == MXEventTypePollStart)
|
||||
{
|
||||
title = [VectorL10n roomEventActionRemovePoll];
|
||||
style = UIAlertActionStyleDefault;
|
||||
itemType = EventMenuItemTypeRemovePoll;
|
||||
}
|
||||
else
|
||||
{
|
||||
title = [VectorL10n roomEventActionRedact];
|
||||
style = UIAlertActionStyleDestructive;
|
||||
itemType = EventMenuItemTypeRemove;
|
||||
}
|
||||
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:title
|
||||
style:style
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:itemType
|
||||
action:[UIAlertAction actionWithTitle:title
|
||||
style:style
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3649,11 +3673,14 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
}]];
|
||||
}
|
||||
|
||||
if (selectedEvent.eventType == MXEventTypePollStart && [selectedEvent.sender isEqualToString:self.mainSession.myUserId]) {
|
||||
if ([self.delegate roomViewController:self canEndPollWithEventIdentifier:selectedEvent.eventId]) {
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionEndPoll]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
if (selectedEvent.eventType == MXEventTypePollStart && [selectedEvent.sender isEqualToString:self.mainSession.myUserId])
|
||||
{
|
||||
if ([self.delegate roomViewController:self canEndPollWithEventIdentifier:selectedEvent.eventId])
|
||||
{
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeEndPoll
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionEndPoll]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self.delegate roomViewController:self endPollWithEventIdentifier:selectedEvent.eventId];
|
||||
@@ -3666,9 +3693,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
// Add reaction history if event contains reactions
|
||||
if (roomBubbleTableViewCell.bubbleData.reactions[selectedEvent.eventId].aggregatedReactionsWithNonZeroCount)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionReactionHistory]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeReactionHistory
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionReactionHistory]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3680,9 +3708,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (![selectedEvent.sender isEqualToString:self.mainSession.myUserId] && RiotSettings.shared.roomContextualMenuShowReportContentOption)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionReport]
|
||||
style:UIAlertActionStyleDestructive
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeReport
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionReport]
|
||||
style:UIAlertActionStyleDestructive
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3772,9 +3801,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
|
||||
if (!isJitsiCallEvent && self.roomDataSource.room.summary.isEncrypted)
|
||||
{
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewEncryption]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeViewEncryption
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n roomEventActionViewEncryption]
|
||||
style:UIAlertActionStyleDefault
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self cancelEventSelection];
|
||||
@@ -3784,9 +3814,10 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
}]];
|
||||
}
|
||||
|
||||
[actionsMenu addAction:[UIAlertAction actionWithTitle:[VectorL10n cancel]
|
||||
style:UIAlertActionStyleCancel
|
||||
handler:^(UIAlertAction * action) {
|
||||
[self.eventMenuBuilder addItemWithType:EventMenuItemTypeCancel
|
||||
action:[UIAlertAction actionWithTitle:[VectorL10n cancel]
|
||||
style:UIAlertActionStyleCancel
|
||||
handler:^(UIAlertAction * action) {
|
||||
MXStrongifyAndReturnIfNil(self);
|
||||
|
||||
[self hideContextualMenuAnimated:YES];
|
||||
@@ -3795,8 +3826,17 @@ const NSTimeInterval kResizeComposerAnimationDuration = .05;
|
||||
}
|
||||
|
||||
// Do not display empty action sheet
|
||||
if (actionsMenu.actions.count > 1)
|
||||
if (!self.eventMenuBuilder.isEmpty)
|
||||
{
|
||||
UIAlertController *actionsMenu = [UIAlertController alertControllerWithTitle:nil message:nil preferredStyle:UIAlertControllerStyleActionSheet];
|
||||
|
||||
// build actions and add them to the alert
|
||||
NSArray<UIAlertAction*> *actions = [self.eventMenuBuilder build];
|
||||
for (UIAlertAction *action in actions)
|
||||
{
|
||||
[actionsMenu addAction:action];
|
||||
}
|
||||
|
||||
NSInteger bubbleComponentIndex = [roomBubbleTableViewCell.bubbleData bubbleComponentIndexForEventId:selectedEvent.eventId];
|
||||
|
||||
CGRect sourceRect = [roomBubbleTableViewCell componentFrameInContentViewForIndex:bubbleComponentIndex];
|
||||
|
||||
59
RiotTests/EventMenuBuilderTests.swift
Normal file
59
RiotTests/EventMenuBuilderTests.swift
Normal file
@@ -0,0 +1,59 @@
|
||||
//
|
||||
// Copyright 2021 New Vector Ltd
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
|
||||
import XCTest
|
||||
import UIKit
|
||||
@testable import Riot
|
||||
|
||||
class EventMenuBuilderTests: XCTestCase {
|
||||
|
||||
func testSorting() {
|
||||
let builder = EventMenuBuilder()
|
||||
|
||||
let title2 = "Title 2"
|
||||
|
||||
builder.addItem(withType: .copy,
|
||||
action: UIAlertAction(title: "Title 1", style: .default, handler: nil))
|
||||
|
||||
builder.addItem(withType: .viewInRoom,
|
||||
action: UIAlertAction(title: title2, style: .default, handler: nil))
|
||||
|
||||
let actions = builder.build()
|
||||
|
||||
XCTAssertEqual(actions.first?.title, title2, "Item with title 'title2' must come first in the result")
|
||||
}
|
||||
|
||||
func testEmptiness() {
|
||||
let builder = EventMenuBuilder()
|
||||
|
||||
XCTAssertTrue(builder.isEmpty, "Builder must be empty after initialization")
|
||||
|
||||
builder.addItem(withType: .cancel,
|
||||
action: UIAlertAction(title: "Cancel", style: .default, handler: nil))
|
||||
|
||||
XCTAssertTrue(builder.isEmpty, "Builder must still be empty after adding only a cancel action")
|
||||
|
||||
builder.addItem(withType: .share,
|
||||
action: UIAlertAction(title: "some_title", style: .default, handler: nil))
|
||||
|
||||
XCTAssertFalse(builder.isEmpty, "Builder must not be empty after adding an item")
|
||||
|
||||
builder.reset()
|
||||
|
||||
XCTAssertTrue(builder.isEmpty, "Builder must be empty again after reset")
|
||||
}
|
||||
|
||||
}
|
||||
@@ -64,3 +64,5 @@ targets:
|
||||
- path: ../Riot/Managers/EncryptionKeyManager/EncryptionKeyManager.swift
|
||||
- path: ../Riot/Managers/KeyValueStorage/
|
||||
- path: ../Riot/PropertyWrappers/UserDefaultsBackedPropertyWrapper.swift
|
||||
- path: ../Riot/Modules/Room/EventMenu/EventMenuBuilder.swift
|
||||
- path: ../Riot/Modules/Room/EventMenu/EventMenuItemType.swift
|
||||
|
||||
Reference in New Issue
Block a user