Files
element-x-ios/ElementX/Sources/Screens/RoomScreen/ComposerToolbar/CompletionSuggestionServiceProtocol.swift
T
Stefan Ceriu 38416dbb5c Plain composer suggestions and pills (#2751)
* Move ComposerToolbar files to withing the RoomScreen folder (as it's not a screen on its own)

* Switch the plain composer to NSAttributedStrings

* Enable suggestions on the plain composer

* Introduce a new `MatrixUserDisplayName` attributed string attributed and use it for mention building

* Implement mention pill rendering and sending on the plain message composer

* Fix plain composer snapshot tests

* Fix broken formatting options layout

* Add clarifying comment.
2024-05-03 10:06:16 +01:00

89 lines
2.4 KiB
Swift

//
// Copyright 2023 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 Combine
import Foundation
import WysiwygComposer
struct SuggestionTrigger: Equatable {
enum SuggestionType: Equatable {
case user
}
let type: SuggestionType
let text: String
let range: NSRange
}
enum SuggestionItem: Identifiable, Equatable {
case user(item: MentionSuggestionItem)
case allUsers(item: MentionSuggestionItem)
var id: String {
switch self {
case .user(let user):
return user.id
case .allUsers:
return PillConstants.atRoom
}
}
var range: NSRange {
switch self {
case .user(let item), .allUsers(let item):
return item.range
}
}
}
struct MentionSuggestionItem: Identifiable, Equatable {
let id: String
let displayName: String?
let avatarURL: URL?
let range: NSRange
}
// sourcery: AutoMockable
protocol CompletionSuggestionServiceProtocol {
var suggestionsPublisher: AnyPublisher<[SuggestionItem], Never> { get }
func processTextMessage(_ textMessage: String?)
func setSuggestionTrigger(_ suggestionTrigger: SuggestionTrigger?)
}
extension WysiwygComposer.SuggestionPattern {
var toElementPattern: SuggestionTrigger? {
switch key {
case .at:
return SuggestionTrigger(type: .user, text: text, range: .init(location: Int(start), length: Int(end)))
default:
return nil
}
}
}
extension CompletionSuggestionServiceMock {
struct CompletionSuggestionServiceMockConfiguration {
var suggestions: [SuggestionItem] = []
}
convenience init(configuration: CompletionSuggestionServiceMockConfiguration) {
self.init()
underlyingSuggestionsPublisher = Just(configuration.suggestions).eraseToAnyPublisher()
}
}