Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion Sources/WordPressData/Objective-C/include/Blog.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ NS_ASSUME_NONNULL_BEGIN
@class PublicizeInfo;
@class BlobEntity;
@class PostCategory;
@class PublicizeConnection;

extern NSString * const BlogEntityName;
extern NSString * const PostFormatStandard;
Expand Down Expand Up @@ -136,7 +137,7 @@ typedef NS_ENUM(NSInteger, SiteVisibility) {
@property (nonatomic, strong, readwrite, nullable) NSSet<PostCategory *> *categories;
@property (nonatomic, strong, readwrite, nullable) NSSet *tags;
@property (nonatomic, strong, readwrite, nullable) NSSet *comments;
@property (nonatomic, strong, readwrite, nullable) NSSet *connections;
@property (nonatomic, strong, readwrite, nullable) NSSet<PublicizeConnection *> *connections;
@property (nonatomic, strong, readwrite, nullable) NSSet *inviteLinks;
@property (nonatomic, strong, readwrite, nullable) NSSet *domains;
@property (nonatomic, strong, readwrite, nullable) NSSet *themes;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import WordPressUI

struct JetpackSocialNoConnectionView: View {

private let viewModel: JetpackSocialNoConnectionViewModel
let viewModel: JetpackSocialNoConnectionViewModel

var body: some View {
VStack(alignment: .leading, spacing: 12.0) {
Expand Down
44 changes: 44 additions & 0 deletions WordPress/Classes/ViewRelated/Post/PostSettings/PostSettings.swift
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ struct PostSettings: Hashable {
// MARK: - Post-specific
var postFormat: String?
var isStickyPost = false
var publicizeMessage: String?
var disabledPublicizeConnectionKeyringIDs: Set<Int> = []

// MARK: - Page-specific
var parentPageID: Int?
Expand Down Expand Up @@ -57,6 +59,17 @@ struct PostSettings: Hashable {
categoryIDs = Set((post.categories ?? []).compactMap {
$0.categoryID?.intValue
})
publicizeMessage = post.publicizeMessage

// Extract disabled connection keyring IDs
if let disabledConnections = post.disabledPublicizeConnections {
disabledPublicizeConnectionKeyringIDs = Set(disabledConnections.compactMap { keyringID, entry in
guard entry[Post.Constants.publicizeValueKey] == Post.Constants.publicizeDisabledValue else {
return nil
}
return keyringID.intValue
})
}
case let page as Page:
parentPageID = page.parentID?.intValue
default:
Expand Down Expand Up @@ -129,6 +142,37 @@ struct PostSettings: Hashable {
if post.isStickyPost != isStickyPost {
post.isStickyPost = isStickyPost
}

// Update publicize message
if post.publicizeMessage != publicizeMessage {
post.publicizeMessage = publicizeMessage
}

// Update disabled publicize connections
if let disabledConnections = post.disabledPublicizeConnections {
// Get current disabled keyring IDs
let currentDisabledKeyringIDs = Set(disabledConnections.compactMap { keyringID, entry in
guard entry[Post.Constants.publicizeValueKey] == Post.Constants.publicizeDisabledValue else {
return nil
}
return keyringID.intValue
})

// Enable connections that were disabled but are now enabled
for keyringID in currentDisabledKeyringIDs.subtracting(disabledPublicizeConnectionKeyringIDs) {
post.enablePublicizeConnectionWithKeyringID(NSNumber(value: keyringID))
}

// Disable connections that were enabled but are now disabled
for keyringID in disabledPublicizeConnectionKeyringIDs.subtracting(currentDisabledKeyringIDs) {
post.disablePublicizeConnectionWithKeyringID(NSNumber(value: keyringID))
}
} else if !disabledPublicizeConnectionKeyringIDs.isEmpty {
// If there were no disabled connections before, disable the ones in settings
for keyringID in disabledPublicizeConnectionKeyringIDs {
post.disablePublicizeConnectionWithKeyringID(NSNumber(value: keyringID))
}
}
}

// Apply page-specific settings
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ private struct PostSettingsView: View {
taxonomySection
}
excerptSection
socialSharingSection
moreOptionsSection
}
.disabled(viewModel.isSaving)
Expand Down Expand Up @@ -231,6 +232,15 @@ private struct PostSettingsView: View {
}
}

// MARK: - "Jetpack Social" Section

@ViewBuilder
private var socialSharingSection: some View {
if let socialViewModel = viewModel.socialSharingViewModel {
PostSettingsSocialSection(viewModel: socialViewModel)
}
}

// MARK: - "More Options" Section

@ViewBuilder
Expand Down Expand Up @@ -376,6 +386,21 @@ private struct SettingsTextFieldView: View {
}
}

@MainActor
private struct PostSettingsSocialSection: View {
@ObservedObject var viewModel: PostSettingsSocialSharingViewModel

var body: some View {
if !viewModel.isHidden {
Section {
PostSettingsSocialSharingRow(viewModel: viewModel)
} header: {
Text(Strings.jetpackSocialHeader)
}
}
}
}

private enum Strings {
static let generalHeader = NSLocalizedString(
"postSettings.section.general",
Expand Down Expand Up @@ -496,4 +521,10 @@ private enum Strings {
value: "The slug is the URL-friendly version of the post title.",
comment: "Hint text for the slug field. Should be the same as the text displayed if the user clicks the (i) in Slug in Calypso."
)

static let jetpackSocialHeader = NSLocalizedString(
"postSettings.jetpackSocial.header",
value: "Jetpack Social",
comment: "Label for the Jetpack Social section in post Settings. Should be the same as WP core."
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ final class PostSettingsViewModel: ObservableObject {
let post: AbstractPost
let isStandalone: Bool
let featuredImageViewModel: PostSettingsFeaturedImageViewModel
private(set) var socialSharingViewModel: PostSettingsSocialSharingViewModel?

@Published var settings: PostSettings {
didSet {
Expand Down Expand Up @@ -94,7 +95,11 @@ final class PostSettingsViewModel: ObservableObject {

/// Weak reference to the view controller for navigation.
/// This is temporary until we can fully migrate to SwiftUI navigation.
weak var viewController: UIViewController?
weak var viewController: UIViewController? {
didSet {
socialSharingViewModel?.viewController = viewController
}
}

init(post: AbstractPost, isStandalone: Bool = false) {
self.post = post
Expand All @@ -116,8 +121,31 @@ final class PostSettingsViewModel: ObservableObject {
// Initialize cached text values
refresh(with: settings)

// Initialize social sharing view model if this is a post
if let post = post as? Post {
setupSocialSharingViewModel(post: post)
}

WPAnalytics.track(.postSettingsShown)
}

private func setupSocialSharingViewModel(post: Post) {
// Create a binding to settings that the social sharing view model can use
let settingsBinding = Binding<PostSettings>(
get: { [weak self] in
self?.settings ?? PostSettings(from: post)
},
set: { [weak self] newValue in
self?.settings = newValue
}
)

socialSharingViewModel = PostSettingsSocialSharingViewModel(
blog: post.blog,
settings: settingsBinding
)
socialSharingViewModel?.viewController = viewController
}

private func refresh(with settings: PostSettings) {
hasChanges = settings != originalSettings
Expand Down Expand Up @@ -194,6 +222,9 @@ final class PostSettingsViewModel: ObservableObject {
settings.status = .publishPrivate
}
settings.password = selection.password.isEmpty ? nil : selection.password

// Refresh social sharing when visibility changes
socialSharingViewModel?.refresh()
}

// MARK: - Navigation
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import SwiftUI
import WordPressData

@MainActor
struct PostSettingsSocialAccountsView: UIViewControllerRepresentable {
let blogID: Int
let model: PrepublishingAutoSharingModel
weak var delegate: PrepublishingSocialAccountsDelegate?
let coreDataStack: CoreDataStackSwift

func makeUIViewController(context: Context) -> PrepublishingSocialAccountsViewController {
PrepublishingSocialAccountsViewController(
blogID: blogID,
model: model,
delegate: delegate,
coreDataStack: coreDataStack
)
}

func updateUIViewController(_ uiViewController: PrepublishingSocialAccountsViewController, context: Context) {
// No updates needed
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import SwiftUI
import WordPressUI

@MainActor
struct PostSettingsSocialSharingRow: View {
@ObservedObject var viewModel: PostSettingsSocialSharingViewModel

var body: some View {
switch viewModel.state {
case .noConnection(let viewModel):
JetpackSocialNoConnectionView(viewModel: viewModel)
case .hasConnections(let viewModel):
autoSharingView(viewModel: viewModel)
case .hidden:
EmptyView()
}
}

@ViewBuilder
private func autoSharingView(viewModel model: PrepublishingAutoSharingModel) -> some View {
NavigationLink {
PostSettingsSocialAccountsView(
blogID: viewModel.blogID ?? 0,
model: model,
delegate: viewModel,
coreDataStack: viewModel.coreDataStack
)
.ignoresSafeArea()
} label: {
PrepublishingAutoSharingView(model: model)
}
}
}
Loading