mirror of
https://github.com/vector-im/element-ios.git
synced 2024-09-29 07:42:40 +00:00
bb506f8dd3
- Updated avatar menu
141 lines
5.2 KiB
Swift
141 lines
5.2 KiB
Swift
//
|
|
// Copyright 2022 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 UIKit
|
|
import MatrixSDK
|
|
|
|
enum AllChatsSpaceActionProviderOption {
|
|
case invitePeople
|
|
case spaceMembers
|
|
case spaceSettings
|
|
case leaveSpace
|
|
}
|
|
|
|
protocol AllChatsSpaceActionProviderDelegate: AnyObject {
|
|
func allChatsSpaceActionProvider(_ actionProvider: AllChatsSpaceActionProvider, didSelect option: AllChatsSpaceActionProviderOption)
|
|
}
|
|
|
|
/// `AllChatsSpaceActionProvider` provides the menu for accessing space options according to the current space
|
|
class AllChatsSpaceActionProvider {
|
|
|
|
// MARK: - Properties
|
|
|
|
weak var delegate: AllChatsSpaceActionProviderDelegate?
|
|
|
|
// MARK: - Private
|
|
|
|
private var currentSpace: MXSpace? {
|
|
didSet {
|
|
spaceName = currentSpace?.summary?.displayname ?? VectorL10n.spaceTag
|
|
}
|
|
}
|
|
private var spaceName: String = VectorL10n.spaceTag
|
|
private var isInviteAvailable: Bool = false
|
|
|
|
// MARK: - RoomActionProviderProtocol
|
|
|
|
var menu: UIMenu {
|
|
guard currentSpace != nil else {
|
|
return UIMenu(title: "", children: [])
|
|
}
|
|
|
|
return UIMenu(title: "", children: [
|
|
UIMenu(title: "", options: .displayInline, children: [
|
|
self.spaceSettingsAction,
|
|
self.spaceMembersAction,
|
|
self.invitePeopleAction
|
|
]),
|
|
self.leaveSpaceAction
|
|
])
|
|
}
|
|
|
|
// MARK: - Public
|
|
|
|
/// Returns an instance of the updated menu accordingly to the given parameters.
|
|
///
|
|
/// Some menu items can be disabled depending on the required power levels of the `parentSpace`. Therefore, `updateMenu()` first returns a temporary context menu
|
|
/// with all sensible items disabled, asynchronously fetches power levels of the `parentSpace`, then gives a new instance of the menu with, potentially, all sensible items
|
|
/// enabled via the `completion` callback.
|
|
///
|
|
/// - Parameters:
|
|
/// - session: The current `MXSession` instance
|
|
/// - space: The current space (`nil` for home space)
|
|
/// - completion: callback called once the power levels of the `parentSpace` have been fetched and the menu items have been computed accordingly.
|
|
/// - Returns: If the `parentSpace` is `nil`, the context menu, the temporary context menu otherwise.
|
|
func updateMenu(with session: MXSession?, space: MXSpace?, completion: @escaping (UIMenu) -> Void) -> UIMenu {
|
|
self.currentSpace = space
|
|
isInviteAvailable = false
|
|
|
|
guard let currentSpace = currentSpace, let spaceRoom = currentSpace.room, let session = session else {
|
|
return self.menu
|
|
}
|
|
|
|
spaceRoom.state { [weak self] roomState in
|
|
guard let self = self else { return }
|
|
|
|
guard let powerLevels = roomState?.powerLevels, let userId = session.myUserId else {
|
|
return
|
|
}
|
|
let userPowerLevel = powerLevels.powerLevelOfUser(withUserID: userId)
|
|
|
|
self.isInviteAvailable = userPowerLevel >= powerLevels.invite
|
|
|
|
completion(self.menu)
|
|
}
|
|
|
|
return self.menu
|
|
}
|
|
|
|
// MARK: - Private
|
|
|
|
private var invitePeopleAction: UIAction {
|
|
UIAction(title: VectorL10n.inviteTo(spaceName),
|
|
image: UIImage(systemName: "square.and.arrow.up"),
|
|
attributes: isInviteAvailable ? [] : .disabled) { [weak self] action in
|
|
guard let self = self else { return }
|
|
|
|
self.delegate?.allChatsSpaceActionProvider(self, didSelect: .invitePeople)
|
|
}
|
|
}
|
|
|
|
private var spaceMembersAction: UIAction {
|
|
UIAction(title: VectorL10n.roomDetailsPeople,
|
|
image: UIImage(systemName: "person")) { [weak self] action in
|
|
guard let self = self else { return }
|
|
|
|
self.delegate?.allChatsSpaceActionProvider(self, didSelect: .spaceMembers)
|
|
}
|
|
}
|
|
|
|
private var spaceSettingsAction: UIAction {
|
|
UIAction(title: VectorL10n.allChatsEditMenuSpaceSettings,
|
|
image: UIImage(systemName: "gearshape")) { [weak self] action in
|
|
guard let self = self else { return }
|
|
|
|
self.delegate?.allChatsSpaceActionProvider(self, didSelect: .spaceSettings)
|
|
}
|
|
}
|
|
|
|
private var leaveSpaceAction: UIAction {
|
|
UIAction(title: VectorL10n.allChatsEditMenuLeaveSpace(spaceName),
|
|
image: UIImage(systemName: "rectangle.portrait.and.arrow.right.fill"),
|
|
attributes: .destructive) { [weak self] action in
|
|
guard let self = self else { return }
|
|
|
|
self.delegate?.allChatsSpaceActionProvider(self, didSelect: .leaveSpace)
|
|
}
|
|
}
|
|
}
|