commit b5a81e2586cb8c20549f40137d7de97c04b49af3
parent 9e0b9debb457424433066d06798b2ad4d93ba0be
Author: Daniel D’Aquino <daniel@daquino.me>
Date: Wed, 18 Sep 2024 19:14:07 -0700
Merge branch 'release_1.10'
Diffstat:
15 files changed, 76 insertions(+), 42 deletions(-)
diff --git a/damus/Components/SupporterBadge.swift b/damus/Components/SupporterBadge.swift
@@ -11,11 +11,13 @@ struct SupporterBadge: View {
let percent: Int?
let purple_account: DamusPurple.Account?
let style: Style
+ let text_color: Color
- init(percent: Int?, purple_account: DamusPurple.Account? = nil, style: Style) {
+ init(percent: Int?, purple_account: DamusPurple.Account? = nil, style: Style, text_color: Color = .secondary) {
self.percent = percent
self.purple_account = purple_account
self.style = style
+ self.text_color = text_color
}
let size: CGFloat = 17
@@ -31,7 +33,7 @@ struct SupporterBadge: View {
if self.style == .full {
let date = format_date(date: purple_account.created_at, time_style: .none)
Text(date)
- .foregroundStyle(.secondary)
+ .foregroundStyle(text_color)
.font(.caption)
}
}
diff --git a/damus/ContentView.swift b/damus/ContentView.swift
@@ -77,7 +77,12 @@ struct ContentView: View {
@State var active_sheet: Sheets? = nil
@State var damus_state: DamusState!
- @SceneStorage("ContentView.selected_timeline") var selected_timeline: Timeline = .home
+ @State var menu_subtitle: String? = nil
+ @SceneStorage("ContentView.selected_timeline") var selected_timeline: Timeline = .home {
+ willSet {
+ self.menu_subtitle = nil
+ }
+ }
@State var muting: MuteItem? = nil
@State var confirm_mute: Bool = false
@State var hide_bar: Bool = false
@@ -101,9 +106,16 @@ struct ContentView: View {
isSideBarOpened = false
}
- var timelineNavItem: Text {
- return Text(timeline_name(selected_timeline))
- .bold()
+ var timelineNavItem: some View {
+ VStack {
+ Text(timeline_name(selected_timeline))
+ .bold()
+ if let menu_subtitle {
+ Text(menu_subtitle)
+ .font(.caption)
+ .foregroundStyle(.secondary)
+ }
+ }
}
func MainContent(damus: DamusState) -> some View {
@@ -122,7 +134,7 @@ struct ContentView: View {
PostingTimelineView(damus_state: damus_state!, home: home, active_sheet: $active_sheet)
case .notifications:
- NotificationsView(state: damus, notifications: home.notifications)
+ NotificationsView(state: damus, notifications: home.notifications, subtitle: $menu_subtitle)
case .dms:
DirectMessagesView(damus_state: damus_state!, model: damus_state!.dms, settings: damus_state!.settings)
diff --git a/damus/Models/FriendFilter.swift b/damus/Models/FriendFilter.swift
@@ -9,7 +9,7 @@ import Foundation
enum FriendFilter: String, StringCodable {
case all
- case friends
+ case friends_of_friends
init?(from string: String) {
guard let ff = FriendFilter(rawValue: string) else {
@@ -27,8 +27,17 @@ enum FriendFilter: String, StringCodable {
switch self {
case .all:
return true
- case .friends:
+ case .friends_of_friends:
return contacts.is_in_friendosphere(pubkey)
}
}
+
+ func description() -> String {
+ switch self {
+ case .all:
+ return NSLocalizedString("All", comment: "Human-readable short description of the 'friends filter' when it is set to 'all'")
+ case .friends_of_friends:
+ return NSLocalizedString("Friends of friends", comment: "Human-readable short description of the 'friends filter' when it is set to 'friends-of-friends'")
+ }
+ }
}
diff --git a/damus/Models/NotificationsManager.swift b/damus/Models/NotificationsManager.swift
@@ -27,7 +27,7 @@ func process_local_notification(state: HeadlessDamusState, event ev: NostrEvent)
func should_display_notification(state: HeadlessDamusState, event ev: NostrEvent, mode: UserSettingsStore.NotificationsMode) -> Bool {
// Do not show notification if it's coming from a mode different from the one selected by our user
- guard state.settings.notifications_mode == mode else {
+ guard state.settings.notification_mode == mode else {
return false
}
diff --git a/damus/Models/Post.swift b/damus/Models/Post.swift
@@ -51,7 +51,7 @@ struct NostrPost {
}
/// Parse the post's contents to find more tags to apply to the final nostr event
- private func make_post_tags(post_blocks: [Block], tags: [[String]]) -> PostTags {
+ func make_post_tags(post_blocks: [Block], tags: [[String]]) -> PostTags {
var new_tags = tags
for post_block in post_blocks {
@@ -89,10 +89,12 @@ struct NostrPost {
// MARK: - Helper structures and functions
-/// A struct used for temporarily holding tag information that was parsed from a post contents to aid in building a nostr event
-fileprivate struct PostTags {
- let blocks: [Block]
- let tags: [[String]]
+extension NostrPost {
+ /// A struct used for temporarily holding tag information that was parsed from a post contents to aid in building a nostr event
+ struct PostTags {
+ let blocks: [Block]
+ let tags: [[String]]
+ }
}
func parse_post_blocks(content: String) -> [Block] {
diff --git a/damus/Models/PushNotificationClient.swift b/damus/Models/PushNotificationClient.swift
@@ -18,7 +18,7 @@ struct PushNotificationClient {
mutating func set_device_token(new_device_token: Data) async throws {
self.device_token = new_device_token
- if settings.enable_experimental_push_notifications && settings.notifications_mode == .push {
+ if settings.enable_push_notifications && settings.notification_mode == .push {
try await self.send_token()
}
}
diff --git a/damus/Models/UserSettingsStore.swift b/damus/Models/UserSettingsStore.swift
@@ -155,8 +155,8 @@ class UserSettingsStore: ObservableObject {
@Setting(key: "like_notification", default_value: true)
var like_notification: Bool
- @StringSetting(key: "notifications_mode", default_value: .local)
- var notifications_mode: NotificationsMode
+ @StringSetting(key: "notification_mode", default_value: .push)
+ var notification_mode: NotificationsMode
@Setting(key: "notification_only_from_following", default_value: false)
var notification_only_from_following: Bool
@@ -207,8 +207,9 @@ class UserSettingsStore: ObservableObject {
@Setting(key: "always_show_onboarding_suggestions", default_value: false)
var always_show_onboarding_suggestions: Bool
- @Setting(key: "enable_experimental_push_notifications", default_value: false)
- var enable_experimental_push_notifications: Bool
+ // @Setting(key: "enable_experimental_push_notifications", default_value: false)
+ // This was a feature flag setting during early development, but now this is enabled for everyone.
+ var enable_push_notifications: Bool = true
@StringSetting(key: "push_notification_environment", default_value: .production)
var push_notification_environment: PushNotificationClient.Environment
diff --git a/damus/Views/Buttons/FriendsButton.swift b/damus/Views/Buttons/FriendsButton.swift
@@ -14,12 +14,12 @@ struct FriendsButton: View {
Button(action: {
switch self.filter {
case .all:
- self.filter = .friends
- case .friends:
+ self.filter = .friends_of_friends
+ case .friends_of_friends:
self.filter = .all
}
}) {
- if filter == .friends {
+ if filter == .friends_of_friends {
LINEAR_GRADIENT
.mask(Image("user-added")
.resizable()
@@ -28,7 +28,7 @@ struct FriendsButton: View {
Image("user-added")
.resizable()
.frame(width: 28, height: 28)
- .foregroundColor(DamusColors.adaptableGrey)
+ .foregroundColor(.gray)
}
}
.buttonStyle(.plain)
diff --git a/damus/Views/DirectMessagesView.swift b/damus/Views/DirectMessagesView.swift
@@ -103,7 +103,7 @@ struct DirectMessagesView: View {
func would_filter_non_friends_from_dms(contacts: Contacts, dms: [DirectMessageModel]) -> Bool {
for dm in dms {
- if !FriendFilter.friends.filter(contacts: contacts, pubkey: dm.pubkey) {
+ if !FriendFilter.friends_of_friends.filter(contacts: contacts, pubkey: dm.pubkey) {
return true
}
}
diff --git a/damus/Views/NoteContentView.swift b/damus/Views/NoteContentView.swift
@@ -120,8 +120,7 @@ struct NoteContentView: View {
EventView(damus: damus_state, event: self.event, options: .embedded_text_only)
.padding(.top)
}
- .background(.thinMaterial)
- .preferredColorScheme(.dark)
+ .background(.thickMaterial)
.onTapGesture(perform: {
damus_state.nav.push(route: Route.Thread(thread: .init(event: self.event, damus_state: damus_state)))
dismiss()
diff --git a/damus/Views/Notifications/NotificationsView.swift b/damus/Views/Notifications/NotificationsView.swift
@@ -56,6 +56,7 @@ struct NotificationsView: View {
@ObservedObject var notifications: NotificationsModel
@StateObject var filter = NotificationFilter()
@SceneStorage("NotificationsView.filter_state") var filter_state: NotificationFilterState = .all
+ @Binding var subtitle: String?
@Environment(\.colorScheme) var colorScheme
@@ -100,6 +101,15 @@ struct NotificationsView: View {
}
.toolbar {
ToolbarItem(placement: .navigationBarTrailing) {
+ Button(
+ action: { state.nav.push(route: Route.NotificationSettings(settings: state.settings)) },
+ label: {
+ Image("settings")
+ .foregroundColor(.gray)
+ }
+ )
+ }
+ ToolbarItem(placement: .navigationBarTrailing) {
if would_filter_non_friends_from_notifications(contacts: state.contacts, state: filter_state, items: self.notifications.notifications) {
FriendsButton(filter: $filter.fine_filter)
}
@@ -107,12 +117,14 @@ struct NotificationsView: View {
}
.onChange(of: filter.fine_filter) { val in
state.settings.friend_filter = val
+ self.subtitle = filter.fine_filter.description()
}
.onChange(of: filter_state) { val in
filter.state = val
}
.onAppear {
self.filter.fine_filter = state.settings.friend_filter
+ self.subtitle = filter.fine_filter.description()
filter.state = filter_state
}
.safeAreaInset(edge: .top, spacing: 0) {
@@ -163,7 +175,7 @@ struct NotificationsView: View {
struct NotificationsView_Previews: PreviewProvider {
static var previews: some View {
- NotificationsView(state: test_damus_state, notifications: NotificationsModel(), filter: NotificationFilter())
+ NotificationsView(state: test_damus_state, notifications: NotificationsModel(), filter: NotificationFilter(), subtitle: .constant(nil))
}
}
@@ -174,7 +186,7 @@ func would_filter_non_friends_from_notifications(contacts: Contacts, state: Noti
continue
}
- if item.would_filter({ ev in FriendFilter.friends.filter(contacts: contacts, pubkey: ev.pubkey) }) {
+ if item.would_filter({ ev in FriendFilter.friends_of_friends.filter(contacts: contacts, pubkey: ev.pubkey) }) {
return true
}
}
diff --git a/damus/Views/Purple/DamusPurpleAccountView.swift b/damus/Views/Purple/DamusPurpleAccountView.swift
@@ -64,7 +64,6 @@ struct DamusPurpleAccountView: View {
.padding(.bottom, 20)
}
.foregroundColor(.white.opacity(0.8))
- .preferredColorScheme(.dark)
.background(.ultraThinMaterial, in: RoundedRectangle(cornerRadius: 12, style: .continuous))
.padding()
}
@@ -81,7 +80,8 @@ struct DamusPurpleAccountView: View {
SupporterBadge(
percent: nil,
purple_account: account,
- style: .full
+ style: .full,
+ text_color: .white
)
}
}
diff --git a/damus/Views/Settings/DeveloperSettingsView.swift b/damus/Views/Settings/DeveloperSettingsView.swift
@@ -18,10 +18,6 @@ struct DeveloperSettingsView: View {
.toggleStyle(.switch)
if settings.developer_mode {
Toggle(NSLocalizedString("Always show onboarding", comment: "Developer mode setting to always show onboarding suggestions."), isOn: $settings.always_show_onboarding_suggestions)
-
- Toggle(NSLocalizedString("Enable experimental push notifications", comment: "Developer mode setting to enable experimental push notifications."), isOn: $settings.enable_experimental_push_notifications)
- .toggleStyle(.switch)
-
Picker(NSLocalizedString("Push notification environment", comment: "Prompt selection of the Push notification environment (Developer feature to switch between real/production mode to test modes)."),
selection: Binding(
get: { () -> PushNotificationClient.Environment in
diff --git a/damus/Views/Settings/NotificationSettingsView.swift b/damus/Views/Settings/NotificationSettingsView.swift
@@ -36,7 +36,7 @@ struct NotificationSettingsView: View {
do {
try await damus_state.push_notification_client.send_token()
await self.sync_up_remote_notification_settings()
- settings.notifications_mode = new_value
+ settings.notification_mode = new_value
}
catch {
notification_mode_setting_error = String(format: NSLocalizedString("Error configuring push notifications with the server: %@", comment: "Error label shown when user tries to enable push notifications but something fails"), error.localizedDescription)
@@ -47,7 +47,7 @@ struct NotificationSettingsView: View {
Task {
do {
try await damus_state.push_notification_client.revoke_token()
- settings.notifications_mode = new_value
+ settings.notification_mode = new_value
notification_preferences_sync_state = .not_applicable
}
catch {
@@ -67,7 +67,7 @@ struct NotificationSettingsView: View {
set: { new_value in
let old_value = raw_binding.wrappedValue
raw_binding.wrappedValue = new_value
- if self.settings.notifications_mode == .push {
+ if self.settings.notification_mode == .push {
Task {
await self.send_push_notification_preferences(on_failure: {
raw_binding.wrappedValue = old_value
@@ -114,7 +114,7 @@ struct NotificationSettingsView: View {
var body: some View {
Form {
- if settings.enable_experimental_push_notifications {
+ if settings.enable_push_notifications {
Section(
header: Text("General", comment: "Section header for general damus notifications user configuration"),
footer: VStack {
@@ -126,7 +126,7 @@ struct NotificationSettingsView: View {
) {
Picker(NSLocalizedString("Notifications mode", comment: "Prompt selection of the notification mode (Feature to switch between local notifications (generated from user's own phone) or push notifications (generated by Damus server)."),
selection: Binding(
- get: { settings.notifications_mode },
+ get: { settings.notification_mode },
set: { newValue in
self.try_to_set_notifications_mode(new_value: newValue)
}
@@ -194,7 +194,7 @@ struct NotificationSettingsView: View {
}
.onAppear(perform: {
Task {
- if self.settings.notifications_mode == .push {
+ if self.settings.notification_mode == .push {
await self.sync_up_remote_notification_settings()
}
}
diff --git a/damusTests/ReplyTests.swift b/damusTests/ReplyTests.swift
@@ -57,7 +57,8 @@ class ReplyTests: XCTestCase {
let ev = NostrEvent(content: content, keypair: test_keypair, tags: [])!
let blocks = parse_note_content(content: .init(note: ev, keypair: test_keypair)).blocks
let post_blocks = parse_post_blocks(content: content)
- let post_tags = make_post_tags(post_blocks: post_blocks, tags: [])
+ let post = NostrPost(content: content, kind: NostrKind.text, tags: [])
+ let post_tags = post.make_post_tags(post_blocks: post_blocks, tags: [])
let tr = interpret_event_refs(tags: ev.tags)
XCTAssertNil(tr)