diff options
-rw-r--r-- | Assets/crop_circle.png | bin | 0 -> 1801566 bytes | |||
-rw-r--r-- | Assets/crop_square.png | bin | 0 -> 2173417 bytes | |||
-rw-r--r-- | Package.swift | 1 | ||||
-rw-r--r-- | README.md | 32 | ||||
-rw-r--r-- | Sources/SwiftyCrop/Models/MaskShape.swift | 2 | ||||
-rw-r--r-- | Sources/SwiftyCrop/Models/SwiftyCropConfiguration.swift (renamed from Sources/SwiftyCrop/Models/Configuration.swift) | 4 | ||||
-rw-r--r-- | Sources/SwiftyCrop/SwiftyCrop.swift | 24 | ||||
-rw-r--r-- | Sources/SwiftyCrop/View/CropView.swift | 6 | ||||
-rw-r--r-- | Tests/SwiftyCropTests/SwiftyCropTests.swift | 10 |
9 files changed, 52 insertions, 27 deletions
diff --git a/Assets/crop_circle.png b/Assets/crop_circle.png Binary files differnew file mode 100644 index 0000000..f0a553b --- /dev/null +++ b/Assets/crop_circle.png diff --git a/Assets/crop_square.png b/Assets/crop_square.png Binary files differnew file mode 100644 index 0000000..a080843 --- /dev/null +++ b/Assets/crop_square.png diff --git a/Package.swift b/Package.swift index 388d74a..ca79f2e 100644 --- a/Package.swift +++ b/Package.swift @@ -5,6 +5,7 @@ import PackageDescription let package = Package( name: "SwiftyCrop", + defaultLocalization: "en", platforms: [.iOS(.v16)], products: [ // Products define the executables and libraries a package produces, making them visible to other packages. @@ -1,6 +1,9 @@ -# SwiftyCrop +# SwiftyCrop - SwiftUI -// TODO: Screenshots, GIFs +<p align="center"> + <img src="https://github.com/benedom/SwiftyCrop/blob/master/Assets/crop_circle.png" style="margin: auto;"/> + <img src="https://github.com/benedom/SwiftyCrop/blob/master/Assets/crop_square.png" style="margin: auto;"/> +</p> ## 🔭 Overview SwiftyCrop allows users to seamlessly crop images within their SwiftUI applications. It provides a user-friendly interface that makes cropping an image as simple as selecting the desired area. @@ -31,8 +34,8 @@ The localization file can be found in `Sources/SwiftyCrop/Resources`. ## 🧳 Requirements - iOS 16.0 or later -- Xcode 14.3 or later -- Swift 5.0 or later +- Xcode 15.0 or later +- Swift 5.9 or later ## 💻 Installation @@ -69,8 +72,6 @@ struct ExampleView: View { var body: some View { VStack { /* - Your view implementation here. - Update `selectedImage` with the image you want to crop, e.g. after picking it from the library or downloading it. @@ -79,8 +80,10 @@ struct ExampleView: View { Below is a sample implementation: */ - Button("Show cropper with system image") { - selectedImage = UIImage(systemName: "photo") + Button("Crop downloaded image") { + Task { + selectedImage = await downloadExampleImage() + } showImageCropper.toggle() } @@ -96,6 +99,17 @@ struct ExampleView: View { } } } + + // Example function for downloading an image + private func downloadExampleImage() async -> UIImage? { + let urlString = "https://picsum.photos/1000/1200" + guard let url = URL(string: urlString), + let (data, _) = try? await URLSession.shared.data(from: url), + let image = UIImage(data: data) + else { return nil } + + return image + } } ``` @@ -127,7 +141,7 @@ All issue reports, feature requests, pull requests and GitHub stars are welcomed ## ✍️ Author -Benedikt Betz +Benedikt Betz & Check24 ## 📃 License diff --git a/Sources/SwiftyCrop/Models/MaskShape.swift b/Sources/SwiftyCrop/Models/MaskShape.swift index c4b1538..d20e722 100644 --- a/Sources/SwiftyCrop/Models/MaskShape.swift +++ b/Sources/SwiftyCrop/Models/MaskShape.swift @@ -1,3 +1,3 @@ -enum MaskShape { +public enum MaskShape { case circle, square } diff --git a/Sources/SwiftyCrop/Models/Configuration.swift b/Sources/SwiftyCrop/Models/SwiftyCropConfiguration.swift index bacdab0..cc3d47a 100644 --- a/Sources/SwiftyCrop/Models/Configuration.swift +++ b/Sources/SwiftyCrop/Models/SwiftyCropConfiguration.swift @@ -1,7 +1,7 @@ import CoreGraphics /// `SwiftyCropConfiguration` is a struct that defines the configuration for cropping behavior. -struct SwiftyCropConfiguration { +public struct SwiftyCropConfiguration { let maxMagnificationScale: CGFloat let maskRadius: CGFloat @@ -10,7 +10,7 @@ struct SwiftyCropConfiguration { /// - Parameters: /// - maxMagnificationScale: The maximum scale factor that the image can be magnified while cropping. Defaults to `4.0`. /// - maskRadius: The radius of the mask used for cropping. Defaults to `130`. - init(maxMagnificationScale: CGFloat = 4.0, maskRadius: CGFloat = 130) { + public init(maxMagnificationScale: CGFloat = 4.0, maskRadius: CGFloat = 130) { self.maxMagnificationScale = maxMagnificationScale self.maskRadius = maskRadius } diff --git a/Sources/SwiftyCrop/SwiftyCrop.swift b/Sources/SwiftyCrop/SwiftyCrop.swift index ab252e6..0de933d 100644 --- a/Sources/SwiftyCrop/SwiftyCrop.swift +++ b/Sources/SwiftyCrop/SwiftyCrop.swift @@ -9,13 +9,25 @@ import SwiftUI /// - maskShape: The shape of the mask used for cropping. /// - configuration: The configuration for the cropping behavior. If nothing is specified, the default is used. /// - onComplete: A closure that's called when the cropping is complete. This closure returns the cropped `UIImage?`. If an error occurs the return value is nil. -struct SwiftyCropView: View { - let imageToCrop: UIImage - let maskShape: MaskShape - let configuration: SwiftyCropConfiguration = SwiftyCropConfiguration() - let onComplete: (UIImage?) -> Void +public struct SwiftyCropView: View { + private let imageToCrop: UIImage + private let maskShape: MaskShape + private let configuration: SwiftyCropConfiguration + private let onComplete: (UIImage?) -> Void - var body: some View { + public init( + imageToCrop: UIImage, + maskShape: MaskShape, + configuration: SwiftyCropConfiguration = SwiftyCropConfiguration(), + onComplete: @escaping (UIImage?) -> Void + ) { + self.imageToCrop = imageToCrop + self.maskShape = maskShape + self.configuration = configuration + self.onComplete = onComplete + } + + public var body: some View { CropView( image: imageToCrop, maskShape: maskShape, diff --git a/Sources/SwiftyCrop/View/CropView.swift b/Sources/SwiftyCrop/View/CropView.swift index 29cfb8a..3cb453a 100644 --- a/Sources/SwiftyCrop/View/CropView.swift +++ b/Sources/SwiftyCrop/View/CropView.swift @@ -31,7 +31,7 @@ struct CropView: View { var body: some View { VStack { - Text("interaction_instructions", tableName: localizableTableName) + Text("interaction_instructions", tableName: localizableTableName, bundle: .module) .font(.system(size: 16, weight: .regular)) .foregroundColor(.white) .padding(.top, 30) @@ -100,7 +100,7 @@ struct CropView: View { Button { dismiss() } label: { - Text("cancel_button", tableName: localizableTableName) + Text("cancel_button", tableName: localizableTableName, bundle: .module) } .foregroundColor(.white) @@ -110,7 +110,7 @@ struct CropView: View { onComplete(viewModel.crop(image)) dismiss() } label: { - Text("save_button", tableName: localizableTableName) + Text("save_button", tableName: localizableTableName, bundle: .module) } .foregroundColor(.white) } diff --git a/Tests/SwiftyCropTests/SwiftyCropTests.swift b/Tests/SwiftyCropTests/SwiftyCropTests.swift index e029923..3e0877f 100644 --- a/Tests/SwiftyCropTests/SwiftyCropTests.swift +++ b/Tests/SwiftyCropTests/SwiftyCropTests.swift @@ -2,11 +2,9 @@ import XCTest @testable import SwiftyCrop final class SwiftyCropTests: XCTestCase { - func testExample() throws { - // XCTest Documentation - // https://developer.apple.com/documentation/xctest - - // Defining Test Cases and Test Methods - // https://developer.apple.com/documentation/xctest/defining_test_cases_and_test_methods + func testConfigurationInit() { + let configuration = SwiftyCropConfiguration(maxMagnificationScale: 1.0, maskRadius: 1.0) + XCTAssertEqual(configuration.maxMagnificationScale, 1.0) + XCTAssertEqual(configuration.maskRadius, 1.0) } } |