From 7a1b1ef5e358d237ccdbd2c88a6f8d9050c10735 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 12:51:10 +0100 Subject: [PATCH 1/8] Theme + Config --- .../RichTextCoordinator+Subscriptions.swift | 2 +- Sources/RichTextKit/RichTextView+Config.swift | 27 ++++++++++- Sources/RichTextKit/RichTextView+Theme.swift | 48 +++++++++++++++++++ Sources/RichTextKit/RichTextView_AppKit.swift | 21 ++++++++ Sources/RichTextKit/RichTextView_UIKit.swift | 24 ++++++++-- 5 files changed, 115 insertions(+), 7 deletions(-) create mode 100644 Sources/RichTextKit/RichTextView+Theme.swift diff --git a/Sources/RichTextKit/Coordinator/RichTextCoordinator+Subscriptions.swift b/Sources/RichTextKit/Coordinator/RichTextCoordinator+Subscriptions.swift index 758cd0b01..8cbef2bc5 100644 --- a/Sources/RichTextKit/Coordinator/RichTextCoordinator+Subscriptions.swift +++ b/Sources/RichTextKit/Coordinator/RichTextCoordinator+Subscriptions.swift @@ -191,7 +191,7 @@ extension RichTextCoordinator { extension ColorRepresentable { #if iOS || os(tvOS) || os(visionOS) - static var textColor: ColorRepresentable { .label } + public static var textColor: ColorRepresentable { .label } #endif } #endif diff --git a/Sources/RichTextKit/RichTextView+Config.swift b/Sources/RichTextKit/RichTextView+Config.swift index fc250f8e2..76b63e08e 100644 --- a/Sources/RichTextKit/RichTextView+Config.swift +++ b/Sources/RichTextKit/RichTextView+Config.swift @@ -22,14 +22,39 @@ public extension RichTextView { - Parameters: - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. */ + #if iOS || os(tvOS) || os(visionOS) public init( - isScrollingEnabled: Bool = true + isScrollingEnabled: Bool = true, + allowsEditingTextAttributes: Bool = true, + autocapitalizationType: UITextAutocapitalizationType = .sentences, + spellCheckingType: UITextSpellCheckingType = .default + ) { self.isScrollingEnabled = isScrollingEnabled + self.allowsEditingTextAttributes = allowsEditingTextAttributes + self.autocapitalizationType = autocapitalizationType + self.spellCheckingType = spellCheckingType } /// Whether or not the editor should scroll. public var isScrollingEnabled: Bool + public var allowsEditingTextAttributes: Bool + public var autocapitalizationType: UITextAutocapitalizationType + public var spellCheckingType: UITextSpellCheckingType + + #else + public init( + isScrollingEnabled: Bool = true, + isContinuousSpellCheckingEnabled: Bool = true + ) { + self.isScrollingEnabled = isScrollingEnabled + self.isContinuousSpellCheckingEnabled = isContinuousSpellCheckingEnabled + } + + /// Whether or not the editor should scroll. + public var isScrollingEnabled: Bool + public var isContinuousSpellCheckingEnabled: Bool + #endif } } diff --git a/Sources/RichTextKit/RichTextView+Theme.swift b/Sources/RichTextKit/RichTextView+Theme.swift new file mode 100644 index 000000000..ad7376bff --- /dev/null +++ b/Sources/RichTextKit/RichTextView+Theme.swift @@ -0,0 +1,48 @@ +// +// RichTextView+Theme.swift +// RichTextKit +// +// Created by Dominik Bucher on 13.02.2024. +// + +#if iOS || macOS || os(tvOS) || os(visionOS) +import SwiftUI + +public extension RichTextView { + + /** + This type can be used to configure a ``RichTextEditor``'s current color properties. + */ + struct Theme { + + /** + Create a custom configuration. + + - Parameters: + - font: default `.systemFont` of point size `16` (this differs on iOS and macOS). + - fontColor: default `.textColor`. + - backgroundColor: Color of whole textView default `.clear`. + */ + public init( + font: FontRepresentable = .systemFont(ofSize: 16), + fontColor: ColorRepresentable = .textColor, + backgroundColor: ColorRepresentable = .clear + ) { + self.font = font + self.fontColor = fontColor + self.backgroundColor = backgroundColor + } + + public let font: FontRepresentable + public let fontColor: ColorRepresentable + public let backgroundColor: ColorRepresentable + } +} + +public extension RichTextView.Theme { + + /// Get a standard rich text editor configuration. + static var standard: Self { .init() } +} +#endif + diff --git a/Sources/RichTextKit/RichTextView_AppKit.swift b/Sources/RichTextKit/RichTextView_AppKit.swift index 49c4a7b19..40136f91c 100644 --- a/Sources/RichTextKit/RichTextView_AppKit.swift +++ b/Sources/RichTextKit/RichTextView_AppKit.swift @@ -29,6 +29,13 @@ open class RichTextView: NSTextView, RichTextViewComponent { /// The configuration to use by the rich text view. public var configuration: Configuration = .standard + + /// Theme for rich text view. + public var theme: Theme = .standard { + didSet { + setupTheme() + } + } /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -118,6 +125,20 @@ open class RichTextView: NSTextView, RichTextViewComponent { imageConfiguration = standardImageConfiguration(for: format) layoutManager?.defaultAttachmentScaling = NSImageScaling.scaleProportionallyDown setContentCompressionResistancePriority(.defaultLow, for: .horizontal) + setupTheme() + setupConfiguration() + } + + // MARK: - Internal + + func setupTheme() { + font = theme.font + textColor = theme.fontColor + backgroundColor = theme.backgroundColor + } + + func setupConfiguration() { + isContinuousSpellCheckingEnabled = configuration.isContinuousSpellCheckingEnabled } // MARK: - Open Functionality diff --git a/Sources/RichTextKit/RichTextView_UIKit.swift b/Sources/RichTextKit/RichTextView_UIKit.swift index 436317e44..96c312d0e 100644 --- a/Sources/RichTextKit/RichTextView_UIKit.swift +++ b/Sources/RichTextKit/RichTextView_UIKit.swift @@ -50,6 +50,15 @@ open class RichTextView: UITextView, RichTextViewComponent { public var configuration: Configuration = .standard { didSet { isScrollEnabled = configuration.isScrollingEnabled + allowsEditingTextAttributes = configuration.allowsEditingTextAttributes + autocapitalizationType = configuration.autocapitalizationType + spellCheckingType = configuration.spellCheckingType + } + } + + public var theme: Theme = .standard { + didSet { + setupTheme() } } @@ -158,17 +167,22 @@ open class RichTextView: UITextView, RichTextViewComponent { imageConfiguration = standardImageConfiguration(for: format) text.autosizeImageAttachments(maxSize: imageAttachmentMaxSize) attributedString = text - allowsEditingTextAttributes = false - autocapitalizationType = .sentences - backgroundColor = .clear richTextDataFormat = format - spellCheckingType = .no trySetupInitialTextColor(for: text) { textColor = .label } setContentCompressionResistancePriority(.defaultLow, for: .horizontal) + setupTheme() } - + + // MARK: - Internal + + func setupTheme() { + font = theme.font + textColor = theme.fontColor + backgroundColor = theme.backgroundColor + } + // MARK: - Open Functionality /// Alert a certain title and message. From 6e4f9cf0ab3761d2e26fcc7c268f7ff171600ce1 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 12:52:28 +0100 Subject: [PATCH 2/8] Only Configuration --- Demo/Demo.xcodeproj/project.pbxproj | 16 +++---- Sources/RichTextKit/RichTextView+Theme.swift | 48 ------------------- Sources/RichTextKit/RichTextView_AppKit.swift | 14 ------ Sources/RichTextKit/RichTextView_UIKit.swift | 17 +------ 4 files changed, 9 insertions(+), 86 deletions(-) delete mode 100644 Sources/RichTextKit/RichTextView+Theme.swift diff --git a/Demo/Demo.xcodeproj/project.pbxproj b/Demo/Demo.xcodeproj/project.pbxproj index e5ae69a9e..ce34b4ed5 100644 --- a/Demo/Demo.xcodeproj/project.pbxproj +++ b/Demo/Demo.xcodeproj/project.pbxproj @@ -415,7 +415,7 @@ CODE_SIGN_ENTITLEMENTS = "Demo (iOS).entitlements"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; - DEVELOPMENT_TEAM = PMEDFW438U; + DEVELOPMENT_TEAM = J4CAUDX828; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; @@ -429,7 +429,7 @@ "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = iphoneos; SUPPORTED_PLATFORMS = "iphoneos iphonesimulator"; @@ -449,7 +449,7 @@ CODE_SIGN_ENTITLEMENTS = "Demo (iOS).entitlements"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; - DEVELOPMENT_TEAM = PMEDFW438U; + DEVELOPMENT_TEAM = J4CAUDX828; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; @@ -463,7 +463,7 @@ "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = iphoneos; SUPPORTED_PLATFORMS = "iphoneos iphonesimulator"; @@ -486,7 +486,7 @@ COMBINE_HIDPI_IMAGES = YES; CURRENT_PROJECT_VERSION = 1; DEAD_CODE_STRIPPING = YES; - DEVELOPMENT_TEAM = PMEDFW438U; + DEVELOPMENT_TEAM = J4CAUDX828; ENABLE_HARDENED_RUNTIME = YES; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; @@ -497,7 +497,7 @@ ); MACOSX_DEPLOYMENT_TARGET = 12.0; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = macosx; SWIFT_EMIT_LOC_STRINGS = YES; @@ -515,7 +515,7 @@ COMBINE_HIDPI_IMAGES = YES; CURRENT_PROJECT_VERSION = 1; DEAD_CODE_STRIPPING = YES; - DEVELOPMENT_TEAM = PMEDFW438U; + DEVELOPMENT_TEAM = J4CAUDX828; ENABLE_HARDENED_RUNTIME = YES; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; @@ -526,7 +526,7 @@ ); MACOSX_DEPLOYMENT_TARGET = 12.0; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = macosx; SWIFT_EMIT_LOC_STRINGS = YES; diff --git a/Sources/RichTextKit/RichTextView+Theme.swift b/Sources/RichTextKit/RichTextView+Theme.swift deleted file mode 100644 index ad7376bff..000000000 --- a/Sources/RichTextKit/RichTextView+Theme.swift +++ /dev/null @@ -1,48 +0,0 @@ -// -// RichTextView+Theme.swift -// RichTextKit -// -// Created by Dominik Bucher on 13.02.2024. -// - -#if iOS || macOS || os(tvOS) || os(visionOS) -import SwiftUI - -public extension RichTextView { - - /** - This type can be used to configure a ``RichTextEditor``'s current color properties. - */ - struct Theme { - - /** - Create a custom configuration. - - - Parameters: - - font: default `.systemFont` of point size `16` (this differs on iOS and macOS). - - fontColor: default `.textColor`. - - backgroundColor: Color of whole textView default `.clear`. - */ - public init( - font: FontRepresentable = .systemFont(ofSize: 16), - fontColor: ColorRepresentable = .textColor, - backgroundColor: ColorRepresentable = .clear - ) { - self.font = font - self.fontColor = fontColor - self.backgroundColor = backgroundColor - } - - public let font: FontRepresentable - public let fontColor: ColorRepresentable - public let backgroundColor: ColorRepresentable - } -} - -public extension RichTextView.Theme { - - /// Get a standard rich text editor configuration. - static var standard: Self { .init() } -} -#endif - diff --git a/Sources/RichTextKit/RichTextView_AppKit.swift b/Sources/RichTextKit/RichTextView_AppKit.swift index 40136f91c..3fb356227 100644 --- a/Sources/RichTextKit/RichTextView_AppKit.swift +++ b/Sources/RichTextKit/RichTextView_AppKit.swift @@ -30,13 +30,6 @@ open class RichTextView: NSTextView, RichTextViewComponent { /// The configuration to use by the rich text view. public var configuration: Configuration = .standard - /// Theme for rich text view. - public var theme: Theme = .standard { - didSet { - setupTheme() - } - } - /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -125,18 +118,11 @@ open class RichTextView: NSTextView, RichTextViewComponent { imageConfiguration = standardImageConfiguration(for: format) layoutManager?.defaultAttachmentScaling = NSImageScaling.scaleProportionallyDown setContentCompressionResistancePriority(.defaultLow, for: .horizontal) - setupTheme() setupConfiguration() } // MARK: - Internal - func setupTheme() { - font = theme.font - textColor = theme.fontColor - backgroundColor = theme.backgroundColor - } - func setupConfiguration() { isContinuousSpellCheckingEnabled = configuration.isContinuousSpellCheckingEnabled } diff --git a/Sources/RichTextKit/RichTextView_UIKit.swift b/Sources/RichTextKit/RichTextView_UIKit.swift index 96c312d0e..63bf0ab7d 100644 --- a/Sources/RichTextKit/RichTextView_UIKit.swift +++ b/Sources/RichTextKit/RichTextView_UIKit.swift @@ -55,12 +55,6 @@ open class RichTextView: UITextView, RichTextViewComponent { spellCheckingType = configuration.spellCheckingType } } - - public var theme: Theme = .standard { - didSet { - setupTheme() - } - } /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -172,17 +166,8 @@ open class RichTextView: UITextView, RichTextViewComponent { textColor = .label } setContentCompressionResistancePriority(.defaultLow, for: .horizontal) - setupTheme() } - - // MARK: - Internal - - func setupTheme() { - font = theme.font - textColor = theme.fontColor - backgroundColor = theme.backgroundColor - } - + // MARK: - Open Functionality /// Alert a certain title and message. From 6e24d66fe8591642ff1cc4d424af2968174c95d5 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 12:56:59 +0100 Subject: [PATCH 3/8] Separate stuff --- Sources/RichTextKit/RichTextView+Config.swift | 59 +------------------ .../RichTextView+Config_AppKit.swift | 31 ++++++++++ .../RichTextView+Config_UIKit.swift | 45 ++++++++++++++ 3 files changed, 79 insertions(+), 56 deletions(-) create mode 100644 Sources/RichTextKit/RichTextView+Config_AppKit.swift create mode 100644 Sources/RichTextKit/RichTextView+Config_UIKit.swift diff --git a/Sources/RichTextKit/RichTextView+Config.swift b/Sources/RichTextKit/RichTextView+Config.swift index 76b63e08e..c2ca3599c 100644 --- a/Sources/RichTextKit/RichTextView+Config.swift +++ b/Sources/RichTextKit/RichTextView+Config.swift @@ -1,66 +1,13 @@ // // RichTextView+Config.swift -// RichTextKit // -// Created by Daniel Saidi on 2024-01-16. -// Copyright © 2024 Daniel Saidi. All rights reserved. +// +// Created by Dominik Bucher on 13.02.2024. // -#if iOS || macOS || os(tvOS) || os(visionOS) -import SwiftUI - -public extension RichTextView { - - /** - This type can be used to configure a ``RichTextEditor``. - */ - struct Configuration { - - /** - Create a custom configuration. - - - Parameters: - - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. - */ - #if iOS || os(tvOS) || os(visionOS) - public init( - isScrollingEnabled: Bool = true, - allowsEditingTextAttributes: Bool = true, - autocapitalizationType: UITextAutocapitalizationType = .sentences, - spellCheckingType: UITextSpellCheckingType = .default - - ) { - self.isScrollingEnabled = isScrollingEnabled - self.allowsEditingTextAttributes = allowsEditingTextAttributes - self.autocapitalizationType = autocapitalizationType - self.spellCheckingType = spellCheckingType - } - - /// Whether or not the editor should scroll. - public var isScrollingEnabled: Bool - public var allowsEditingTextAttributes: Bool - public var autocapitalizationType: UITextAutocapitalizationType - public var spellCheckingType: UITextSpellCheckingType - - #else - public init( - isScrollingEnabled: Bool = true, - isContinuousSpellCheckingEnabled: Bool = true - ) { - self.isScrollingEnabled = isScrollingEnabled - self.isContinuousSpellCheckingEnabled = isContinuousSpellCheckingEnabled - } - - /// Whether or not the editor should scroll. - public var isScrollingEnabled: Bool - public var isContinuousSpellCheckingEnabled: Bool - #endif - } -} +import Foundation public extension RichTextView.Configuration { - /// Get a standard rich text editor configuration. static var standard: Self { .init() } } -#endif diff --git a/Sources/RichTextKit/RichTextView+Config_AppKit.swift b/Sources/RichTextKit/RichTextView+Config_AppKit.swift new file mode 100644 index 000000000..f650ca251 --- /dev/null +++ b/Sources/RichTextKit/RichTextView+Config_AppKit.swift @@ -0,0 +1,31 @@ +// +// RichTextView+Config_AppKit.swift +// +// +// Created by Dominik Bucher on 13.02.2024. +// + +#if macOS +import Foundation + +public extension RichTextView { + + /** + This type can be used to configure a ``RichTextEditor``. + */ + struct Configuration { + + public init( + isScrollingEnabled: Bool = true, + isContinuousSpellCheckingEnabled: Bool = true + ) { + self.isScrollingEnabled = isScrollingEnabled + self.isContinuousSpellCheckingEnabled = isContinuousSpellCheckingEnabled + } + + /// Whether or not the editor should scroll. + public var isScrollingEnabled: Bool + public var isContinuousSpellCheckingEnabled: Bool + } +} +#endif diff --git a/Sources/RichTextKit/RichTextView+Config_UIKit.swift b/Sources/RichTextKit/RichTextView+Config_UIKit.swift new file mode 100644 index 000000000..8e933fa7d --- /dev/null +++ b/Sources/RichTextKit/RichTextView+Config_UIKit.swift @@ -0,0 +1,45 @@ +// +// RichTextView+Config_UIKit.swift +// RichTextKit +// +// Created by Daniel Saidi on 2024-01-16. +// Copyright © 2024 Daniel Saidi. All rights reserved. +// + +#if iOS || os(tvOS) || os(visionOS) +import SwiftUI + +public extension RichTextView { + + /** + This type can be used to configure a ``RichTextEditor``. + */ + struct Configuration { + + /** + Create a custom configuration. + + - Parameters: + - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. + */ + public init( + isScrollingEnabled: Bool = true, + allowsEditingTextAttributes: Bool = true, + autocapitalizationType: UITextAutocapitalizationType = .sentences, + spellCheckingType: UITextSpellCheckingType = .default + + ) { + self.isScrollingEnabled = isScrollingEnabled + self.allowsEditingTextAttributes = allowsEditingTextAttributes + self.autocapitalizationType = autocapitalizationType + self.spellCheckingType = spellCheckingType + } + + /// Whether or not the editor should scroll. + public var isScrollingEnabled: Bool + public var allowsEditingTextAttributes: Bool + public var autocapitalizationType: UITextAutocapitalizationType + public var spellCheckingType: UITextSpellCheckingType + } +} +#endif From cfef0f2156e92ef074e6df0f4f90ae120844624b Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 13:00:48 +0100 Subject: [PATCH 4/8] Add Configuration --- Sources/RichTextKit/RichTextView+Config_AppKit.swift | 5 +++++ Sources/RichTextKit/RichTextView+Config_UIKit.swift | 6 ++++++ 2 files changed, 11 insertions(+) diff --git a/Sources/RichTextKit/RichTextView+Config_AppKit.swift b/Sources/RichTextKit/RichTextView+Config_AppKit.swift index f650ca251..61a9f6c10 100644 --- a/Sources/RichTextKit/RichTextView+Config_AppKit.swift +++ b/Sources/RichTextKit/RichTextView+Config_AppKit.swift @@ -15,6 +15,10 @@ public extension RichTextView { */ struct Configuration { + /// Create a custom configuration + /// - Parameters: + /// - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. + /// - isContinuousSpellCheckingEnabled: Whether the editor spell-checks in realtime. Defaults to `true`. public init( isScrollingEnabled: Bool = true, isContinuousSpellCheckingEnabled: Bool = true @@ -25,6 +29,7 @@ public extension RichTextView { /// Whether or not the editor should scroll. public var isScrollingEnabled: Bool + /// Whether the editor spell-checks in realtime. public var isContinuousSpellCheckingEnabled: Bool } } diff --git a/Sources/RichTextKit/RichTextView+Config_UIKit.swift b/Sources/RichTextKit/RichTextView+Config_UIKit.swift index 8e933fa7d..fca68d2fb 100644 --- a/Sources/RichTextKit/RichTextView+Config_UIKit.swift +++ b/Sources/RichTextKit/RichTextView+Config_UIKit.swift @@ -21,6 +21,9 @@ public extension RichTextView { - Parameters: - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. + - allowsEditingTextAttributes: If editor allows editing text attributes, by default `true`. + - autocapitalizationType: Type of Auto capitalization, default is to `.sentences`. + - spellCheckingType: Whether textView spell-Checks, default is `.default`. */ public init( isScrollingEnabled: Bool = true, @@ -37,8 +40,11 @@ public extension RichTextView { /// Whether or not the editor should scroll. public var isScrollingEnabled: Bool + /// Whether textView allows editting text attributes public var allowsEditingTextAttributes: Bool + /// Kind of auto capitalization public var autocapitalizationType: UITextAutocapitalizationType + /// If TextView spell-checks the text. public var spellCheckingType: UITextSpellCheckingType } } From 9f6b34ed60237c5099bc9f131a826e20e9f02921 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 13:07:35 +0100 Subject: [PATCH 5/8] Fix tests --- Demo/Demo.xcodeproj/project.pbxproj | 16 ++++++++-------- .../RichTextKit/RichTextView+Config_UIKit.swift | 5 ++--- Sources/RichTextKit/RichTextView_AppKit.swift | 6 +++--- Sources/RichTextKit/RichTextView_UIKit.swift | 1 + .../RichTextViewRepresentableTests.swift | 6 ++++-- 5 files changed, 18 insertions(+), 16 deletions(-) diff --git a/Demo/Demo.xcodeproj/project.pbxproj b/Demo/Demo.xcodeproj/project.pbxproj index ce34b4ed5..e5ae69a9e 100644 --- a/Demo/Demo.xcodeproj/project.pbxproj +++ b/Demo/Demo.xcodeproj/project.pbxproj @@ -415,7 +415,7 @@ CODE_SIGN_ENTITLEMENTS = "Demo (iOS).entitlements"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; - DEVELOPMENT_TEAM = J4CAUDX828; + DEVELOPMENT_TEAM = PMEDFW438U; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; @@ -429,7 +429,7 @@ "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = iphoneos; SUPPORTED_PLATFORMS = "iphoneos iphonesimulator"; @@ -449,7 +449,7 @@ CODE_SIGN_ENTITLEMENTS = "Demo (iOS).entitlements"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; - DEVELOPMENT_TEAM = J4CAUDX828; + DEVELOPMENT_TEAM = PMEDFW438U; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; @@ -463,7 +463,7 @@ "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = iphoneos; SUPPORTED_PLATFORMS = "iphoneos iphonesimulator"; @@ -486,7 +486,7 @@ COMBINE_HIDPI_IMAGES = YES; CURRENT_PROJECT_VERSION = 1; DEAD_CODE_STRIPPING = YES; - DEVELOPMENT_TEAM = J4CAUDX828; + DEVELOPMENT_TEAM = PMEDFW438U; ENABLE_HARDENED_RUNTIME = YES; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; @@ -497,7 +497,7 @@ ); MACOSX_DEPLOYMENT_TARGET = 12.0; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = macosx; SWIFT_EMIT_LOC_STRINGS = YES; @@ -515,7 +515,7 @@ COMBINE_HIDPI_IMAGES = YES; CURRENT_PROJECT_VERSION = 1; DEAD_CODE_STRIPPING = YES; - DEVELOPMENT_TEAM = J4CAUDX828; + DEVELOPMENT_TEAM = PMEDFW438U; ENABLE_HARDENED_RUNTIME = YES; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; @@ -526,7 +526,7 @@ ); MACOSX_DEPLOYMENT_TARGET = 12.0; MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = com.develodom.richtextkit.Demo; + PRODUCT_BUNDLE_IDENTIFIER = com.danielsaidi.richtextkit.Demo; PRODUCT_NAME = Demo; SDKROOT = macosx; SWIFT_EMIT_LOC_STRINGS = YES; diff --git a/Sources/RichTextKit/RichTextView+Config_UIKit.swift b/Sources/RichTextKit/RichTextView+Config_UIKit.swift index fca68d2fb..765f75355 100644 --- a/Sources/RichTextKit/RichTextView+Config_UIKit.swift +++ b/Sources/RichTextKit/RichTextView+Config_UIKit.swift @@ -23,14 +23,13 @@ public extension RichTextView { - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. - allowsEditingTextAttributes: If editor allows editing text attributes, by default `true`. - autocapitalizationType: Type of Auto capitalization, default is to `.sentences`. - - spellCheckingType: Whether textView spell-Checks, default is `.default`. + - spellCheckingType: Whether textView spell-Checks, default is `.no`. */ public init( isScrollingEnabled: Bool = true, allowsEditingTextAttributes: Bool = true, autocapitalizationType: UITextAutocapitalizationType = .sentences, - spellCheckingType: UITextSpellCheckingType = .default - + spellCheckingType: UITextSpellCheckingType = .no ) { self.isScrollingEnabled = isScrollingEnabled self.allowsEditingTextAttributes = allowsEditingTextAttributes diff --git a/Sources/RichTextKit/RichTextView_AppKit.swift b/Sources/RichTextKit/RichTextView_AppKit.swift index 3fb356227..721f1e718 100644 --- a/Sources/RichTextKit/RichTextView_AppKit.swift +++ b/Sources/RichTextKit/RichTextView_AppKit.swift @@ -29,7 +29,7 @@ open class RichTextView: NSTextView, RichTextViewComponent { /// The configuration to use by the rich text view. public var configuration: Configuration = .standard - + /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -120,9 +120,9 @@ open class RichTextView: NSTextView, RichTextViewComponent { setContentCompressionResistancePriority(.defaultLow, for: .horizontal) setupConfiguration() } - + // MARK: - Internal - + func setupConfiguration() { isContinuousSpellCheckingEnabled = configuration.isContinuousSpellCheckingEnabled } diff --git a/Sources/RichTextKit/RichTextView_UIKit.swift b/Sources/RichTextKit/RichTextView_UIKit.swift index 63bf0ab7d..fb90f68a2 100644 --- a/Sources/RichTextKit/RichTextView_UIKit.swift +++ b/Sources/RichTextKit/RichTextView_UIKit.swift @@ -162,6 +162,7 @@ open class RichTextView: UITextView, RichTextViewComponent { text.autosizeImageAttachments(maxSize: imageAttachmentMaxSize) attributedString = text richTextDataFormat = format + backgroundColor = .clear trySetupInitialTextColor(for: text) { textColor = .label } diff --git a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift index 9b1a707e4..d9f706443 100644 --- a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift +++ b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift @@ -45,9 +45,10 @@ final class RichTextViewComponentTests: XCTestCase { func testSettingUpWithEmptyTextWorks() { let string = NSAttributedString(string: "") view.setup(with: string, format: .rtf) + view.configuration = .standard XCTAssertEqual(view.richText.string, "") #if iOS || os(tvOS) - XCTAssertFalse(view.allowsEditingTextAttributes) + XCTAssertTrue(view.allowsEditingTextAttributes) XCTAssertEqual(view.autocapitalizationType, .sentences) #endif XCTAssertEqual(view.backgroundColor, .clear) @@ -63,9 +64,10 @@ final class RichTextViewComponentTests: XCTestCase { func testSettingUpWithNonEmptyTextWorks() { let string = NSAttributedString(string: "foo bar baz") view.setup(with: string, format: .rtf) + view.configuration = .standard XCTAssertEqual(view.richText.string, "foo bar baz") #if iOS || os(tvOS) - XCTAssertFalse(view.allowsEditingTextAttributes) + XCTAssertTrue(view.allowsEditingTextAttributes) XCTAssertEqual(view.autocapitalizationType, .sentences) #endif XCTAssertEqual(view.backgroundColor, .clear) From 84d93e6ee99dd84d5c25221c2d11ec7ef6f64c24 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 13:11:15 +0100 Subject: [PATCH 6/8] Run swiftformat --- Sources/RichTextKit/RichTextView+Config_AppKit.swift | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Sources/RichTextKit/RichTextView+Config_AppKit.swift b/Sources/RichTextKit/RichTextView+Config_AppKit.swift index 61a9f6c10..3052f117e 100644 --- a/Sources/RichTextKit/RichTextView+Config_AppKit.swift +++ b/Sources/RichTextKit/RichTextView+Config_AppKit.swift @@ -1,6 +1,6 @@ // // RichTextView+Config_AppKit.swift -// +// // // Created by Dominik Bucher on 13.02.2024. // @@ -9,12 +9,12 @@ import Foundation public extension RichTextView { - + /** This type can be used to configure a ``RichTextEditor``. */ struct Configuration { - + /// Create a custom configuration /// - Parameters: /// - isScrollingEnabled: Whether or not the editor should scroll, by default `true`. @@ -26,7 +26,7 @@ public extension RichTextView { self.isScrollingEnabled = isScrollingEnabled self.isContinuousSpellCheckingEnabled = isContinuousSpellCheckingEnabled } - + /// Whether or not the editor should scroll. public var isScrollingEnabled: Bool /// Whether the editor spell-checks in realtime. From ffcdd5c28331f7fd2f98c254e22190753cf1e111 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 13:30:54 +0100 Subject: [PATCH 7/8] Add Themes --- .../Component/RichTextViewComponent.swift | 19 -------- Sources/RichTextKit/RichTextView+Theme.swift | 47 +++++++++++++++++++ Sources/RichTextKit/RichTextView_AppKit.swift | 15 ++++-- Sources/RichTextKit/RichTextView_UIKit.swift | 22 +++++++-- .../RichTextViewRepresentableTests.swift | 4 +- 5 files changed, 76 insertions(+), 31 deletions(-) create mode 100644 Sources/RichTextKit/RichTextView+Theme.swift diff --git a/Sources/RichTextKit/Component/RichTextViewComponent.swift b/Sources/RichTextKit/Component/RichTextViewComponent.swift index f51bc73c4..ff78777a6 100644 --- a/Sources/RichTextKit/Component/RichTextViewComponent.swift +++ b/Sources/RichTextKit/Component/RichTextViewComponent.swift @@ -133,22 +133,3 @@ public extension RichTextViewComponent { format.supportsImages ? .enabled : .disabled } } - -extension RichTextViewComponent { - - /// This can be called to setup the initial font size. - func setupInitialFontSize() { - let font = FontRepresentable.standardRichTextFont - let size = font.pointSize - setRichTextFontSize(size) - } - - /// This can be called to setup an initial text color. - func trySetupInitialTextColor( - for text: NSAttributedString, - _ action: () -> Void - ) { - guard text.string.isEmpty else { return } - action() - } -} diff --git a/Sources/RichTextKit/RichTextView+Theme.swift b/Sources/RichTextKit/RichTextView+Theme.swift new file mode 100644 index 000000000..6a563203a --- /dev/null +++ b/Sources/RichTextKit/RichTextView+Theme.swift @@ -0,0 +1,47 @@ +// +// RichTextView+Theme.swift +// RichTextKit +// +// Created by Dominik Bucher on 13.02.2024. +// + +#if iOS || macOS || os(tvOS) || os(visionOS) +import SwiftUI + +public extension RichTextView { + + /** + This type can be used to configure a ``RichTextEditor``'s current color properties. + */ + struct Theme { + + /** + Create a custom configuration. + + - Parameters: + - font: default `.systemFont` of point size `16` (this differs on iOS and macOS). + - fontColor: default `.textColor`. + - backgroundColor: Color of whole textView default `.clear`. + */ + public init( + font: FontRepresentable = .systemFont(ofSize: 16), + fontColor: ColorRepresentable = .textColor, + backgroundColor: ColorRepresentable = .clear + ) { + self.font = font + self.fontColor = fontColor + self.backgroundColor = backgroundColor + } + + public let font: FontRepresentable + public let fontColor: ColorRepresentable + public let backgroundColor: ColorRepresentable + } +} + +public extension RichTextView.Theme { + + /// Get a standard rich text editor configuration. + static var standard: Self { .init() } +} +#endif diff --git a/Sources/RichTextKit/RichTextView_AppKit.swift b/Sources/RichTextKit/RichTextView_AppKit.swift index 721f1e718..5e224bc60 100644 --- a/Sources/RichTextKit/RichTextView_AppKit.swift +++ b/Sources/RichTextKit/RichTextView_AppKit.swift @@ -30,6 +30,9 @@ open class RichTextView: NSTextView, RichTextViewComponent { /// The configuration to use by the rich text view. public var configuration: Configuration = .standard + /// The theme for coloring and setting style to text view. + public var theme: Theme = .standard + /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -107,18 +110,14 @@ open class RichTextView: NSTextView, RichTextViewComponent { format: RichTextDataFormat ) { attributedString = .empty - setupInitialFontSize() attributedString = text allowsImageEditing = true allowsUndo = true - backgroundColor = .clear - trySetupInitialTextColor(for: text) { - textColor = .textColor - } imageConfiguration = standardImageConfiguration(for: format) layoutManager?.defaultAttachmentScaling = NSImageScaling.scaleProportionallyDown setContentCompressionResistancePriority(.defaultLow, for: .horizontal) setupConfiguration() + setupTheme() } // MARK: - Internal @@ -127,6 +126,12 @@ open class RichTextView: NSTextView, RichTextViewComponent { isContinuousSpellCheckingEnabled = configuration.isContinuousSpellCheckingEnabled } + func setupTheme() { + font = theme.font + textColor = theme.fontColor + backgroundColor = theme.backgroundColor + } + // MARK: - Open Functionality /** diff --git a/Sources/RichTextKit/RichTextView_UIKit.swift b/Sources/RichTextKit/RichTextView_UIKit.swift index fb90f68a2..f654b9a0c 100644 --- a/Sources/RichTextKit/RichTextView_UIKit.swift +++ b/Sources/RichTextKit/RichTextView_UIKit.swift @@ -56,6 +56,12 @@ open class RichTextView: UITextView, RichTextViewComponent { } } + public var theme: Theme = .standard { + didSet { + setupTheme() + } + } + /// The style to use when highlighting text in the view. public var highlightingStyle: RichTextHighlightingStyle = .standard @@ -157,16 +163,22 @@ open class RichTextView: UITextView, RichTextViewComponent { format: RichTextDataFormat ) { attributedString = .empty - setupInitialFontSize() imageConfiguration = standardImageConfiguration(for: format) text.autosizeImageAttachments(maxSize: imageAttachmentMaxSize) attributedString = text richTextDataFormat = format - backgroundColor = .clear - trySetupInitialTextColor(for: text) { - textColor = .label - } setContentCompressionResistancePriority(.defaultLow, for: .horizontal) + setupTheme() + } + + // MARK: - Internal functionality + + func setupTheme() { + if text.isEmpty { + font = theme.font + textColor = theme.fontColor + } + backgroundColor = theme.backgroundColor } // MARK: - Open Functionality diff --git a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift index d9f706443..58961d757 100644 --- a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift +++ b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift @@ -74,9 +74,9 @@ final class RichTextViewComponentTests: XCTestCase { XCTAssertEqual(view.contentCompressionResistancePriority(for: .horizontal), .defaultLow) #if iOS || os(tvOS) XCTAssertEqual(view.spellCheckingType, .no) - XCTAssertEqual(view.textColor, nil) + XCTAssertEqual(view.textColor, .textColor) #elseif macOS - XCTAssertEqual(view.textColor, nil) + XCTAssertEqual(view.textColor, .textColor) #endif } } From da7f86308ff53de99b1b825b4cca0a3d11360510 Mon Sep 17 00:00:00 2001 From: Dominik Bucher Date: Tue, 13 Feb 2024 15:48:24 +0100 Subject: [PATCH 8/8] Fix test when no color set to default text --- Tests/RichTextKitTests/RichTextViewRepresentableTests.swift | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift index 58961d757..1a61d16d8 100644 --- a/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift +++ b/Tests/RichTextKitTests/RichTextViewRepresentableTests.swift @@ -65,6 +65,7 @@ final class RichTextViewComponentTests: XCTestCase { let string = NSAttributedString(string: "foo bar baz") view.setup(with: string, format: .rtf) view.configuration = .standard + view.theme = .standard XCTAssertEqual(view.richText.string, "foo bar baz") #if iOS || os(tvOS) XCTAssertTrue(view.allowsEditingTextAttributes) @@ -74,9 +75,9 @@ final class RichTextViewComponentTests: XCTestCase { XCTAssertEqual(view.contentCompressionResistancePriority(for: .horizontal), .defaultLow) #if iOS || os(tvOS) XCTAssertEqual(view.spellCheckingType, .no) - XCTAssertEqual(view.textColor, .textColor) + XCTAssertEqual(view.textColor, nil) #elseif macOS - XCTAssertEqual(view.textColor, .textColor) + XCTAssertEqual(view.textColor, nil) #endif } }