change: hiding timeline media has three options

This commit is contained in:
Mauro Romito
2025-04-09 17:03:47 +02:00
committed by Mauro
parent 3a51db4400
commit eb98606201
5 changed files with 56 additions and 10 deletions

View File

@@ -18,7 +18,7 @@ protocol CommonSettingsProtocol {
var traceLogPacks: Set<TraceLogPack> { get }
var enableOnlySignedDeviceIsolationMode: Bool { get }
var hideInviteAvatars: Bool { get }
var hideTimelineMedia: Bool { get }
var timelineMediaVisibility: TimelineMediaVisibility { get }
}
/// Store Element specific app settings.
@@ -47,7 +47,7 @@ final class AppSettings {
case sharePresence
case hideUnreadMessagesBadge
case hideInviteAvatars
case hideTimelineMedia
case timelineMediaVisibility
case elementCallBaseURLOverride
@@ -353,8 +353,14 @@ final class AppSettings {
@UserPreference(key: UserDefaultsKeys.hideInviteAvatars, defaultValue: false, storageType: .userDefaults(store))
var hideInviteAvatars
@UserPreference(key: UserDefaultsKeys.hideTimelineMedia, defaultValue: false, storageType: .userDefaults(store))
var hideTimelineMedia
@UserPreference(key: UserDefaultsKeys.timelineMediaVisibility, defaultValue: TimelineMediaVisibility.always, storageType: .userDefaults(store))
var timelineMediaVisibility
}
extension AppSettings: CommonSettingsProtocol { }
enum TimelineMediaVisibility: Codable {
case always
case privateOnly
case never
}

View File

@@ -34,7 +34,7 @@ protocol AdvancedSettingsProtocol: AnyObject {
var viewSourceEnabled: Bool { get set }
var appAppearance: AppAppearance { get set }
var sharePresence: Bool { get set }
var hideTimelineMedia: Bool { get set }
var timelineMediaVisibility: TimelineMediaVisibility { get set }
var hideInviteAvatars: Bool { get set }
var optimizeMediaUploads: Bool { get set }
}

View File

@@ -35,6 +35,7 @@ struct AdvancedSettingsScreen: View {
}
moderationAndSafetySection
timelineMediaSection
}
.compoundList()
.navigationTitle(L10n.commonAdvancedSettings)
@@ -43,8 +44,6 @@ struct AdvancedSettingsScreen: View {
private var moderationAndSafetySection: some View {
Section {
ListRow(label: .plain(title: L10n.screenAdvancedSettingsHideTimelineMediaToggleTitle),
kind: .toggle($context.hideTimelineMedia))
ListRow(label: .plain(title: L10n.screenAdvancedSettingsHideInviteAvatarsToggleTitle),
kind: .toggle($context.hideInviteAvatars))
} header: {
@@ -52,6 +51,23 @@ struct AdvancedSettingsScreen: View {
.compoundListSectionHeader()
}
}
private var timelineMediaSection: some View {
Section {
ListRow(label: .plain(title: L10n.screenAdvancedSettingsShowMediaTimelineAlwaysShow),
kind: .selection(isSelected: context.timelineMediaVisibility == .always) { context.timelineMediaVisibility = .always })
ListRow(label: .plain(title: L10n.screenAdvancedSettingsShowMediaTimelinePrivateRooms),
kind: .selection(isSelected: context.timelineMediaVisibility == .privateOnly) { context.timelineMediaVisibility = .privateOnly })
ListRow(label: .plain(title: L10n.screenAdvancedSettingsShowMediaTimelineAlwaysHide),
kind: .selection(isSelected: context.timelineMediaVisibility == .never) { context.timelineMediaVisibility = .never })
} header: {
Text(L10n.screenAdvancedSettingsShowMediaTimelineTitle)
.compoundListSectionHeader()
} footer: {
Text(L10n.screenAdvancedSettingsShowMediaTimelineSubtitle)
.compoundListSectionFooter()
}
}
}
private extension AppAppearance {

View File

@@ -88,13 +88,21 @@ class TimelineViewModel: TimelineViewModelType, TimelineViewModelProtocol {
timelineControllerFactory: timelineControllerFactory,
clientProxy: clientProxy)
let hideTimelineMedia = switch appSettings.timelineMediaVisibility {
case .always:
false
case .privateOnly:
roomProxy.infoPublisher.value.isPublic
case .never:
true
}
super.init(initialViewState: TimelineViewState(timelineKind: timelineController.timelineKind,
roomID: roomProxy.id,
isDirectOneToOneRoom: roomProxy.isDirectOneToOneRoom,
timelineState: TimelineState(focussedEvent: focussedEventID.map { .init(eventID: $0, appearance: .immediate) }),
ownUserID: roomProxy.ownUserID,
isViewSourceEnabled: appSettings.viewSourceEnabled,
hideTimelineMedia: appSettings.hideTimelineMedia,
hideTimelineMedia: hideTimelineMedia,
pinnedEventIDs: roomProxy.infoPublisher.value.pinnedEventIDs,
emojiProvider: emojiProvider,
mapTilerConfiguration: appSettings.mapTilerConfiguration,
@@ -519,7 +527,21 @@ class TimelineViewModel: TimelineViewModelType, TimelineViewModelProtocol {
.weakAssign(to: \.state.isViewSourceEnabled, on: self)
.store(in: &cancellables)
appSettings.$hideTimelineMedia
appSettings.$timelineMediaVisibility
.combineLatest(roomProxy.infoPublisher
.map(\.isPublic)
.removeDuplicates()
.receive(on: DispatchQueue.main))
.map { timelineMediaVisibility, isPublic in
switch timelineMediaVisibility {
case .always:
false
case .privateOnly:
isPublic
case .never:
true
}
}
.weakAssign(to: \.state.hideTimelineMedia, on: self)
.store(in: &cancellables)
}

View File

@@ -106,7 +106,9 @@ struct NotificationContentBuilder {
let displayName = notificationItem.senderDisplayName ?? notificationItem.roomDisplayName
notification.body = String(messageEventStringBuilder.buildAttributedString(for: messageType, senderDisplayName: displayName).characters)
guard !settings.hideTimelineMedia else { return notification }
// For now we are fine hiding all images if the visibility is not `always` while we wait for an `isPublic` flag
// to be implemented in the SDK.
guard settings.timelineMediaVisibility == .always else { return notification }
switch messageType {
case .image(content: let content):