├── BoilerPlateSwiftUI ├── Network │ └── .gitkeep ├── Resources │ ├── Assets.xcassets │ │ ├── Contents.json │ │ └── AppIcon.appiconset │ │ │ └── Contents.json │ ├── Colors.xcassets │ │ ├── Contents.json │ │ └── Color.colorset │ │ │ └── Contents.json │ ├── Icons.xcassets │ │ ├── Contents.json │ │ └── Image.imageset │ │ │ └── Contents.json │ ├── Images.xcassets │ │ ├── Contents.json │ │ └── Image.imageset │ │ │ └── Contents.json │ ├── Constants │ │ ├── MapApplication.swift │ │ └── URLDefinitions.swift │ ├── en.lproj │ │ └── Localizable.strings │ ├── tr.lproj │ │ └── Localizable.strings │ ├── de.lproj │ │ └── Localizable.strings │ ├── Mocks │ │ └── sample-data.json │ └── Info.plist ├── Configs │ ├── AppStore.xcconfig │ ├── Production.xcconfig │ ├── Development.xcconfig │ └── Configuration.swift ├── Scenes │ ├── Main │ │ └── MainView.swift │ └── Home │ │ ├── NewPhotoPickerView.swift │ │ ├── HomeView.swift │ │ └── ImagePickerView.swift ├── Utility │ ├── Extensions │ │ ├── UITableViewCellExtensions.swift │ │ ├── UICollectionViewCellExtensions.swift │ │ ├── UIViewControllerExtensions.swift │ │ ├── UICollectionViewExtensions.swift │ │ ├── UIApplicationExtension.swift │ │ ├── ArrayExtensions.swift │ │ ├── StringExtensions.swift │ │ ├── UIImagePickerControllerSourceTypeExtension.swift │ │ ├── UITableViewExtensions.swift │ │ ├── URLExtensions.swift │ │ └── UIDeviceExtension.swift │ ├── ViewModifiers │ │ ├── BigButtonTextModifier.swift │ │ └── OnFirstAppearModifier.swift │ ├── ViewRepresentables │ │ └── ImagePicker.swift │ └── Logger.swift ├── Application │ ├── AppDelegate.swift │ ├── Services │ │ └── LoggingService.swift │ └── BoilerPlateSwiftUIApp.swift └── Managers │ ├── LoggerManager.swift │ └── URLSessionAutoLogging.swift ├── .github ├── ISSUE_TEMPLATE │ ├── custom.md │ ├── feature-request.md │ └── bug_report.md ├── workflows │ └── ios-build-check.yml └── PULL_REQUEST_TEMPLATE.md ├── BoilerPlateSwiftUI.xcodeproj ├── project.xcworkspace │ ├── contents.xcworkspacedata │ └── xcshareddata │ │ └── IDEWorkspaceChecks.plist ├── xcshareddata │ └── xcschemes │ │ ├── BoilerPlateSwiftUI-Pulse.xcscheme │ │ └── boilerplate-ios-swiftui.xcscheme └── project.pbxproj ├── scripts ├── installation │ ├── swiftlint.sh │ ├── install-githooks.sh │ └── rename-project.swift └── git-hooks │ ├── pre-commit │ └── commit-msg ├── BoilerPlateSwiftUITests ├── Info.plist └── BoilerPlateSwiftUITests.swift ├── BoilerPlateSwiftUIUITests ├── Info.plist └── BoilerPlateSwiftUIUITests.swift ├── .gitignore ├── .swiftlint.yml └── README.md /BoilerPlateSwiftUI/Network/.gitkeep: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Colors.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Icons.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Images.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/custom.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Custom issue template 3 | about: Describe this issue template's purpose here. 4 | title: "[BSU-XXXX] - Custom Request" 5 | labels: '' 6 | assignees: '' 7 | 8 | --- 9 | 10 | 11 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /scripts/installation/swiftlint.sh: -------------------------------------------------------------------------------- 1 | if test ! $(which brew); then 2 | echo "Installing homebrew..." 3 | ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)" 4 | fi 5 | # Update homebrew recipes 6 | brew update 7 | brew install swiftlint 8 | echo "Ready to go!.." -------------------------------------------------------------------------------- /BoilerPlateSwiftUI.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Constants/MapApplication.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MapApplication.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 23.05.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | enum MapApplication: String { 12 | case google = "Google Maps" 13 | case apple = "Maps" 14 | case yandex = "Yandex Maps" 15 | } 16 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Icons.xcassets/Image.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "scale" : "2x" 10 | }, 11 | { 12 | "idiom" : "universal", 13 | "scale" : "3x" 14 | } 15 | ], 16 | "info" : { 17 | "version" : 1, 18 | "author" : "xcode" 19 | } 20 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Configs/AppStore.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // AppStore.xcconfig 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Can Baybunar on 19.11.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | // Configuration settings file format documentation can be found at: 10 | // https://help.apple.com/xcode/#/dev745c5c974 11 | 12 | PRODUCT_BUNDLE_IDENTIFIER = com.adesso.BoilerPlateSwiftUI 13 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Images.xcassets/Image.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "scale" : "2x" 10 | }, 11 | { 12 | "idiom" : "universal", 13 | "scale" : "3x" 14 | } 15 | ], 16 | "info" : { 17 | "version" : 1, 18 | "author" : "xcode" 19 | } 20 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Configs/Production.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Production.xcconfig 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Can Baybunar on 19.11.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | // Configuration settings file format documentation can be found at: 10 | // https://help.apple.com/xcode/#/dev745c5c974 11 | 12 | PRODUCT_BUNDLE_IDENTIFIER = com.adesso.BoilerPlateSwiftUI.prod 13 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Configs/Development.xcconfig: -------------------------------------------------------------------------------- 1 | // 2 | // Development.xcconfig 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Can Baybunar on 19.11.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | // Configuration settings file format documentation can be found at: 10 | // https://help.apple.com/xcode/#/dev745c5c974 11 | 12 | PRODUCT_BUNDLE_IDENTIFIER = com.adesso.BoilerPlateSwiftUI.development 13 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Colors.xcassets/Color.colorset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | }, 6 | "colors" : [ 7 | { 8 | "idiom" : "universal", 9 | "color" : { 10 | "color-space" : "srgb", 11 | "components" : { 12 | "red" : "1.000", 13 | "alpha" : "1.000", 14 | "blue" : "1.000", 15 | "green" : "1.000" 16 | } 17 | } 18 | } 19 | ] 20 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Scenes/Main/MainView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MainView.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Cagri Gider on 14.08.2022. 6 | // Copyright © 2022 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct MainView: View { 12 | var body: some View { 13 | HomeView() 14 | } 15 | } 16 | 17 | struct MainView_Previews: PreviewProvider { 18 | static var previews: some View { 19 | MainView() 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/en.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* 2 | Localizable.strings 3 | BoilerPlateSwiftUI 4 | 5 | Created by Selim Gungorer on 14.09.2022. 6 | Copyright © 2022 Adesso Turkey. All rights reserved. 7 | */ 8 | 9 | "Hello, World!" = "Hello"; 10 | "select_photo" = "Choose a Photo"; 11 | "take_photo" = "Take a Photo"; 12 | "delete_image" = "Delete Image"; 13 | "source_library" = "Library"; 14 | "source_camera" = "Camera"; 15 | "source_saved_album" = "Saved Album"; 16 | "source_select_title" = "Select a source"; 17 | -------------------------------------------------------------------------------- /.github/workflows/ios-build-check.yml: -------------------------------------------------------------------------------- 1 | name: iOS Build Check Workflow 2 | 3 | on: 4 | push: 5 | branches: [ develop ] 6 | pull_request: 7 | branches: [ develop ] 8 | 9 | jobs: 10 | build: 11 | name: Build scheme 12 | runs-on: macos-latest 13 | 14 | steps: 15 | - name: Checkout 16 | uses: actions/checkout@v2 17 | - name: Build 18 | run: | 19 | xcodebuild -scheme boilerplate-ios-swiftui clean build -sdk iphoneos -configuration Development CODE_SIGNING_ALLOWED=No 20 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/tr.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* 2 | Localizable.strings 3 | BoilerPlateSwiftUI 4 | 5 | Created by Selim Gungorer on 14.09.2022. 6 | Copyright © 2022 Adesso Turkey. All rights reserved. 7 | */ 8 | 9 | "Hello, World!" = "Merhaba"; 10 | "select_photo" = "Bir Fotoğraf Seç"; 11 | "take_photo" = "Fotoğraf Çek"; 12 | "delete_image" = "Fotoğrafı Sil"; 13 | "source_library" = "Kütüphane"; 14 | "source_camera" = "Kamera"; 15 | "source_saved_album" = "Kaydedilmiş Albüm"; 16 | "source_select_title" = "Bir kaynak seç"; 17 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UITableViewCellExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UITableViewCellExtensions.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension UITableViewCell { 11 | static func register(to tableView: UITableView?) { 12 | let className = String(describing: Self.self) 13 | let nib = UINib(nibName: className, bundle: nil) 14 | tableView?.register(nib, forCellReuseIdentifier: className) 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/de.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | /* 2 | Localizable.strings 3 | BoilerPlateSwiftUI 4 | 5 | Created by Selim Gungorer on 14.09.2022. 6 | Copyright © 2022 Adesso Turkey. All rights reserved. 7 | */ 8 | 9 | "Hello, World!" = "Hallo"; 10 | "select_photo" = "Wähle ein Foto"; 11 | "take_photo" = "Mach ein Foto"; 12 | "delete_image" = "Foto Löschen"; 13 | "source_library" = "Bibliothek"; 14 | "source_camera" = "Kamera"; 15 | "source_saved_album" = "Gespeichertes Album"; 16 | "source_select_title" = "Wählen Sie eine Quelle aus"; 17 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UICollectionViewCellExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UICollectionViewCellExtensions.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension UICollectionViewCell { 11 | static func register(to collectionView: UICollectionView?) { 12 | let nib = UINib(nibName: String(describing: Self.self), bundle: nil) 13 | collectionView?.register(nib, forCellWithReuseIdentifier: String(describing: Self.self)) 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | ## Description 2 | 3 | Please include a summary of the change or which issue is fixed. Please also include relevant motivation and context. 4 | 5 | ## Related issue 6 | 7 | Related to: 8 | 9 | ## Explanation of changes 10 | 11 | Please delete options that are not relevant. 12 | 13 | - [ ] Bug fix (non-breaking change which fixes an issue) 14 | - [ ] New feature (non-breaking change which adds functionality) 15 | - [ ] Breaking change (fix or feature that would cause existing functionality to not work as expected) 16 | - [ ] This change requires a documentation update 17 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UIViewControllerExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UIViewControllerExtensions.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension UIViewController { 11 | static func instantiate() -> Self { 12 | func instanceFromNib() -> T { 13 | T(nibName: String(describing: self), bundle: nil) 14 | } 15 | 16 | return instanceFromNib() 17 | } 18 | 19 | func hideKeyboard() { 20 | UIApplication.shared.sendAction(#selector(UIResponder.resignFirstResponder), to: nil, from: nil, for: nil) 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/ViewModifiers/BigButtonTextModifier.swift: -------------------------------------------------------------------------------- 1 | // 2 | // BigButtonTextModifier.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 10.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct BigButtonTextModifier: ViewModifier { 12 | 13 | var backgroundColor: Color = .green 14 | 15 | func body(content: Content) -> some View { 16 | content 17 | .font(.title3) 18 | .foregroundColor(.white) 19 | .padding(.all) 20 | .background(backgroundColor) 21 | .cornerRadius(20) 22 | .shadow(radius: 8) 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature-request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature request 3 | about: Suggest an idea for this project 4 | title: "[BSU-XXXX] - Feature Request" 5 | labels: '' 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Is your feature request related to a problem? Please describe.** 11 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] 12 | 13 | **Describe the solution you'd like** 14 | A clear and concise description of what you want to happen. 15 | 16 | **Describe alternatives you've considered** 17 | A clear and concise description of any alternative solutions or features you've considered. 18 | 19 | **Additional context** 20 | Add any other context or screenshots about the feature request here. 21 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UICollectionViewExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UICollectionViewExtensions.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension UICollectionView { 11 | func dequeue(withIdentifier identifier: String = String(describing: T.self), 12 | for indexPath: IndexPath) -> T { 13 | guard let cell = self.dequeueReusableCell(withReuseIdentifier: identifier, for: indexPath) as? T else { 14 | fatalError("Could not dequeue cell with identifier \(identifier) from collectionView \(self)") 15 | } 16 | return cell 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Application/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // AppDelegate 4 | // 5 | // Created by Sucu, Ege on 22.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | // This will include methods which the new SwiftUI Lifecycle does not support yet. 12 | class AppDelegate: NSObject, UIApplicationDelegate { 13 | func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) { 14 | // Handle remote notifications here 15 | } 16 | 17 | func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error) { 18 | // Handle remote notification failures here 19 | print(error.localizedDescription) 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Application/Services/LoggingService.swift: -------------------------------------------------------------------------------- 1 | // 2 | // LoggingService.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Baha Ulug on 3.12.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class LoggingService { 12 | init() { 13 | LoggerManager.instance.setup(level: .debug) 14 | logApplicationAndDeviceInfo() 15 | } 16 | 17 | private func logApplicationAndDeviceInfo() { 18 | let version = UIApplication.appVersion 19 | let build = UIApplication.appBuild 20 | let deviceModel = UIDevice.modelName 21 | let osVersion = UIDevice.osVersion 22 | 23 | LoggerManager.instance.setInfo(version: version, build: build, deviceModel: deviceModel, osVersion: osVersion) 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Configs/Configuration.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Configuration.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Baha Ulug on 1.12.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | final class Configuration { 12 | 13 | static var isProduction: Bool { 14 | #if Production 15 | return true 16 | #else 17 | return false 18 | #endif 19 | } 20 | 21 | static var isAppStore: Bool { 22 | #if AppStore 23 | return true 24 | #else 25 | return false 26 | #endif 27 | } 28 | 29 | static var isDevelopment: Bool { 30 | #if Development 31 | return true 32 | #else 33 | return false 34 | #endif 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUITests/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | $(PRODUCT_BUNDLE_PACKAGE_TYPE) 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | 22 | 23 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/ViewModifiers/OnFirstAppearModifier.swift: -------------------------------------------------------------------------------- 1 | // 2 | // OnFirstAppearModifier.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Said on 10.10.2022. 6 | // Copyright © 2022 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct OnFirstAppearModifier: ViewModifier { 12 | 13 | let perform: () -> Void 14 | @State private var firstTime: Bool = true 15 | 16 | func body(content: Content) -> some View { 17 | content.onAppear { 18 | if firstTime { 19 | firstTime = false 20 | self.perform() 21 | } 22 | } 23 | } 24 | } 25 | 26 | extension View { 27 | 28 | func onFirstAppear(perform: @escaping () -> Void) -> some View { 29 | self.modifier(OnFirstAppearModifier(perform: perform)) 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUIUITests/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | $(PRODUCT_BUNDLE_PACKAGE_TYPE) 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | 22 | 23 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UIApplicationExtension.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UIApplicationExtension.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Baha Ulug on 3.12.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | extension UIApplication { 12 | 13 | static let appVersion: String = { 14 | if let appVersion = Bundle.main.object(forInfoDictionaryKey: "CFBundleShortVersionString") as? String { 15 | return appVersion 16 | } else { 17 | return "" 18 | } 19 | }() 20 | 21 | static let appBuild: String = { 22 | if let appBuild = Bundle.main.object(forInfoDictionaryKey: kCFBundleVersionKey as String) as? String { 23 | return appBuild 24 | } else { 25 | return "" 26 | } 27 | }() 28 | } 29 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Constants/URLDefinitions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // URLDefinitions.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 23.05.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | struct URLDefinitions { 12 | static let googleMapsAppStoreURL = URL(string: "https://apps.apple.com/us/app/google-maps/id585027354") 13 | static let googleMapsDeeplinkURL = URL(string: "comgooglemaps://") 14 | static let googleMapsLocationString = "comgooglemaps://?saddr=&daddr=%ld,%ld" 15 | static let yandexMapsAppStoreURL = URL(string: "https://itunes.apple.com/ru/app/yandex.navigator/id474500851") 16 | static let yandexMapsDeeplinkURL = URL(string: "yandexnavi://") 17 | static let yandexMapsLocationString = "yandexnavi://build_route_on_map?lat_to=%ld&lon_to=%ld" 18 | } 19 | -------------------------------------------------------------------------------- /scripts/installation/install-githooks.sh: -------------------------------------------------------------------------------- 1 | # This script copies the githooks into the proper location. 2 | # 3 | # This script should be called directly. 4 | 5 | PARENTDIR=$(cd ../ && pwd) 6 | PROJECTDIR=$(cd ../../ && pwd) 7 | SRC_DIR="$PARENTDIR/git-hooks/" 8 | DST_DIR="$PROJECTDIR/.git/hooks" 9 | COPY_HIDDEN= 10 | ORIG_IFS=$IFS 11 | IFS=$(echo -en "\n\b") 12 | 13 | if [[ ! -e "$SRC_DIR" ]]; then 14 | echo "error: Path does not exist: $SRC_DIR" 15 | exit 2 16 | fi 17 | 18 | #cp -a /$SRC_DIR/. /$DST_DIR/ 19 | # Copy gitHooks dir recursively 20 | CODE= 21 | if [[ -n $COPY_HIDDEN ]]; then 22 | rsync -Lra "$SRC_DIR" "$DST_DIR" 23 | CODE=$? 24 | else 25 | rsync -Lra --exclude="- .*" "$SRC_DIR" "$DST_DIR" 26 | CODE=$? 27 | fi 28 | 29 | if [ $CODE -ne 0 ]; then 30 | echo "error: Error occurred on copying Code $CODE" 31 | exit 3 32 | fi 33 | 34 | IFS=$ORIG_IFS 35 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/ArrayExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ArrayExtensions.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 12.04.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | extension Array: RawRepresentable where Element: Codable { 12 | public init?(rawValue: String) { 13 | guard let data = rawValue.data(using: .utf8), 14 | let result = try? JSONDecoder().decode([Element].self, from: data) 15 | else { 16 | return nil 17 | } 18 | self = result 19 | } 20 | 21 | public var rawValue: String { 22 | guard let data = try? JSONEncoder().encode(self), 23 | let result = String(data: data, encoding: .utf8) 24 | else { 25 | return "[]" 26 | } 27 | return result 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help us improve 4 | title: "[BSU-XXXX] - Bugfix Request" 5 | labels: '' 6 | assignees: '' 7 | 8 | --- 9 | 10 | **Describe the bug** 11 | A clear and concise description of what the bug is. 12 | 13 | **To Reproduce** 14 | Steps to reproduce the behavior: 15 | 1. Go to '...' 16 | 2. Click on '....' 17 | 3. Scroll down to '....' 18 | 4. See error 19 | 20 | **Expected behavior** 21 | A clear and concise description of what you expected to happen. 22 | 23 | **Screenshots** 24 | If applicable, add screenshots to help explain your problem. 25 | 26 | **Smartphone (please complete the following information):** 27 | - Device: [e.g. iPhone12] 28 | - OS: [e.g. iOS15.2] 29 | - Browser [e.g. stock browser, safari] 30 | - Version [e.g. 22] 31 | 32 | **Additional context** 33 | Add any other context about the problem here. 34 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Mocks/sample-data.json: -------------------------------------------------------------------------------- 1 | { 2 | "id": "0001", 3 | "type": "donut", 4 | "name": "Cake", 5 | "ppu": 0.55, 6 | "batters": 7 | { 8 | "batter": 9 | [ 10 | { "id": "1001", "type": "Regular" }, 11 | { "id": "1002", "type": "Chocolate" }, 12 | { "id": "1003", "type": "Blueberry" }, 13 | { "id": "1004", "type": "Devil's Food" } 14 | ] 15 | }, 16 | "topping": 17 | [ 18 | { "id": "5001", "type": "None" }, 19 | { "id": "5002", "type": "Glazed" }, 20 | { "id": "5005", "type": "Sugar" }, 21 | { "id": "5007", "type": "Powdered Sugar" }, 22 | { "id": "5006", "type": "Chocolate with Sprinkles" }, 23 | { "id": "5003", "type": "Chocolate" }, 24 | { "id": "5004", "type": "Maple" } 25 | ] 26 | } 27 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/StringExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // StringExtensions.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension String { 11 | 12 | var localized: String { 13 | NSLocalizedString(self, comment: "") // swiftlint:disable:this nslocalizedstring_key 14 | } 15 | 16 | func localized(withComment comment: String, tableName: String? = nil, bundle: Bundle = Bundle.main, value: String = "") -> String { 17 | NSLocalizedString(self, tableName: tableName, bundle: bundle, value: value, comment: comment) // swiftlint:disable:this nslocalizedstring_key 18 | } 19 | 20 | func localized(withDefaultValue value: String, tableName: String? = nil, bundle: Bundle = Bundle.main, comment: String = "") -> String { 21 | NSLocalizedString(self, tableName: nil, bundle: Bundle.main, value: value, comment: comment) // swiftlint:disable:this nslocalizedstring_key 22 | } 23 | 24 | static var empty: Self { 25 | "" 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UIImagePickerControllerSourceTypeExtension.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UIImagePickerControllerSourceTypeExtension.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 10.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | extension UIImagePickerController.SourceType: CaseIterable { 12 | public static var allCases: [UIImagePickerController.SourceType] { 13 | [.camera, .savedPhotosAlbum, .photoLibrary].filter { sourceType in 14 | UIImagePickerController.isSourceTypeAvailable(sourceType) 15 | } 16 | } 17 | 18 | func text() -> String { 19 | switch self { 20 | case .camera: 21 | return "source_camera" 22 | case .savedPhotosAlbum: 23 | return "source_saved_album" 24 | case .photoLibrary: 25 | return "source_library" 26 | default: // Since the available type will be now filtered, this will not trigger. 27 | return "" 28 | } 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUITests/BoilerPlateSwiftUITests.swift: -------------------------------------------------------------------------------- 1 | // 2 | // boilerplate-ios-swiftuiTests.swift 3 | // boilerplate-ios-swiftuiTests 4 | // 5 | // Created by Can Baybunar on 18.11.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import XCTest 10 | @testable import BoilerPlateSwiftUI 11 | 12 | class BoilerPlateSwiftUITests: XCTestCase { 13 | 14 | override func setUp() { 15 | // Put setup code here. This method is called before the invocation of each test method in the class. 16 | } 17 | 18 | override func tearDown() { 19 | // Put teardown code here. This method is called after the invocation of each test method in the class. 20 | } 21 | 22 | func testExample() { 23 | // This is an example of a functional test case. 24 | // Use XCTAssert and related functions to verify your tests produce the correct results. 25 | } 26 | 27 | func testPerformanceExample() { 28 | // This is an example of a performance test case. 29 | self.measure { 30 | // Put the code you want to measure the time of here. 31 | } 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Scenes/Home/NewPhotoPickerView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // NewPhotoPickerView.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 10.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | import PhotosUI 11 | 12 | @available(iOS 16.0, *) 13 | struct NewPhotoPickerView: View { 14 | 15 | @State private var selectedItem: PhotosPickerItem? 16 | @Binding var selectedImage: Image? 17 | var body: some View { 18 | VStack { 19 | PhotosPicker( 20 | selection: $selectedItem, 21 | matching: .images, 22 | photoLibrary: .shared()) { 23 | Text("select_photo") 24 | .modifier(BigButtonTextModifier(backgroundColor: .green)) 25 | } 26 | .onChange(of: selectedItem) { newItem in 27 | Task { 28 | if let data = try? await newItem?.loadTransferable(type: Data.self), 29 | let uiImage = UIImage(data: data) { 30 | selectedImage = Image(uiImage: uiImage) 31 | } 32 | } 33 | } 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /scripts/git-hooks/pre-commit: -------------------------------------------------------------------------------- 1 | 2 | 3 | # Git Hook for SwiftLint 4 | # Runs at every commit and checks for an error. 5 | # For the test, you can run `git commit` with an empty` commit message` 6 | 7 | export PATH=${PATH}:/opt/homebrew/bin:/usr/local/bin 8 | #Path to swiftlint 9 | LINT= $(which swiftlint) 10 | 11 | if [[ -e "${LINT}" ]]; then 12 | echo "SwiftLint Start..." 13 | echo $(pwd) 14 | else 15 | echo "SwiftLint does not exist, download from https://github.com/realm/SwiftLint" 16 | exit 1 17 | fi 18 | 19 | RESULT=$($LINT lint --quiet --config .swiftlint.yml) 20 | 21 | if [ "$RESULT" == '' ]; then 22 | printf "SwiftLint Finished.\n" 23 | else 24 | echo "" 25 | printf "SwiftLint Failed. Please check below:\n" 26 | 27 | while read -r line; do 28 | FILEPATH=$(echo $line | cut -d : -f 1) 29 | L=$(echo $line | cut -d : -f 2) 30 | C=$(echo $line | cut -d : -f 3) 31 | TYPE=$(echo $line | cut -d : -f 4 | cut -c 2-) 32 | MESSAGE=$(echo $line | cut -d : -f 5 | cut -c 2-) 33 | DESCRIPTION=$(echo $line | cut -d : -f 6 | cut -c 2-) 34 | printf "\n $TYPE\n" 35 | printf " $FILEPATH:$L:$C\n" 36 | printf " $MESSAGE - $DESCRIPTION\n" 37 | done <<< "$RESULT" 38 | 39 | printf "\nCOMMIT ABORTED. Please fix them before commiting.\n" 40 | 41 | exit 1 42 | fi -------------------------------------------------------------------------------- /scripts/git-hooks/commit-msg: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # 3 | # An example hook script to check the commit log message. 4 | # Called by "git commit" with one argument, the name of the file 5 | # that has the commit message. The hook should exit with non-zero 6 | # status after issuing an appropriate message if it wants to stop the 7 | # commit. The hook is allowed to edit the commit message file. 8 | # 9 | # To enable this hook, rename this file to "commit-msg". 10 | 11 | # Uncomment the below to add a Signed-off-by line to the message. 12 | # Doing this in a hook is a bad idea in general, but the prepare-commit-msg 13 | # hook is more suited to it. 14 | # 15 | # SOB=$(git var GIT_AUTHOR_IDENT | sed -n 's/^\(.*>\).*$/Signed-off-by: \1/p') 16 | # grep -qs "^$SOB" "$1" || echo "$SOB" >> "$1" 17 | 18 | # This example catches duplicate Signed-off-by lines. 19 | 20 | INPUT_FILE=$1 21 | START_LINE=`head -1 $INPUT_FILE` 22 | PATTERN='^\[((?i)[A-Za-z]+-[0-9]+)\].|(?i)merge' 23 | length=${#START_LINE} 24 | 25 | check=$(head -1 $1 | egrep $PATTERN) 26 | if [ "" = "$check" ]; then 27 | echo "Bad commit message. You must write [ticketid] see example: [ISSUE-123] commit message" 28 | echo "Message: ${START_LINE}" 29 | exit 1 30 | fi 31 | 32 | if [ $length -le 50 ]; then 33 | echo "Please enter a message with at least 50 characters." 34 | echo "Message: ${START_LINE}" 35 | exit 1 36 | fi 37 | 38 | 39 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/UITableViewExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // UITableViewExtension.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Copyright © 2020 Adesso Turkey. All rights reserved. 6 | // 7 | 8 | import UIKit 9 | 10 | extension UITableView { 11 | 12 | func dequeue(withIdentifier identifier: String = String(describing: T.self)) -> T { 13 | guard let cell = self.dequeueReusableCell(withIdentifier: identifier) as? T 14 | else { fatalError("Could not dequeue cell with identifier \(identifier) from tableView \(self)") } 15 | return cell 16 | } 17 | 18 | func dequeue(withIdentifier identifier: String = String(describing: T.self), at indexPath: IndexPath) -> T { 19 | guard let cell = self.dequeueReusableCell(withIdentifier: identifier, for: indexPath) as? T 20 | else { fatalError("Could not dequeue cell with identifier \(identifier) from tableView \(self)") } 21 | return cell 22 | } 23 | 24 | func dequeueHeaderFooterView(withIdentifier identifier: String = String(describing: T.self)) -> T { 25 | guard let cell = self.dequeueReusableHeaderFooterView(withIdentifier: identifier) as? T else { 26 | fatalError("Could not dequeue cell with identifier \(identifier) from tableView \(self)") } 27 | return cell 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUIUITests/BoilerPlateSwiftUIUITests.swift: -------------------------------------------------------------------------------- 1 | // 2 | // boilerplate-ios-swiftuiUITests.swift 3 | // boilerplate-ios-swiftuiUITests 4 | // 5 | // Created by Can Baybunar on 18.11.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import XCTest 10 | 11 | class BoilerPlateSwiftUIUITests: XCTestCase { 12 | 13 | override func setUp() { 14 | // Put setup code here. This method is called before the invocation of each test method in the class. 15 | 16 | // In UI tests it is usually best to stop immediately when a failure occurs. 17 | continueAfterFailure = false 18 | 19 | // In UI tests it’s important to set the initial state - such as interface orientation - required for your tests before they run. The setUp method is a good place to do this. 20 | } 21 | 22 | override func tearDown() { 23 | // Put teardown code here. This method is called after the invocation of each test method in the class. 24 | } 25 | 26 | func testExample() { 27 | // UI tests must launch the application that they test. 28 | let app = XCUIApplication() 29 | app.launch() 30 | 31 | // Use recording to get started writing UI tests. 32 | // Use XCTAssert and related functions to verify your tests produce the correct results. 33 | } 34 | 35 | func testLaunchPerformance() { 36 | if #available(macOS 10.15, iOS 13.0, tvOS 13.0, *) { 37 | // This measures how long it takes to launch your application. 38 | measure(metrics: [XCTOSSignpostMetric.applicationLaunch]) { 39 | XCUIApplication().launch() 40 | } 41 | } 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Application/BoilerPlateSwiftUIApp.swift: -------------------------------------------------------------------------------- 1 | // 2 | // BoilerPlateSwiftUIApp.swift 3 | // BoilerPlateSwiftUIApp 4 | // 5 | // Created by Cagri Gider on 14.08.2022. 6 | // Copyright © 2022 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | #if PULSE 11 | import Pulse 12 | #endif 13 | 14 | @main 15 | struct BoilerPlateSwiftUIApp: App { 16 | @Environment(\.scenePhase) private var phase 17 | @UIApplicationDelegateAdaptor private var appDelegate: AppDelegate 18 | // Check out https://developer.apple.com/documentation/swiftui/scenephase for more information 19 | private var loggingService: LoggingService 20 | 21 | init() { 22 | #if PULSE 23 | Experimental.URLSessionProxy.shared.isEnabled = true 24 | URLSessionProxyDelegate.enableAutomaticRegistration() 25 | #endif 26 | loggingService = LoggingService() 27 | } 28 | 29 | var body: some Scene { 30 | WindowGroup { 31 | MainView() 32 | .onChange(of: phase, perform: manageChanges(for:)) 33 | .onOpenURL(perform: onOpenURL(_:)) 34 | } 35 | } 36 | 37 | private func manageChanges(for phase: ScenePhase) { 38 | switch phase { 39 | case .active: 40 | // App became active 41 | activated() 42 | case .background: 43 | // App is running in the background 44 | backgrounded() 45 | case .inactive: 46 | // App became inactive 47 | deactivated() 48 | @unknown default: 49 | // Fallback for future cases 50 | break 51 | } 52 | } 53 | } 54 | 55 | // MARK: - App Life Cycle 56 | extension BoilerPlateSwiftUIApp { 57 | func activated() {} 58 | func backgrounded() {} 59 | func deactivated() {} 60 | func onOpenURL(_ url: URL) {} // URL Opening management. Same as AppDelegate's `application(_:open:options:)` 61 | } 62 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | $(PRODUCT_BUNDLE_PACKAGE_TYPE) 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | LSApplicationQueriesSchemes 22 | 23 | comgooglemaps 24 | yandexnavi 25 | 26 | LSRequiresIPhoneOS 27 | 28 | UIApplicationSceneManifest 29 | 30 | UIApplicationSupportsMultipleScenes 31 | 32 | UISceneConfigurations 33 | 34 | 35 | UILaunchScreen 36 | 37 | UIColorName 38 | Color 39 | UIImageName 40 | 41 | 42 | UIRequiredDeviceCapabilities 43 | 44 | armv7 45 | 46 | UISupportedInterfaceOrientations 47 | 48 | UIInterfaceOrientationPortrait 49 | UIInterfaceOrientationLandscapeLeft 50 | UIInterfaceOrientationLandscapeRight 51 | 52 | UISupportedInterfaceOrientations~ipad 53 | 54 | UIInterfaceOrientationPortrait 55 | UIInterfaceOrientationPortraitUpsideDown 56 | UIInterfaceOrientationLandscapeLeft 57 | UIInterfaceOrientationLandscapeRight 58 | 59 | 60 | 61 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Resources/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "20x20", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "20x20", 11 | "scale" : "3x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "29x29", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "size" : "29x29", 21 | "scale" : "3x" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "size" : "40x40", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "size" : "40x40", 31 | "scale" : "3x" 32 | }, 33 | { 34 | "idiom" : "iphone", 35 | "size" : "60x60", 36 | "scale" : "2x" 37 | }, 38 | { 39 | "idiom" : "iphone", 40 | "size" : "60x60", 41 | "scale" : "3x" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "size" : "20x20", 46 | "scale" : "1x" 47 | }, 48 | { 49 | "idiom" : "ipad", 50 | "size" : "20x20", 51 | "scale" : "2x" 52 | }, 53 | { 54 | "idiom" : "ipad", 55 | "size" : "29x29", 56 | "scale" : "1x" 57 | }, 58 | { 59 | "idiom" : "ipad", 60 | "size" : "29x29", 61 | "scale" : "2x" 62 | }, 63 | { 64 | "idiom" : "ipad", 65 | "size" : "40x40", 66 | "scale" : "1x" 67 | }, 68 | { 69 | "idiom" : "ipad", 70 | "size" : "40x40", 71 | "scale" : "2x" 72 | }, 73 | { 74 | "idiom" : "ipad", 75 | "size" : "76x76", 76 | "scale" : "1x" 77 | }, 78 | { 79 | "idiom" : "ipad", 80 | "size" : "76x76", 81 | "scale" : "2x" 82 | }, 83 | { 84 | "idiom" : "ipad", 85 | "size" : "83.5x83.5", 86 | "scale" : "2x" 87 | }, 88 | { 89 | "idiom" : "ios-marketing", 90 | "size" : "1024x1024", 91 | "scale" : "1x" 92 | } 93 | ], 94 | "info" : { 95 | "version" : 1, 96 | "author" : "xcode" 97 | } 98 | } -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Scenes/Home/HomeView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // HomeView.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Cagri Gider on 14.08.2022. 6 | // Copyright © 2022 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | #if PULSE 11 | import PulseUI 12 | #endif 13 | 14 | struct HomeView: View { 15 | @State private var showPulse = false 16 | var body: some View { 17 | ZStack { 18 | Color.red 19 | VStack { 20 | Text("Hello, World!") 21 | .font(.largeTitle) 22 | .bold() 23 | // You can use the code block below to test out the old & new photo picker. 24 | // ImagePickerView() 25 | // .padding(.all) 26 | // .background(Color.white) 27 | // .cornerRadius(10) 28 | // .shadow(radius: 8) 29 | // .padding(.all) 30 | } 31 | #if PULSE 32 | Button { 33 | showPulse.toggle() 34 | // Write a test function to make a fetch request in order to track Network activity. 35 | } label: { 36 | Text("Test Networking") 37 | .font(.title) 38 | .bold() 39 | .foregroundColor(.white) 40 | }.offset(.init(width: 0, height: 200)) 41 | #endif 42 | 43 | } 44 | .ignoresSafeArea() 45 | .sheet(isPresented: $showPulse) { 46 | NavigationView { 47 | pulseView() 48 | } 49 | } 50 | } 51 | 52 | @ViewBuilder 53 | func pulseView() -> some View { 54 | #if PULSE 55 | ConsoleView() 56 | .navigationBarItems(leading: Button("Close") { showPulse = false }) 57 | #else 58 | EmptyView() 59 | #endif 60 | } 61 | 62 | } 63 | 64 | struct HomeView_Previews: PreviewProvider { 65 | static var previews: some View { 66 | HomeView() 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/ViewRepresentables/ImagePicker.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ImagePicker.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 10.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct ImagePicker: UIViewControllerRepresentable { 12 | typealias UIViewControllerType = UIImagePickerController 13 | 14 | var sourceType: UIImagePickerController.SourceType = .camera 15 | var compressQuality: CGFloat 16 | @Binding var selectedImage: Image? 17 | @Environment(\.dismiss) var dismiss 18 | 19 | func makeUIViewController(context: Context) -> UIImagePickerController { 20 | let imagePickerController = UIImagePickerController() 21 | imagePickerController.allowsEditing = true 22 | imagePickerController.sourceType = sourceType 23 | imagePickerController.delegate = context.coordinator 24 | return imagePickerController 25 | } 26 | 27 | func updateUIViewController(_ uiViewController: UIImagePickerController, context: Context) {} 28 | } 29 | 30 | extension ImagePicker { 31 | 32 | func makeCoordinator() -> Coordinator { Coordinator(parent: self) } 33 | class Coordinator: NSObject, UIImagePickerControllerDelegate, UINavigationControllerDelegate { 34 | var parent: ImagePicker 35 | 36 | init(parent: ImagePicker) { self.parent = parent } 37 | func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey: Any]) { 38 | if let uiImage = info[.editedImage] as? UIImage { 39 | parent.selectedImage = Image(uiImage: uiImage) 40 | if (0.0...1.0).contains(parent.compressQuality) { 41 | if let data = uiImage.jpegData(compressionQuality: parent.compressQuality), // We can also save this data here. 42 | let compressedImage = UIImage(data: data) { 43 | parent.selectedImage = Image(uiImage: compressedImage) 44 | } 45 | } 46 | } 47 | parent.dismiss() 48 | } 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Extensions/URLExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // URLExtensions.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 23.05.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | import MapKit 11 | 12 | // MARK: - Map URL Extension 13 | /// This extension is designed to open any location with users favorite map application. 14 | /// 15 | extension View { 16 | 17 | func openURLWithMap(latitude: CGFloat, longitude: CGFloat, application: MapApplication) { 18 | switch application { 19 | case .google: 20 | guard let deeplink = URLDefinitions.googleMapsDeeplinkURL else { return } 21 | if UIApplication.shared.canOpenURL(deeplink) { 22 | let url = URL(string: String(format: URLDefinitions.googleMapsLocationString, latitude, longitude)) 23 | if let url { 24 | UIApplication.shared.open(url) 25 | } 26 | } else { 27 | if let url = URLDefinitions.googleMapsAppStoreURL { 28 | UIApplication.shared.open(url) 29 | } 30 | } 31 | case .apple: 32 | let coordinate = CLLocationCoordinate2D(latitude: latitude, longitude: longitude) 33 | let placemark = MKPlacemark(coordinate: coordinate) 34 | let item = MKMapItem(placemark: placemark) 35 | item.openInMaps() 36 | case .yandex: 37 | guard let deeplink = URLDefinitions.yandexMapsDeeplinkURL else { return } 38 | if UIApplication.shared.canOpenURL(deeplink) { 39 | let url = URL(string: String(format: URLDefinitions.yandexMapsLocationString, latitude, longitude)) 40 | if let url { 41 | UIApplication.shared.open(url) 42 | } 43 | } else { 44 | if let url = URLDefinitions.yandexMapsAppStoreURL { 45 | UIApplication.shared.open(url) 46 | } 47 | } 48 | } 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Xcode 2 | # 3 | # gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore 4 | 5 | ## User settings 6 | xcuserdata/ 7 | 8 | ## compatibility with Xcode 8 and earlier (ignoring not required starting Xcode 9) 9 | *.xcscmblueprint 10 | *.xccheckout 11 | 12 | ## compatibility with Xcode 3 and earlier (ignoring not required starting Xcode 4) 13 | build/ 14 | DerivedData/ 15 | *.moved-aside 16 | *.pbxuser 17 | !default.pbxuser 18 | *.mode1v3 19 | !default.mode1v3 20 | *.mode2v3 21 | !default.mode2v3 22 | *.perspectivev3 23 | !default.perspectivev3 24 | 25 | ## Obj-C/Swift specific 26 | *.hmap 27 | 28 | ## App packaging 29 | *.ipa 30 | *.dSYM.zip 31 | *.dSYM 32 | 33 | ## Playgrounds 34 | timeline.xctimeline 35 | playground.xcworkspace 36 | 37 | # Swift Package Manager 38 | # 39 | # Add this line if you want to avoid checking in source code from Swift Package Manager dependencies. 40 | # Packages/ 41 | # Package.pins 42 | Package.resolved 43 | # *.xcodeproj 44 | # 45 | # Xcode automatically generates this directory with a .xcworkspacedata file and xcuserdata 46 | # hence it is not needed unless you have added a package configuration file to your project 47 | # .swiftpm 48 | 49 | .build/ 50 | 51 | # CocoaPods 52 | # 53 | # We recommend against adding the Pods directory to your .gitignore. However 54 | # you should judge for yourself, the pros and cons are mentioned at: 55 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control 56 | # 57 | Pods/ 58 | 59 | # Carthage 60 | # 61 | # Add this line if you want to avoid checking in source code from Carthage dependencies. 62 | # 63 | #Frameworks/Carthage/Checkouts 64 | #Frameworks/Carthage/Build 65 | # 66 | 67 | # fastlane 68 | # 69 | # It is recommended to not store the screenshots in the git repo. 70 | # Instead, use fastlane to re-generate the screenshots whenever they are needed. 71 | # For more information about the recommended setup visit: 72 | # https://docs.fastlane.tools/best-practices/source-control/#source-control 73 | 74 | fastlane/report.xml 75 | fastlane/Preview.html 76 | fastlane/screenshots/**/*.png 77 | fastlane/test_output 78 | 79 | # Code Injection 80 | # 81 | # After new code Injection tools there's a generated folder /iOSInjectionProject 82 | # https://github.com/johnno1962/injectionforxcode 83 | 84 | iOSInjectionProject/ 85 | .DS_Store 86 | -------------------------------------------------------------------------------- /.swiftlint.yml: -------------------------------------------------------------------------------- 1 | disabled_rules: # rule identifiers to exclude from running 2 | - identifier_name 3 | - nesting 4 | - function_parameter_count 5 | - type_name 6 | excluded: # paths to ignore during linting. Takes precedence over `included`. 7 | - Pods 8 | - Project/R.generated.swift 9 | 10 | type_body_length: 11 | - 300 # warning 12 | - 400 # error 13 | 14 | # or they can set both explicitly 15 | file_length: 16 | warning: 500 17 | error: 800 18 | 19 | line_length: 20 | warning: 175 21 | error: 200 22 | ignores_function_declarations: true 23 | ignores_comments: true 24 | ignores_interpolated_strings: true 25 | ignores_urls: true 26 | 27 | disabled_rules: 28 | - todo 29 | 30 | large_tuple: # warn user when using 3 values in tuple, give error if there are 4 31 | - 3 32 | - 4 33 | 34 | opt_in_rules: 35 | - closure_spacing 36 | - conditional_returns_on_newline 37 | - duplicate_imports 38 | - empty_string 39 | - force_unwrapping 40 | - implicit_return 41 | - let_var_whitespace 42 | - nslocalizedstring_key 43 | - private_action 44 | - private_outlet 45 | - switch_case_on_newline 46 | - unneeded_parentheses_in_closure_argument 47 | #- weak_computed_property 48 | - control_statement 49 | - empty_count 50 | - trailing_newline 51 | - colon 52 | - comma 53 | 54 | 55 | 56 | conditional_returns_on_newline: 57 | severity: error 58 | if_only: true 59 | 60 | cyclomatic_complexity: 61 | warning: 10 62 | error: 20 63 | ignores_case_statements: true 64 | 65 | discouraged_direct_init: 66 | severity: error 67 | types: 68 | - Bundle 69 | - UIDevice 70 | - UIScreen 71 | - UIApplication 72 | 73 | force_cast: 74 | severity: error 75 | 76 | force_try: 77 | severity: error 78 | 79 | force_unwrapping: 80 | severity: error 81 | 82 | function_parameter_count: 83 | warning: 5 84 | error: 5 85 | 86 | identifier_name: 87 | min_length: 88 | warning: 3 89 | error: 2 90 | max_length: 91 | warning: 40 92 | error: 64 93 | excluded: 94 | - id 95 | 96 | nesting: 97 | type_level: 98 | warning: 2 99 | function_level: 100 | warning: 3 101 | 102 | switch_case_alignment: 103 | severity: error 104 | indented_cases: true 105 | 106 | switch_case_on_newline: 107 | severity: error 108 | 109 | type_name: 110 | min_length: 111 | warning: 3 112 | max_length: 113 | warning: 1000 114 | excluded: 115 | - "ID" 116 | - "Id" 117 | - "boilerplate_ios_swiftuiApp" 118 | - "boilerplate_ios_swiftuiTests" 119 | - "boilerplate_ios_swiftuiUITests" 120 | 121 | unneeded_break_in_switch: 122 | severity: error 123 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Managers/LoggerManager.swift: -------------------------------------------------------------------------------- 1 | // 2 | // LoggerManager.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Baha Ulug on 3.12.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import CocoaLumberjack 10 | 11 | class LoggerManager { 12 | 13 | private enum Constants { 14 | static let secondsInOneDay: TimeInterval = 60 * 60 * 24 15 | static let bytesInTenMegabytes: UInt64 = 1024 * 10 16 | static let maximumFileSize: UInt = 7 17 | } 18 | 19 | private let logger = Logger() 20 | private var fileLogger: DDFileLogger? 21 | static let instance = LoggerManager() 22 | 23 | func setLogLevel(_ logLevel: LogLevel) { 24 | logger.setLogLevel(logLevel) 25 | } 26 | 27 | func setup(level: LogLevel = .debug, directoryPath: String? = nil) { 28 | let ddosLogger = DDOSLogger.sharedInstance 29 | guard let documentsDirectory = directoryPath ?? NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, 30 | FileManager.SearchPathDomainMask.userDomainMask, 31 | true).first else { return } 32 | 33 | logger.setLogLevel(level) 34 | DDLog.add(ddosLogger) 35 | 36 | let fileManager = DDLogFileManagerDefault(logsDirectory: documentsDirectory) 37 | fileLogger = DDFileLogger(logFileManager: fileManager) 38 | 39 | if let fileLogger = fileLogger { 40 | fileLogger.rollingFrequency = Constants.secondsInOneDay 41 | fileLogger.maximumFileSize = Constants.bytesInTenMegabytes 42 | fileLogger.logFileManager.maximumNumberOfLogFiles = Constants.maximumFileSize 43 | DDLog.add(fileLogger) 44 | } 45 | } 46 | 47 | func getLogData() -> [Data] { 48 | guard let fileLogger = fileLogger else { return [] } 49 | let logFilePaths = fileLogger.logFileManager.sortedLogFilePaths 50 | var logFileDataArray = [Data]() 51 | for logFilePath in logFilePaths { 52 | let fileURL = URL(fileURLWithPath: logFilePath) 53 | if let logFileData = try? Data(contentsOf: fileURL, options: Data.ReadingOptions.mappedIfSafe) { 54 | logFileDataArray.insert(logFileData, at: 0) 55 | } 56 | } 57 | return logFileDataArray 58 | } 59 | 60 | func setInfo(version: String, build: String, deviceModel: String, osVersion: String) { 61 | logger.info("Application started. Version: \(version), Build: \(build), Device: \(deviceModel), iOS: \(osVersion)") 62 | } 63 | 64 | func setError(errorMessage: String) { 65 | logger.error(errorMessage) 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI.xcodeproj/xcshareddata/xcschemes/BoilerPlateSwiftUI-Pulse.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 32 | 33 | 43 | 45 | 51 | 52 | 53 | 54 | 60 | 62 | 68 | 69 | 70 | 71 | 73 | 74 | 77 | 78 | 79 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Scenes/Home/ImagePickerView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ImagePickerView.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 10.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct ImagePickerView: View { 12 | 13 | @State private var sourceType: UIImagePickerController.SourceType = .camera 14 | @State private var shouldShowImagePicker = false 15 | @State private var selectedImage: Image? 16 | var body: some View { 17 | VStack { 18 | VStack { 19 | Text("source_select_title") 20 | .font(.title3) 21 | .bold() 22 | Picker("Source Type", selection: $sourceType) { 23 | ForEach(UIImagePickerController.SourceType.allCases, id: \.self) { sourceType in 24 | Text(sourceType 25 | .text() 26 | .localized) 27 | .tag(sourceType.rawValue) 28 | } 29 | } 30 | .tint(.red) 31 | } 32 | .padding(.all) 33 | .background(Color.white) 34 | .cornerRadius(10) 35 | .shadow(radius: 8) 36 | .padding(.bottom, 40) 37 | 38 | if #available(iOS 16, *) { 39 | if sourceType == .photoLibrary || sourceType == .savedPhotosAlbum { 40 | NewPhotoPickerView(selectedImage: $selectedImage) 41 | } else { 42 | Button { 43 | shouldShowImagePicker.toggle() 44 | } label: { 45 | Text(sourceType == .camera ? "take_photo" : "select_photo") 46 | .modifier(BigButtonTextModifier(backgroundColor: .green)) 47 | } 48 | } 49 | } else { 50 | Button { 51 | shouldShowImagePicker.toggle() 52 | } label: { 53 | Text(sourceType == .camera ? "take_photo" : "select_photo") 54 | .modifier(BigButtonTextModifier(backgroundColor: .green)) 55 | } 56 | } 57 | 58 | if let selectedImage { 59 | selectedImage 60 | .resizable() 61 | .scaledToFit() 62 | .cornerRadius(20) 63 | .padding(.all) 64 | .shadow(radius: 8) 65 | Button { 66 | self.selectedImage = nil 67 | } label: { 68 | Text("delete_image") 69 | .modifier(BigButtonTextModifier(backgroundColor: .red)) 70 | } 71 | } 72 | } 73 | .sheet(isPresented: $shouldShowImagePicker, onDismiss: { 74 | // make an action after it's dismissed 75 | }, content: { 76 | ImagePicker(sourceType: sourceType, compressQuality: 0.8, selectedImage: $selectedImage) 77 | }) 78 | } 79 | } 80 | 81 | struct ImagePickerView_Previews: PreviewProvider { 82 | static var previews: some View { 83 | Group { 84 | ImagePickerView() 85 | ImagePickerView() 86 | .environment(\.locale, .init(identifier: "tr")) 87 | ImagePickerView() 88 | .environment(\.locale, .init(identifier: "de")) 89 | } 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Utility/Logger.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Logger.swift 3 | // boilerplate-ios-swiftui 4 | // 5 | // Created by Baha Ulug on 3.12.2020. 6 | // Copyright © 2020 Adesso Turkey. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | import CocoaLumberjackSwift 11 | 12 | enum LogLevel: Int, CustomStringConvertible { 13 | 14 | case verbose = 0 15 | case debug 16 | case info 17 | case warning 18 | case error 19 | 20 | var description: String { 21 | switch self { 22 | case .verbose: 23 | return "Verbose" 24 | case .debug: 25 | return "Debug" 26 | case .info: 27 | return "Info" 28 | case .warning: 29 | return "Warning" 30 | case .error: 31 | return "Error" 32 | } 33 | } 34 | } 35 | 36 | struct LogMessage: CustomStringConvertible { 37 | 38 | let level: LogLevel 39 | let message: String 40 | 41 | let file: String 42 | let function: String 43 | let line: Int 44 | 45 | var description: String { 46 | "\(file) [\(function):\(line)] \(level.description): \(message)" 47 | } 48 | } 49 | 50 | final class Logger { 51 | 52 | var logLevel: LogLevel 53 | 54 | init(logLevel: LogLevel = .debug) { 55 | self.logLevel = logLevel 56 | } 57 | 58 | func setLogLevel(_ logLevel: LogLevel) { 59 | self.logLevel = logLevel 60 | } 61 | 62 | func log(level: LogLevel, message: String, file: String = #file, function: String = #function, line: Int = #line) { 63 | guard level.rawValue >= logLevel.rawValue else { return } 64 | 65 | let message = LogMessage(level: level, 66 | message: message, 67 | file: shortenFileName(file), 68 | function: String(describing: function), 69 | line: line) 70 | 71 | switch level { 72 | case .verbose: 73 | DDLogVerbose(message.description) 74 | case .debug: 75 | DDLogDebug(message.description) 76 | case .info: 77 | DDLogInfo(message.description) 78 | case .warning: 79 | DDLogWarn(message.description) 80 | case .error: 81 | DDLogError(message.description) 82 | } 83 | } 84 | 85 | func verbose(_ message: String, file: String = #file, function: String = #function, line: Int = #line) { 86 | log(level: .verbose, message: message, file: file, function: function, line: line) 87 | } 88 | 89 | func debug(_ message: String, file: String = #file, function: String = #function, line: Int = #line) { 90 | log(level: .debug, message: message, file: file, function: function, line: line) 91 | } 92 | 93 | func info(_ message: String, file: String = #file, function: String = #function, line: Int = #line) { 94 | log(level: .info, message: message, file: file, function: function, line: line) 95 | } 96 | 97 | func warn(_ message: String, file: String = #file, function: String = #function, line: Int = #line) { 98 | log(level: .warning, message: message, file: file, function: function, line: line) 99 | } 100 | 101 | func error(_ message: String, file: String = #file, function: String = #function, line: Int = #line) { 102 | log(level: .error, message: message, file: file, function: function, line: line) 103 | } 104 | 105 | private func shortenFileName(_ fileName: String) -> String { 106 | var str = String(describing: fileName) 107 | if let idx = str.range(of: "/", options: .backwards)?.upperBound { 108 | str = String(str[idx...]) 109 | } 110 | if let idx = str.range(of: ".", options: .backwards)?.lowerBound { 111 | str = String(str[.. String { 28 | switch identifier { 29 | case "iPhone6,1", "iPhone6,2": 30 | return "iPhone 5s" 31 | case "iPhone7,2": 32 | return "iPhone 6" 33 | case "iPhone7,1": 34 | return "iPhone 6 Plus" 35 | case "iPhone8,1": 36 | return "iPhone 6s" 37 | case "iPhone8,2": 38 | return "iPhone 6s Plus" 39 | case "iPhone8,4": 40 | return "iPhone SE" 41 | case "iPhone9,1", "iPhone9,3": 42 | return "iPhone 7" 43 | case "iPhone9,2", "iPhone9,4": 44 | return "iPhone 7 Plus" 45 | case "iPhone10,1", "iPhone10,4": 46 | return "iPhone 8" 47 | case "iPhone10,2", "iPhone10,5": 48 | return "iPhone 8 Plus" 49 | case "iPhone10,3", "iPhone10,6": 50 | return "iPhone X" 51 | case "iPhone11,2": 52 | return "iPhone XS" 53 | case "iPhone11,4", "iPhone11,6": 54 | return "iPhone XS Max" 55 | case "iPhone11,8": 56 | return "iPhone XR" 57 | case "iPhone12,1": 58 | return "iPhone 11" 59 | case "iPhone12,3": 60 | return "iPhone 11 Pro" 61 | case "iPhone12,5": 62 | return "iPhone 11 Pro Max" 63 | case "iPhone12,8": 64 | return "iPhone SE (2nd generation)" 65 | case "iPad4,1", "iPad4,2", "iPad4,3": 66 | return "iPad Air" 67 | case "iPad5,3", "iPad5,4": 68 | return "iPad Air 2" 69 | case "iPad11,4", "iPad11,5": 70 | return "iPad Air (3rd generation)" 71 | case "iPad4,4", "iPad4,5", "iPad4,6": 72 | return "iPad mini 2" 73 | case "iPad4,7", "iPad4,8", "iPad4,9": 74 | return "iPad mini 3" 75 | case "iPad5,1", "iPad5,2": 76 | return "iPad mini 4" 77 | case "iPad11,1", "iPad11,2": 78 | return "iPad mini (5th generation)" 79 | case "iPad6,3", "iPad6,4": 80 | return "iPad Pro (9.7-inch)" 81 | case "iPad7,3", "iPad7,4": 82 | return "iPad Pro (10.5-inch)" 83 | case "iPad8,1", "iPad8,2", "iPad8,3", "iPad8,4": 84 | return "iPad Pro (11-inch) (1st generation)" 85 | case "iPad8,9", "iPad8,10": 86 | return "iPad Pro (11-inch) (2nd generation)" 87 | case "iPad6,7", "iPad6,8": 88 | return "iPad Pro (12.9-inch) (1st generation)" 89 | case "iPad7,1", "iPad7,2": 90 | return "iPad Pro (12.9-inch) (2nd generation)" 91 | case "iPad8,5", "iPad8,6", "iPad8,7", "iPad8,8": 92 | return "iPad Pro (12.9-inch) (3rd generation)" 93 | case "iPad8,11", "iPad8,12": 94 | return "iPad Pro (12.9-inch) (4th generation)" 95 | case "i386", "x86_64": 96 | return "Simulator \(mapToDevice(identifier: ProcessInfo().environment["SIMULATOR_MODEL_IDENTIFIER"] ?? "iOS"))" 97 | default: 98 | return identifier 99 | } 100 | } 101 | 102 | return mapToDevice(identifier: identifier) 103 | }() 104 | } 105 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI/Managers/URLSessionAutoLogging.swift: -------------------------------------------------------------------------------- 1 | // 2 | // URLSessionAutoLogging.swift 3 | // BoilerPlateSwiftUI 4 | // 5 | // Created by Sucu, Ege on 16.02.2023. 6 | // Copyright © 2023 Adesso Turkey. All rights reserved. 7 | // 8 | #if PULSE 9 | import Pulse 10 | import Foundation 11 | import ObjectiveC.runtime 12 | 13 | extension Experimental { 14 | 15 | static var networkLogger = NetworkLogger() 16 | 17 | /// Swizzles `URLSession` APIs to track _all_ tasks, even the ones created 18 | /// using the Async/Await and completion-based APIs. 19 | /// 20 | /// - warning: This is sample code that is _not_ designed to be used in 21 | /// production because it contains some private APIs. Do _not_ in your 22 | /// production builds. It's only for testing purposes. 23 | static func swizzleURLSession() { 24 | swizzleInit() 25 | swizzleReceiveData() 26 | swizzleFinishWithError() 27 | } 28 | 29 | private static func swizzleReceiveData() { 30 | let selector = NSSelectorFromString("_didReceiveData:") 31 | // swiftlint:disable:next force_unwrapping 32 | let klass: AnyClass = NSClassFromString("__NSCFURLLocalSessionConnection")! 33 | 34 | let originalImp = class_getMethodImplementation(klass, selector) 35 | typealias IMPType = @convention(c) (AnyObject, Selector, AnyObject) -> Void 36 | let originalImpCallable = unsafeBitCast(originalImp, to: IMPType.self) 37 | 38 | let block: @convention(block) (AnyObject, AnyObject) -> Void = { 39 | if let this = $0 as? NSObject, let task = this.value(forKey: "task") as? URLSessionDataTask, let data = $1 as? Data { 40 | Experimental.networkLogger.logDataTask(task, didReceive: data) 41 | } 42 | originalImpCallable($0, selector, $1) 43 | } 44 | 45 | setNewIMPWithBlock(block, forSelector: selector, toClass: klass) 46 | } 47 | 48 | private static func swizzleInit() { 49 | let selector = NSSelectorFromString("initWithTask:delegate:delegateQueue:") 50 | // swiftlint:disable:next force_unwrapping 51 | let klass: AnyClass = NSClassFromString("__NSCFURLLocalSessionConnection")! 52 | 53 | let originalImp = class_getMethodImplementation(klass, selector) 54 | typealias IMPType = @convention(c) (AnyObject, Selector, AnyObject, AnyObject, AnyObject) -> AnyObject 55 | let originalImpCallable = unsafeBitCast(originalImp, to: IMPType.self) 56 | 57 | let block: @convention(block) (AnyObject, AnyObject, AnyObject, AnyObject) -> AnyObject = { 58 | if let task = $1 as? URLSessionTask { 59 | Experimental.networkLogger.logTaskCreated(task) 60 | } 61 | return originalImpCallable($0, selector, $1, $2, $3) 62 | } 63 | 64 | setNewIMPWithBlock(block, forSelector: selector, toClass: klass) 65 | } 66 | 67 | private static func swizzleFinishWithError() { 68 | let selector = NSSelectorFromString("_didFinishWithError:") 69 | // swiftlint:disable:next force_unwrapping 70 | let klass: AnyClass = NSClassFromString("__NSCFURLLocalSessionConnection")! 71 | 72 | let originalImp = class_getMethodImplementation(klass, selector) 73 | typealias IMPType = @convention(c) (AnyObject, Selector, AnyObject?) -> Void 74 | let originalImpCallable = unsafeBitCast(originalImp, to: IMPType.self) 75 | 76 | let block: @convention(block) (AnyObject, AnyObject?) -> Void = { 77 | if let this = $0 as? NSObject, 78 | let task = this.value(forKey: "task") as? URLSessionTask, 79 | let metrics = task.value(forKey: "_incompleteTaskMetrics") as? URLSessionTaskMetrics { 80 | Experimental.networkLogger.logTask(task, didFinishCollecting: metrics) 81 | } 82 | 83 | if let this = $0 as? NSObject, let task = this.value(forKey: "task") as? URLSessionTask, let error = $1 as? (Error?) { 84 | Experimental.networkLogger.logTask(task, didCompleteWithError: error) 85 | } 86 | 87 | originalImpCallable($0, selector, $1) 88 | } 89 | 90 | setNewIMPWithBlock(block, forSelector: selector, toClass: klass) 91 | } 92 | 93 | private static func setNewIMPWithBlock(_ block: T, forSelector selector: Selector, toClass klass: AnyClass) { 94 | let method = class_getInstanceMethod(klass, selector) 95 | let imp = imp_implementationWithBlock(unsafeBitCast(block, to: AnyObject.self)) 96 | // swiftlint:disable:next force_unwrapping 97 | if !class_addMethod(klass, selector, imp, method_getTypeEncoding(method!)) { 98 | // swiftlint:disable:next force_unwrapping 99 | method_setImplementation(method!, imp) 100 | } 101 | } 102 | } 103 | #endif 104 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI.xcodeproj/xcshareddata/xcschemes/boilerplate-ios-swiftui.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 29 | 35 | 36 | 37 | 38 | 39 | 44 | 45 | 47 | 53 | 54 | 55 | 57 | 63 | 64 | 65 | 66 | 67 | 77 | 79 | 85 | 86 | 87 | 88 | 94 | 96 | 102 | 103 | 104 | 105 | 107 | 108 | 111 | 112 | 113 | -------------------------------------------------------------------------------- /scripts/installation/rename-project.swift: -------------------------------------------------------------------------------- 1 | #!/usr/bin/swift 2 | 3 | import Foundation 4 | // swiftlint:disable all 5 | class XcodeProjectRenamer: NSObject { 6 | 7 | // MARK: - Properties 8 | let fileManager = FileManager.default 9 | var processedPaths = [String]() 10 | 11 | var oldName: String = "" 12 | let newName: String 13 | 14 | // MARK: - Init 15 | init(newName: String) { 16 | self.newName = newName 17 | } 18 | 19 | // MARK: - API 20 | func run() { 21 | var currentPath = fileManager.currentDirectoryPath 22 | let scriptPath: URL = URL(fileURLWithPath: currentPath) 23 | var folderPath: URL = scriptPath.deletingLastPathComponent() 24 | folderPath = folderPath.deletingLastPathComponent() 25 | 26 | if let oldProjectName = findOldProjectName(folderPath) { 27 | oldName = oldProjectName 28 | print("Old project name found, processing continues") 29 | } else { 30 | print("Old project name not found, please enter old project name: ") 31 | if let name = readLine() { 32 | oldName = name 33 | } 34 | } 35 | 36 | if fileManager.changeCurrentDirectoryPath(folderPath.path) { 37 | print("\nSuccess") 38 | currentPath = fileManager.currentDirectoryPath 39 | } else { 40 | print("Xcode project or workspace with name: [\(oldName)] is not found at current path.") 41 | } 42 | 43 | print("from changing directory Current directory is \(currentPath)") 44 | print("\n------------------------------------------") 45 | print("Rename Xcode Project from [\(oldName)] to [\(newName)]") 46 | print("Current Path: ") 47 | print("------------------------------------------\n") 48 | 49 | if validatePath(currentPath) { 50 | enumeratePath(currentPath) 51 | } else { 52 | print("Xcode project or workspace with name: [\(oldName)] is not found at current path.") 53 | } 54 | 55 | print("\n------------------------------------------") 56 | print("Xcode Project Rename Finished!") 57 | print("------------------------------------------\n") 58 | } 59 | 60 | // MARK: - Helpers 61 | 62 | private func findOldProjectName(_ projectFolderPath: URL) -> String? { 63 | do { 64 | let directoryContents = try FileManager.default.contentsOfDirectory(at: projectFolderPath, includingPropertiesForKeys: nil, options: []) 65 | guard let projectFileName = directoryContents.filter({ $0.pathExtension == "xcodeproj" }).first?.deletingPathExtension().lastPathComponent else { return nil } 66 | return projectFileName 67 | } 68 | catch { 69 | return nil 70 | } 71 | } 72 | 73 | private func validatePath(_ path: String) -> Bool { 74 | let projectPath = path.appending("/\(oldName).xcodeproj") 75 | let workspacePath = path.appending("/\(oldName).xcworkspace") 76 | let isValid = fileManager.fileExists(atPath: projectPath) || fileManager.fileExists(atPath: workspacePath) 77 | return isValid 78 | } 79 | 80 | private func enumeratePath(_ path: String) { 81 | let enumerator = fileManager.enumerator(atPath: path) 82 | while let element = enumerator?.nextObject() as? String { 83 | let itemPath = path.appending("/\(element)") 84 | if !processedPaths.contains(itemPath) && !shouldSkip(element) { 85 | processPath(itemPath) 86 | } 87 | } 88 | } 89 | 90 | private func processPath(_ path: String) { 91 | print("Processing: \(path)") 92 | 93 | var isDir: ObjCBool = false 94 | if fileManager.fileExists(atPath: path, isDirectory: &isDir) { 95 | if isDir.boolValue { 96 | enumeratePath(path) 97 | } else { 98 | updateContentsOfFile(atPath: path) 99 | } 100 | renameItem(atPath: path) 101 | } 102 | 103 | processedPaths.append(path) 104 | } 105 | 106 | private func shouldSkip(_ element: String) -> Bool { 107 | guard 108 | !element.hasPrefix("."), 109 | !element.contains(".DS_Store"), 110 | !element.contains("Carthage"), 111 | !element.contains("Pods"), 112 | !element.contains("fastlane"), 113 | !element.contains("build") 114 | else { return true } 115 | 116 | let fileExtension = URL(fileURLWithPath: element).pathExtension 117 | switch fileExtension { 118 | case "appiconset", "json", "png", "xcuserstate": 119 | return true 120 | default: 121 | return false 122 | } 123 | } 124 | 125 | private func updateContentsOfFile(atPath path: String) { 126 | do { 127 | let oldContent = try String(contentsOfFile: path, encoding: .utf8) 128 | if oldContent.contains(oldName){ 129 | var newContent = oldContent.replacingOccurrences(of: oldName, with: newName) 130 | if oldContent.contains("\(oldName)Tests") || oldContent.contains("\(oldName)UITests"){ 131 | let testClassOldName = oldName.replacingOccurrences(of: "-", with: "_") 132 | newContent = newContent.replacingOccurrences(of: testClassOldName, with: newName) 133 | } 134 | try newContent.write(toFile: path, atomically: true, encoding: .utf8) 135 | } 136 | } catch { 137 | print("Error while updating file: \(error.localizedDescription)\n") 138 | } 139 | } 140 | 141 | private func renameItem(atPath path: String) { 142 | do { 143 | let oldItemName = URL(fileURLWithPath: path).lastPathComponent 144 | if oldItemName.contains(oldName) { 145 | let newItemName = oldItemName.replacingOccurrences(of: oldName, with: newName) 146 | let directoryURL = URL(fileURLWithPath: path).deletingLastPathComponent() 147 | let newPath = directoryURL.appendingPathComponent(newItemName).path 148 | try fileManager.moveItem(atPath: path, toPath: newPath) 149 | print("-- Renamed: \(oldItemName) -> \(newItemName)") 150 | } else if oldItemName.contains(oldName.replacingOccurrences(of: "-", with: "_")) { 151 | let newItemName = oldItemName 152 | .replacingOccurrences( 153 | of: oldName.replacingOccurrences(of: "-", with: "_"), 154 | with: newName.replacingOccurrences(of: "-", with: "_")) 155 | let directoryURL = URL(fileURLWithPath: path).deletingLastPathComponent() 156 | let newPath = directoryURL.appendingPathComponent(newItemName).path 157 | try fileManager.moveItem(atPath: path, toPath: newPath) 158 | print("-- Renamed: \(oldItemName) -> \(newItemName)") 159 | } 160 | } catch { 161 | print("Error while renaming file: \(error.localizedDescription)") 162 | } 163 | } 164 | 165 | } 166 | 167 | let arguments = CommandLine.arguments 168 | if arguments.count == 2 { 169 | let newName = arguments[1].replacingOccurrences(of: " ", with: "") 170 | let xpr = XcodeProjectRenamer(newName: newName) 171 | xpr.run() 172 | } else { 173 | print("Invalid number of arguments! Expected NEW project name.") 174 | } 175 | 176 | // swiftlint:enable all 177 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | [![swift-version](https://img.shields.io/badge/swift-5.7-brightgreen.svg)](https://github.com/apple/swift) 2 | [![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0) 3 | ![GitHub Workflow Status (branch)](https://img.shields.io/github/workflow/status/adessoTurkey/boilerplate-ios-swiftui/iOS%20Build%20Check%20Workflow/develop) 4 | 5 | iOS SwiftUI Boilerplate 6 | ============================ 7 | 8 | This is the iOS SwiftUI Boilerplate created by adesso Turkey for new projects using Swift 5. The project's primary objective is to help the development of a new one to kick-start the environment with configurations, the required features used in common adesso projects, and the helpful functionalities. 9 | 10 | Table of Contents 11 | ----------------- 12 | 13 | - [Prerequisites](#prerequisites) 14 | - [Branching Strategy](#branching) 15 | - [Project Structure](#project-structure) 16 | - [Workspace Preparing](#workspace-preparing) 17 | - [List of Frameworks](#list-of-frameworks) 18 | - [License](#license) 19 | 20 | ## Prerequisites 21 | 22 | - [MacOS Monterey (12.5 or higher)](https://support.apple.com/kb/SP777) 23 | - [Xcode 14 or higher](https://developer.apple.com/download/) ~ Swift 5.7 24 | - Swiftlint - To Install SwiftLint, please check Swiftlint Installation section from read me file 25 | 26 | ## Swiftlint Installation 27 | 28 | - On the directory of `{project_root}/scripts/installation`, via terminal 29 | - run `sh swiftlint.sh` to install brew (if necessary) and swiftlint. 30 | 31 | 32 | ## Branching Strategy 33 | 34 | Gitflow is a legacy Git workflow that was originally a disruptive and novel strategy for managing Git branches. Gitflow has fallen in popularity in favor of trunk-based workflows, which are now considered best practices for modern continuous software development and DevOps practices. Gitflow also can be challenging to use with CI/CD. 35 | 36 | | Branch | Description | 37 | | --- | --- | 38 | | **Main** | In the Git flow workflow, the main branch is used to store code that is release-ready and ready for production. | 39 | | **Develop** | The develop branch contains pre-production code with recently built features that are currently being tested. It is established at the beginning of a project and maintained during the development process. | 40 | | **Feature** | You will create a feature branch off the develop branch while working on a new feature, and once it has been finished and carefully reviewed, you will merge your changes into the develop branch. | 41 | | **Hotfix** | The hotfix branch is utilized in the Git pipeline to swiftly address required changes in your main branch. Your main branch should serve as the base for the hotfix branch, and it should be merged back into both the main and develop branches. | 42 | | **Release** | The release branch should be used when preparing new production releases. Typically, the work being performed on release branches concerns finishing touches and minor bugs specific to releasing new code, with code that should be addressed separately from the main develop branch. | 43 | 44 | 45 | - Branch names should start with feature, hotfix or release according to purpose of the branch then should continue with ticketid. see example: feature/BSU-1234 46 | - Pull requests should refer to specific issue with ticketid. see example: [BSU-1234] - New feature 47 | - Merge strategy: Rebase and Merge is preffered for maintaining a linear project history. 48 | 49 | ## Project Structure 50 | 51 | | Name | Description | 52 | | --- | --- | 53 | | **Application/Services**/ | Application based services will be defined here, such as logging, network, server... | 54 | | **Configs**/ | Everything relative to build and environment configuration will be defined here | 55 | | **Managers**/ | Managers will be put here such as LoggerManager, UtilityManager... | 56 | | **Network**/ | Network related implementations will be defined here. You can find network related developments under feature/adesso-network branch. If you want to use it, you can merge it to develop easily. | 57 | | **Scenes**/ | Application related scenes will be defined here, such as navigation viewcontrollers, storyboards... | 58 | | **Utility**/ | Extensions, final classes etc. will be putt here | 59 | | **Resources**/ | Images, icons, assets, fonts, Mocks, `Localizable.strings`... 60 | 61 | ## Workspace Preparing 62 | 63 | #### Networking Layer (Optional) 64 | 65 | - If you wish to use an `async-await network layer` in your application 66 | - you can merge the `BSU-0020` optional branch. This is an optional feature, and merging it into your codebase will enable the use of async-await for network requests. 67 | 68 | ```shell 69 | # switch to the "develop" branch 70 | git checkout develop 71 | 72 | # fetch the latest version of the "BSU-0020" branch 73 | git fetch origin BSU-0020 74 | 75 | # merge the "BSU-0020" branch into the "develop" branch 76 | git merge origin/BSU-0020 77 | ``` 78 | 79 | then you can start the workspace preparing. 80 | 81 | - On the directory of `{project_root}/scripts/installation`, via terminal 82 | - run `./rename-project.swift "$NEW_PROJECT_NAME"` to change project name. 83 | - run `sh install-githooks.sh` to install git-hooks into your project. Includes following git hooks; Git hooks include SwiftLint validation, git message character limitation and issue-id check 84 | - pre-commit: This hook provides swiftlint control to detect errors quickly before commit. 85 | - commit-msg: This hook checks that messages must have a minimum 50 characters. It also tells it should contain an issue tag. Ticket id must be between square brackets and [ticketid] separated by hyphens. See example: "[ISSUE-123] commit message" or "[JIRA-56] - commit message" 86 | 87 | #### Encryption Choice (Optional) 88 | 89 | - If you wish to silence App Store Connect's "Encryption Ask" or don't use any external encryption in your project, you can define `ITSAppUsesNonExemptEncryption` key as `NO` in the Info.plist. [Learn More](https://developer.apple.com/documentation/bundleresources/information_property_list/itsappusesnonexemptencryption) 90 | 91 | 92 | ## List of Frameworks 93 | 94 | | Framework | Description | 95 | | ------------------------------- | --------------------------------------------------------------------- | 96 | | [SwiftLint](https://github.com/realm/SwiftLint) | A tool to enforce Swift style and conventions. | 97 | | [Pulse](https://github.com/kean/Pulse) | Pulse is a powerful logging system for Apple Platforms. Native. Built with SwiftUI. | 98 | | [CocoaLumberjack](https://github.com/CocoaLumberjack/CocoaLumberjack) | Powerful & flexible logging framework. | 99 | 100 | ## Useful Tools and Resources 101 | 102 | - [SwiftLint](https://github.com/realm/SwiftLint) - A tool to enforce Swift style and conventions. 103 | - [TestFlight](https://help.apple.com/itunes-connect/developer/#/devdc42b26b8) - TestFlight beta testing lets you distribute beta builds of your app to testers and collect feedback. 104 | - [Appcenter](https://appcenter.ms/) - Continuously build, test, release, and monitor apps for every platform. 105 | 106 | ## Join the crew! 107 | 108 | [Act now to join][linkedin/jobs] our team and become an adessi — enjoy a Great Place to Work! 109 | 110 | ## License 111 | 112 | ``` 113 | Copyright 2020 adesso Turkey 114 | 115 | Licensed under the Apache License, Version 2.0 (the "License"); 116 | you may not use this file except in compliance with the License. 117 | You may obtain a copy of the License at 118 | 119 | http://www.apache.org/licenses/LICENSE-2.0 120 | 121 | Unless required by applicable law or agreed to in writing, software 122 | distributed under the License is distributed on an "AS IS" BASIS, 123 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 124 | See the License for the specific language governing permissions and 125 | limitations under the License. 126 | ``` 127 | 128 | [linkedin/jobs]: https://www.linkedin.com/company/adessoturkey/jobs/ 129 | -------------------------------------------------------------------------------- /BoilerPlateSwiftUI.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 54; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 18CADB3228A92CDC007FC2C8 /* MainView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3128A92CDC007FC2C8 /* MainView.swift */; }; 11 | 18CADB3528A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3428A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift */; }; 12 | 18CADB3828A93B4F007FC2C8 /* HomeView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3728A93B4F007FC2C8 /* HomeView.swift */; }; 13 | 18CADB3A28A97CC8007FC2C8 /* BoilerPlateSwiftUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3928A97CC8007FC2C8 /* BoilerPlateSwiftUITests.swift */; }; 14 | 18CADB3C28A97CDF007FC2C8 /* BoilerPlateSwiftUIUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3B28A97CDF007FC2C8 /* BoilerPlateSwiftUIUITests.swift */; }; 15 | 26BCDA102579826700096894 /* LoggerManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA0F2579826700096894 /* LoggerManager.swift */; }; 16 | 26BCDA202579833600096894 /* Logger.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA1F2579833600096894 /* Logger.swift */; }; 17 | 26BCDA252579852700096894 /* LoggingService.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA242579852700096894 /* LoggingService.swift */; }; 18 | 26BCDA2A2579857E00096894 /* UIApplicationExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA292579857E00096894 /* UIApplicationExtension.swift */; }; 19 | 26BCDA2F2579859500096894 /* UIDeviceExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA2E2579859500096894 /* UIDeviceExtension.swift */; }; 20 | 26C4C62525769BE400358DAE /* Configuration.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26C4C62425769BE400358DAE /* Configuration.swift */; }; 21 | 26C4C7012578BFE600358DAE /* sample-data.json in Resources */ = {isa = PBXBuildFile; fileRef = 26C4C7002578BFE600358DAE /* sample-data.json */; }; 22 | 2F56AE86256E44730007D0A2 /* UICollectionViewExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE85256E44730007D0A2 /* UICollectionViewExtensions.swift */; }; 23 | 2F56AE88256E44A10007D0A2 /* UITableViewCellExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE87256E44A10007D0A2 /* UITableViewCellExtensions.swift */; }; 24 | 2F56AE8A256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE89256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift */; }; 25 | 2F56AE8C256E44F00007D0A2 /* UIViewControllerExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE8B256E44F00007D0A2 /* UIViewControllerExtensions.swift */; }; 26 | 2F56AE8E256E487F0007D0A2 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE8D256E487F0007D0A2 /* StringExtensions.swift */; }; 27 | 2F56AE92256E4CD30007D0A2 /* Colors.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE91256E4CD30007D0A2 /* Colors.xcassets */; }; 28 | 2F56AE94256E65910007D0A2 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE93256E65910007D0A2 /* Images.xcassets */; }; 29 | 2F56AE9C256E6EF70007D0A2 /* Icons.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE9B256E6EF70007D0A2 /* Icons.xcassets */; }; 30 | 2FCDE0FF2565722600203445 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2FCDE0FE2565722600203445 /* Assets.xcassets */; }; 31 | 2FCDE1572566AE2700203445 /* UITableViewExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2FCDE1562566AE2700203445 /* UITableViewExtensions.swift */; }; 32 | 720A19F829E6BCF600265401 /* ArrayExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 720A19F729E6BCF600265401 /* ArrayExtensions.swift */; }; 33 | 7259FCBB299EAD3300BF8309 /* UIViewControllerExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE8B256E44F00007D0A2 /* UIViewControllerExtensions.swift */; }; 34 | 7259FCBC299EAD3300BF8309 /* UICollectionViewExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE85256E44730007D0A2 /* UICollectionViewExtensions.swift */; }; 35 | 7259FCBD299EAD3300BF8309 /* ImagePicker.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4408F29965134004D1FC5 /* ImagePicker.swift */; }; 36 | 7259FCBE299EAD3300BF8309 /* StringExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE8D256E487F0007D0A2 /* StringExtensions.swift */; }; 37 | 7259FCBF299EAD3300BF8309 /* MainView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3128A92CDC007FC2C8 /* MainView.swift */; }; 38 | 7259FCC0299EAD3300BF8309 /* UICollectionViewCellExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE89256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift */; }; 39 | 7259FCC1299EAD3300BF8309 /* UIApplicationExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA292579857E00096894 /* UIApplicationExtension.swift */; }; 40 | 7259FCC2299EAD3300BF8309 /* NewPhotoPickerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4409529966B1C004D1FC5 /* NewPhotoPickerView.swift */; }; 41 | 7259FCC3299EAD3300BF8309 /* Configuration.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26C4C62425769BE400358DAE /* Configuration.swift */; }; 42 | 7259FCC5299EAD3300BF8309 /* LoggingService.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA242579852700096894 /* LoggingService.swift */; }; 43 | 7259FCC6299EAD3300BF8309 /* LoggerManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA0F2579826700096894 /* LoggerManager.swift */; }; 44 | 7259FCC8299EAD3300BF8309 /* URLSessionAutoLogging.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72EB01A5299E39D700DF6C24 /* URLSessionAutoLogging.swift */; }; 45 | 7259FCC9299EAD3300BF8309 /* ImagePickerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B44091299654B5004D1FC5 /* ImagePickerView.swift */; }; 46 | 7259FCCA299EAD3300BF8309 /* Logger.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA1F2579833600096894 /* Logger.swift */; }; 47 | 7259FCCB299EAD3300BF8309 /* BoilerPlateSwiftUIApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3428A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift */; }; 48 | 7259FCCC299EAD3300BF8309 /* UIImagePickerControllerSourceTypeExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4409729967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift */; }; 49 | 7259FCCD299EAD3300BF8309 /* BigButtonTextModifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B440932996688B004D1FC5 /* BigButtonTextModifier.swift */; }; 50 | 7259FCCE299EAD3300BF8309 /* OnFirstAppearModifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = D1AC819628F69C4500E5B0AE /* OnFirstAppearModifier.swift */; }; 51 | 7259FCCF299EAD3300BF8309 /* UITableViewExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2FCDE1562566AE2700203445 /* UITableViewExtensions.swift */; }; 52 | 7259FCD0299EAD3300BF8309 /* UITableViewCellExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2F56AE87256E44A10007D0A2 /* UITableViewCellExtensions.swift */; }; 53 | 7259FCD1299EAD3300BF8309 /* UIDeviceExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 26BCDA2E2579859500096894 /* UIDeviceExtension.swift */; }; 54 | 7259FCD2299EAD3300BF8309 /* HomeView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18CADB3728A93B4F007FC2C8 /* HomeView.swift */; }; 55 | 7259FCD4299EAD3300BF8309 /* PulseUI in Frameworks */ = {isa = PBXBuildFile; productRef = 7259FCB9299EAD3300BF8309 /* PulseUI */; }; 56 | 7259FCD5299EAD3300BF8309 /* Pulse in Frameworks */ = {isa = PBXBuildFile; productRef = 7259FCB7299EAD3300BF8309 /* Pulse */; }; 57 | 7259FCD6299EAD3300BF8309 /* CocoaLumberjackSwift in Frameworks */ = {isa = PBXBuildFile; productRef = 7259FCB5299EAD3300BF8309 /* CocoaLumberjackSwift */; }; 58 | 7259FCD8299EAD3300BF8309 /* Colors.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE91256E4CD30007D0A2 /* Colors.xcassets */; }; 59 | 7259FCD9299EAD3300BF8309 /* sample-data.json in Resources */ = {isa = PBXBuildFile; fileRef = 26C4C7002578BFE600358DAE /* sample-data.json */; }; 60 | 7259FCDA299EAD3300BF8309 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE93256E65910007D0A2 /* Images.xcassets */; }; 61 | 7259FCDB299EAD3300BF8309 /* Localizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F856462F28D12DC90015D3DF /* Localizable.strings */; }; 62 | 7259FCDD299EAD3300BF8309 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2FCDE0FE2565722600203445 /* Assets.xcassets */; }; 63 | 7259FCDE299EAD3300BF8309 /* Icons.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2F56AE9B256E6EF70007D0A2 /* Icons.xcassets */; }; 64 | 727273812A1CBAB60050D236 /* MapApplication.swift in Sources */ = {isa = PBXBuildFile; fileRef = 727273802A1CBAB60050D236 /* MapApplication.swift */; }; 65 | 72A7BE1C2A1CA5E000D66097 /* URLExtensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72A7BE1B2A1CA5E000D66097 /* URLExtensions.swift */; }; 66 | 72A7BE1F2A1CA9C300D66097 /* URLDefinitions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72A7BE1E2A1CA9C300D66097 /* URLDefinitions.swift */; }; 67 | 72B4409029965134004D1FC5 /* ImagePicker.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4408F29965134004D1FC5 /* ImagePicker.swift */; }; 68 | 72B44092299654B5004D1FC5 /* ImagePickerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B44091299654B5004D1FC5 /* ImagePickerView.swift */; }; 69 | 72B440942996688B004D1FC5 /* BigButtonTextModifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B440932996688B004D1FC5 /* BigButtonTextModifier.swift */; }; 70 | 72B4409629966B1C004D1FC5 /* NewPhotoPickerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4409529966B1C004D1FC5 /* NewPhotoPickerView.swift */; }; 71 | 72B4409829967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72B4409729967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift */; }; 72 | 72C4BE3E29A6376C0032CFF2 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72C4BE3D29A6376C0032CFF2 /* AppDelegate.swift */; }; 73 | 72C4BE3F29A637E20032CFF2 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72C4BE3D29A6376C0032CFF2 /* AppDelegate.swift */; }; 74 | 72EB01A6299E39D700DF6C24 /* URLSessionAutoLogging.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72EB01A5299E39D700DF6C24 /* URLSessionAutoLogging.swift */; }; 75 | 72EB01B4299E57AB00DF6C24 /* Pulse in Frameworks */ = {isa = PBXBuildFile; productRef = 72EB01B3299E57AB00DF6C24 /* Pulse */; }; 76 | 72EB01B6299E57AB00DF6C24 /* PulseUI in Frameworks */ = {isa = PBXBuildFile; productRef = 72EB01B5299E57AB00DF6C24 /* PulseUI */; }; 77 | D1703A4F28C9CDA70071EF00 /* CocoaLumberjackSwift in Frameworks */ = {isa = PBXBuildFile; productRef = D1703A4E28C9CDA70071EF00 /* CocoaLumberjackSwift */; }; 78 | D1AC819728F69C4500E5B0AE /* OnFirstAppearModifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = D1AC819628F69C4500E5B0AE /* OnFirstAppearModifier.swift */; }; 79 | F856462D28D12DC90015D3DF /* Localizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F856462F28D12DC90015D3DF /* Localizable.strings */; }; 80 | /* End PBXBuildFile section */ 81 | 82 | /* Begin PBXContainerItemProxy section */ 83 | 2FCDE1092565722600203445 /* PBXContainerItemProxy */ = { 84 | isa = PBXContainerItemProxy; 85 | containerPortal = 2FCDE0EA2565722400203445 /* Project object */; 86 | proxyType = 1; 87 | remoteGlobalIDString = 2FCDE0F12565722400203445; 88 | remoteInfo = "boilerplate-ios-swiftui"; 89 | }; 90 | 2FCDE1142565722600203445 /* PBXContainerItemProxy */ = { 91 | isa = PBXContainerItemProxy; 92 | containerPortal = 2FCDE0EA2565722400203445 /* Project object */; 93 | proxyType = 1; 94 | remoteGlobalIDString = 2FCDE0F12565722400203445; 95 | remoteInfo = "boilerplate-ios-swiftui"; 96 | }; 97 | /* End PBXContainerItemProxy section */ 98 | 99 | /* Begin PBXFileReference section */ 100 | 18CADB3128A92CDC007FC2C8 /* MainView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainView.swift; sourceTree = ""; }; 101 | 18CADB3428A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BoilerPlateSwiftUIApp.swift; sourceTree = ""; }; 102 | 18CADB3728A93B4F007FC2C8 /* HomeView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HomeView.swift; sourceTree = ""; }; 103 | 18CADB3928A97CC8007FC2C8 /* BoilerPlateSwiftUITests.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BoilerPlateSwiftUITests.swift; sourceTree = ""; }; 104 | 18CADB3B28A97CDF007FC2C8 /* BoilerPlateSwiftUIUITests.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BoilerPlateSwiftUIUITests.swift; sourceTree = ""; }; 105 | 26BCDA0F2579826700096894 /* LoggerManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LoggerManager.swift; sourceTree = ""; }; 106 | 26BCDA1F2579833600096894 /* Logger.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Logger.swift; sourceTree = ""; }; 107 | 26BCDA242579852700096894 /* LoggingService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LoggingService.swift; sourceTree = ""; }; 108 | 26BCDA292579857E00096894 /* UIApplicationExtension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UIApplicationExtension.swift; sourceTree = ""; }; 109 | 26BCDA2E2579859500096894 /* UIDeviceExtension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UIDeviceExtension.swift; sourceTree = ""; }; 110 | 26C4C62425769BE400358DAE /* Configuration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Configuration.swift; sourceTree = ""; }; 111 | 26C4C7002578BFE600358DAE /* sample-data.json */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.json; path = "sample-data.json"; sourceTree = ""; }; 112 | 2F56AE85256E44730007D0A2 /* UICollectionViewExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UICollectionViewExtensions.swift; sourceTree = ""; }; 113 | 2F56AE87256E44A10007D0A2 /* UITableViewCellExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UITableViewCellExtensions.swift; sourceTree = ""; }; 114 | 2F56AE89256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UICollectionViewCellExtensions.swift; sourceTree = ""; }; 115 | 2F56AE8B256E44F00007D0A2 /* UIViewControllerExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UIViewControllerExtensions.swift; sourceTree = ""; }; 116 | 2F56AE8D256E487F0007D0A2 /* StringExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StringExtensions.swift; sourceTree = ""; }; 117 | 2F56AE91256E4CD30007D0A2 /* Colors.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Colors.xcassets; sourceTree = ""; }; 118 | 2F56AE93256E65910007D0A2 /* Images.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Images.xcassets; sourceTree = ""; }; 119 | 2F56AE9B256E6EF70007D0A2 /* Icons.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Icons.xcassets; sourceTree = ""; }; 120 | 2FCDE0F22565722400203445 /* BoilerPlateSwiftUI.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = BoilerPlateSwiftUI.app; sourceTree = BUILT_PRODUCTS_DIR; }; 121 | 2FCDE0FE2565722600203445 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 122 | 2FCDE1032565722600203445 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 123 | 2FCDE1082565722600203445 /* BoilerPlateSwiftUITests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = BoilerPlateSwiftUITests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 124 | 2FCDE10E2565722600203445 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 125 | 2FCDE1132565722600203445 /* BoilerPlateSwiftUIUITests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = BoilerPlateSwiftUIUITests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 126 | 2FCDE1192565722600203445 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 127 | 2FCDE1292566444C00203445 /* Development.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Development.xcconfig; sourceTree = ""; }; 128 | 2FCDE134256651EF00203445 /* Production.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Production.xcconfig; sourceTree = ""; }; 129 | 2FCDE1352566520A00203445 /* AppStore.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = AppStore.xcconfig; sourceTree = ""; }; 130 | 2FCDE1562566AE2700203445 /* UITableViewExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UITableViewExtensions.swift; sourceTree = ""; }; 131 | 720A19F729E6BCF600265401 /* ArrayExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ArrayExtensions.swift; sourceTree = ""; }; 132 | 7259FCE4299EAD3300BF8309 /* BoilerPlateSwiftUI-Pulse.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "BoilerPlateSwiftUI-Pulse.app"; sourceTree = BUILT_PRODUCTS_DIR; }; 133 | 727273802A1CBAB60050D236 /* MapApplication.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MapApplication.swift; sourceTree = ""; }; 134 | 72A7BE1B2A1CA5E000D66097 /* URLExtensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = URLExtensions.swift; sourceTree = ""; }; 135 | 72A7BE1E2A1CA9C300D66097 /* URLDefinitions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = URLDefinitions.swift; sourceTree = ""; }; 136 | 72B4408F29965134004D1FC5 /* ImagePicker.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImagePicker.swift; sourceTree = ""; }; 137 | 72B44091299654B5004D1FC5 /* ImagePickerView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImagePickerView.swift; sourceTree = ""; }; 138 | 72B440932996688B004D1FC5 /* BigButtonTextModifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BigButtonTextModifier.swift; sourceTree = ""; }; 139 | 72B4409529966B1C004D1FC5 /* NewPhotoPickerView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NewPhotoPickerView.swift; sourceTree = ""; }; 140 | 72B4409729967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UIImagePickerControllerSourceTypeExtension.swift; sourceTree = ""; }; 141 | 72C4BE3D29A6376C0032CFF2 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; 142 | 72EB01A5299E39D700DF6C24 /* URLSessionAutoLogging.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = URLSessionAutoLogging.swift; sourceTree = ""; }; 143 | D1AC819628F69C4500E5B0AE /* OnFirstAppearModifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = OnFirstAppearModifier.swift; sourceTree = ""; }; 144 | F856462E28D12DC90015D3DF /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/Localizable.strings; sourceTree = ""; }; 145 | F856463028D12DDD0015D3DF /* de */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = de; path = de.lproj/Localizable.strings; sourceTree = ""; }; 146 | F856463128D12DE80015D3DF /* tr */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = tr; path = tr.lproj/Localizable.strings; sourceTree = ""; }; 147 | /* End PBXFileReference section */ 148 | 149 | /* Begin PBXFrameworksBuildPhase section */ 150 | 2FCDE0EF2565722400203445 /* Frameworks */ = { 151 | isa = PBXFrameworksBuildPhase; 152 | buildActionMask = 2147483647; 153 | files = ( 154 | 72EB01B6299E57AB00DF6C24 /* PulseUI in Frameworks */, 155 | 72EB01B4299E57AB00DF6C24 /* Pulse in Frameworks */, 156 | D1703A4F28C9CDA70071EF00 /* CocoaLumberjackSwift in Frameworks */, 157 | ); 158 | runOnlyForDeploymentPostprocessing = 0; 159 | }; 160 | 2FCDE1052565722600203445 /* Frameworks */ = { 161 | isa = PBXFrameworksBuildPhase; 162 | buildActionMask = 2147483647; 163 | files = ( 164 | ); 165 | runOnlyForDeploymentPostprocessing = 0; 166 | }; 167 | 2FCDE1102565722600203445 /* Frameworks */ = { 168 | isa = PBXFrameworksBuildPhase; 169 | buildActionMask = 2147483647; 170 | files = ( 171 | ); 172 | runOnlyForDeploymentPostprocessing = 0; 173 | }; 174 | 7259FCD3299EAD3300BF8309 /* Frameworks */ = { 175 | isa = PBXFrameworksBuildPhase; 176 | buildActionMask = 2147483647; 177 | files = ( 178 | 7259FCD4299EAD3300BF8309 /* PulseUI in Frameworks */, 179 | 7259FCD5299EAD3300BF8309 /* Pulse in Frameworks */, 180 | 7259FCD6299EAD3300BF8309 /* CocoaLumberjackSwift in Frameworks */, 181 | ); 182 | runOnlyForDeploymentPostprocessing = 0; 183 | }; 184 | /* End PBXFrameworksBuildPhase section */ 185 | 186 | /* Begin PBXGroup section */ 187 | 18CADB2E28A92C80007FC2C8 /* Main */ = { 188 | isa = PBXGroup; 189 | children = ( 190 | 18CADB3128A92CDC007FC2C8 /* MainView.swift */, 191 | ); 192 | path = Main; 193 | sourceTree = ""; 194 | }; 195 | 18CADB3628A93B3F007FC2C8 /* Home */ = { 196 | isa = PBXGroup; 197 | children = ( 198 | 18CADB3728A93B4F007FC2C8 /* HomeView.swift */, 199 | 72B44091299654B5004D1FC5 /* ImagePickerView.swift */, 200 | 72B4409529966B1C004D1FC5 /* NewPhotoPickerView.swift */, 201 | ); 202 | path = Home; 203 | sourceTree = ""; 204 | }; 205 | 26BCDA36257A398600096894 /* Network */ = { 206 | isa = PBXGroup; 207 | children = ( 208 | ); 209 | path = Network; 210 | sourceTree = ""; 211 | }; 212 | 26C4C5632576519000358DAE /* Services */ = { 213 | isa = PBXGroup; 214 | children = ( 215 | 26BCDA242579852700096894 /* LoggingService.swift */, 216 | ); 217 | path = Services; 218 | sourceTree = ""; 219 | }; 220 | 26C4C58825766B4400358DAE /* Managers */ = { 221 | isa = PBXGroup; 222 | children = ( 223 | 26BCDA0F2579826700096894 /* LoggerManager.swift */, 224 | 72EB01A5299E39D700DF6C24 /* URLSessionAutoLogging.swift */, 225 | ); 226 | path = Managers; 227 | sourceTree = ""; 228 | }; 229 | 26C4C6FF2578BFE600358DAE /* Mocks */ = { 230 | isa = PBXGroup; 231 | children = ( 232 | 26C4C7002578BFE600358DAE /* sample-data.json */, 233 | ); 234 | path = Mocks; 235 | sourceTree = ""; 236 | }; 237 | 2FCDE0E92565722400203445 = { 238 | isa = PBXGroup; 239 | children = ( 240 | 2FCDE0F42565722400203445 /* BoilerPlateSwiftUI */, 241 | 2FCDE10B2565722600203445 /* BoilerPlateSwiftUITests */, 242 | 2FCDE1162565722600203445 /* BoilerPlateSwiftUIUITests */, 243 | 2FCDE0F32565722400203445 /* Products */, 244 | 72EB01A8299E3DDF00DF6C24 /* Frameworks */, 245 | ); 246 | sourceTree = ""; 247 | }; 248 | 2FCDE0F32565722400203445 /* Products */ = { 249 | isa = PBXGroup; 250 | children = ( 251 | 2FCDE0F22565722400203445 /* BoilerPlateSwiftUI.app */, 252 | 2FCDE1082565722600203445 /* BoilerPlateSwiftUITests.xctest */, 253 | 2FCDE1132565722600203445 /* BoilerPlateSwiftUIUITests.xctest */, 254 | 7259FCE4299EAD3300BF8309 /* BoilerPlateSwiftUI-Pulse.app */, 255 | ); 256 | name = Products; 257 | sourceTree = ""; 258 | }; 259 | 2FCDE0F42565722400203445 /* BoilerPlateSwiftUI */ = { 260 | isa = PBXGroup; 261 | children = ( 262 | 2FCDE1252565B96500203445 /* Application */, 263 | 2FCDE1282566415900203445 /* Configs */, 264 | 26C4C58825766B4400358DAE /* Managers */, 265 | 26BCDA36257A398600096894 /* Network */, 266 | 2FCDE1272566413F00203445 /* Scenes */, 267 | 2FCDE1262566412700203445 /* Resources */, 268 | 2FCDE13725665B5E00203445 /* Utility */, 269 | ); 270 | path = BoilerPlateSwiftUI; 271 | sourceTree = ""; 272 | }; 273 | 2FCDE10B2565722600203445 /* BoilerPlateSwiftUITests */ = { 274 | isa = PBXGroup; 275 | children = ( 276 | 18CADB3928A97CC8007FC2C8 /* BoilerPlateSwiftUITests.swift */, 277 | 2FCDE10E2565722600203445 /* Info.plist */, 278 | ); 279 | path = BoilerPlateSwiftUITests; 280 | sourceTree = ""; 281 | }; 282 | 2FCDE1162565722600203445 /* BoilerPlateSwiftUIUITests */ = { 283 | isa = PBXGroup; 284 | children = ( 285 | 18CADB3B28A97CDF007FC2C8 /* BoilerPlateSwiftUIUITests.swift */, 286 | 2FCDE1192565722600203445 /* Info.plist */, 287 | ); 288 | path = BoilerPlateSwiftUIUITests; 289 | sourceTree = ""; 290 | }; 291 | 2FCDE1252565B96500203445 /* Application */ = { 292 | isa = PBXGroup; 293 | children = ( 294 | 26C4C5632576519000358DAE /* Services */, 295 | 18CADB3428A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift */, 296 | 72C4BE3D29A6376C0032CFF2 /* AppDelegate.swift */, 297 | ); 298 | path = Application; 299 | sourceTree = ""; 300 | }; 301 | 2FCDE1262566412700203445 /* Resources */ = { 302 | isa = PBXGroup; 303 | children = ( 304 | 72A7BE1D2A1CA9B700D66097 /* Constants */, 305 | 26C4C6FF2578BFE600358DAE /* Mocks */, 306 | 2FCDE0FE2565722600203445 /* Assets.xcassets */, 307 | 2F56AE91256E4CD30007D0A2 /* Colors.xcassets */, 308 | 2F56AE9B256E6EF70007D0A2 /* Icons.xcassets */, 309 | 2F56AE93256E65910007D0A2 /* Images.xcassets */, 310 | 2FCDE1032565722600203445 /* Info.plist */, 311 | F856462F28D12DC90015D3DF /* Localizable.strings */, 312 | ); 313 | path = Resources; 314 | sourceTree = ""; 315 | }; 316 | 2FCDE1272566413F00203445 /* Scenes */ = { 317 | isa = PBXGroup; 318 | children = ( 319 | 18CADB2E28A92C80007FC2C8 /* Main */, 320 | 18CADB3628A93B3F007FC2C8 /* Home */, 321 | 9D57D89A29BB7DD1002400BB /* Launch */, 322 | ); 323 | path = Scenes; 324 | sourceTree = ""; 325 | }; 326 | 2FCDE1282566415900203445 /* Configs */ = { 327 | isa = PBXGroup; 328 | children = ( 329 | 2FCDE1292566444C00203445 /* Development.xcconfig */, 330 | 2FCDE134256651EF00203445 /* Production.xcconfig */, 331 | 2FCDE1352566520A00203445 /* AppStore.xcconfig */, 332 | 26C4C62425769BE400358DAE /* Configuration.swift */, 333 | ); 334 | path = Configs; 335 | sourceTree = ""; 336 | }; 337 | 2FCDE13725665B5E00203445 /* Utility */ = { 338 | isa = PBXGroup; 339 | children = ( 340 | 72B4408E29965119004D1FC5 /* ViewRepresentables */, 341 | D1AC819828F69C9600E5B0AE /* ViewModifiers */, 342 | 2FCDE13825665B7200203445 /* Extensions */, 343 | 26BCDA1F2579833600096894 /* Logger.swift */, 344 | ); 345 | path = Utility; 346 | sourceTree = ""; 347 | }; 348 | 2FCDE13825665B7200203445 /* Extensions */ = { 349 | isa = PBXGroup; 350 | children = ( 351 | 2FCDE1562566AE2700203445 /* UITableViewExtensions.swift */, 352 | 2F56AE87256E44A10007D0A2 /* UITableViewCellExtensions.swift */, 353 | 2F56AE85256E44730007D0A2 /* UICollectionViewExtensions.swift */, 354 | 2F56AE89256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift */, 355 | 2F56AE8B256E44F00007D0A2 /* UIViewControllerExtensions.swift */, 356 | 2F56AE8D256E487F0007D0A2 /* StringExtensions.swift */, 357 | 26BCDA292579857E00096894 /* UIApplicationExtension.swift */, 358 | 26BCDA2E2579859500096894 /* UIDeviceExtension.swift */, 359 | 72B4409729967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift */, 360 | 720A19F729E6BCF600265401 /* ArrayExtensions.swift */, 361 | 72A7BE1B2A1CA5E000D66097 /* URLExtensions.swift */, 362 | ); 363 | path = Extensions; 364 | sourceTree = ""; 365 | }; 366 | 72A7BE1D2A1CA9B700D66097 /* Constants */ = { 367 | isa = PBXGroup; 368 | children = ( 369 | 72A7BE1E2A1CA9C300D66097 /* URLDefinitions.swift */, 370 | 727273802A1CBAB60050D236 /* MapApplication.swift */, 371 | ); 372 | path = Constants; 373 | sourceTree = ""; 374 | }; 375 | 72B4408E29965119004D1FC5 /* ViewRepresentables */ = { 376 | isa = PBXGroup; 377 | children = ( 378 | 72B4408F29965134004D1FC5 /* ImagePicker.swift */, 379 | ); 380 | path = ViewRepresentables; 381 | sourceTree = ""; 382 | }; 383 | 72EB01A8299E3DDF00DF6C24 /* Frameworks */ = { 384 | isa = PBXGroup; 385 | children = ( 386 | ); 387 | name = Frameworks; 388 | sourceTree = ""; 389 | }; 390 | 9D57D89A29BB7DD1002400BB /* Launch */ = { 391 | isa = PBXGroup; 392 | children = ( 393 | ); 394 | name = Launch; 395 | path = ../Launch; 396 | sourceTree = ""; 397 | }; 398 | D1AC819828F69C9600E5B0AE /* ViewModifiers */ = { 399 | isa = PBXGroup; 400 | children = ( 401 | D1AC819628F69C4500E5B0AE /* OnFirstAppearModifier.swift */, 402 | 72B440932996688B004D1FC5 /* BigButtonTextModifier.swift */, 403 | ); 404 | path = ViewModifiers; 405 | sourceTree = ""; 406 | }; 407 | /* End PBXGroup section */ 408 | 409 | /* Begin PBXNativeTarget section */ 410 | 2FCDE0F12565722400203445 /* BoilerPlateSwiftUI */ = { 411 | isa = PBXNativeTarget; 412 | buildConfigurationList = 2FCDE11C2565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUI" */; 413 | buildPhases = ( 414 | 2FCDE0EE2565722400203445 /* Sources */, 415 | 2FCDE0EF2565722400203445 /* Frameworks */, 416 | 2FCDE0F02565722400203445 /* Resources */, 417 | 26C4C4452575230A00358DAE /* Swiftlint */, 418 | ); 419 | buildRules = ( 420 | ); 421 | dependencies = ( 422 | ); 423 | name = BoilerPlateSwiftUI; 424 | packageProductDependencies = ( 425 | D1703A4E28C9CDA70071EF00 /* CocoaLumberjackSwift */, 426 | 72EB01B3299E57AB00DF6C24 /* Pulse */, 427 | 72EB01B5299E57AB00DF6C24 /* PulseUI */, 428 | ); 429 | productName = "boilerplate-ios-swiftui"; 430 | productReference = 2FCDE0F22565722400203445 /* BoilerPlateSwiftUI.app */; 431 | productType = "com.apple.product-type.application"; 432 | }; 433 | 2FCDE1072565722600203445 /* BoilerPlateSwiftUITests */ = { 434 | isa = PBXNativeTarget; 435 | buildConfigurationList = 2FCDE11F2565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUITests" */; 436 | buildPhases = ( 437 | 2FCDE1042565722600203445 /* Sources */, 438 | 2FCDE1052565722600203445 /* Frameworks */, 439 | 2FCDE1062565722600203445 /* Resources */, 440 | ); 441 | buildRules = ( 442 | ); 443 | dependencies = ( 444 | 2FCDE10A2565722600203445 /* PBXTargetDependency */, 445 | ); 446 | name = BoilerPlateSwiftUITests; 447 | packageProductDependencies = ( 448 | ); 449 | productName = "boilerplate-ios-swiftuiTests"; 450 | productReference = 2FCDE1082565722600203445 /* BoilerPlateSwiftUITests.xctest */; 451 | productType = "com.apple.product-type.bundle.unit-test"; 452 | }; 453 | 2FCDE1122565722600203445 /* BoilerPlateSwiftUIUITests */ = { 454 | isa = PBXNativeTarget; 455 | buildConfigurationList = 2FCDE1222565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUIUITests" */; 456 | buildPhases = ( 457 | 2FCDE10F2565722600203445 /* Sources */, 458 | 2FCDE1102565722600203445 /* Frameworks */, 459 | 2FCDE1112565722600203445 /* Resources */, 460 | ); 461 | buildRules = ( 462 | ); 463 | dependencies = ( 464 | 2FCDE1152565722600203445 /* PBXTargetDependency */, 465 | ); 466 | name = BoilerPlateSwiftUIUITests; 467 | productName = "boilerplate-ios-swiftuiUITests"; 468 | productReference = 2FCDE1132565722600203445 /* BoilerPlateSwiftUIUITests.xctest */; 469 | productType = "com.apple.product-type.bundle.ui-testing"; 470 | }; 471 | 7259FCB4299EAD3300BF8309 /* BoilerPlateSwiftUI-Pulse */ = { 472 | isa = PBXNativeTarget; 473 | buildConfigurationList = 7259FCE0299EAD3300BF8309 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUI-Pulse" */; 474 | buildPhases = ( 475 | 7259FCBA299EAD3300BF8309 /* Sources */, 476 | 7259FCD3299EAD3300BF8309 /* Frameworks */, 477 | 7259FCD7299EAD3300BF8309 /* Resources */, 478 | 7259FCDF299EAD3300BF8309 /* Swiftlint */, 479 | ); 480 | buildRules = ( 481 | ); 482 | dependencies = ( 483 | ); 484 | name = "BoilerPlateSwiftUI-Pulse"; 485 | packageProductDependencies = ( 486 | 7259FCB5299EAD3300BF8309 /* CocoaLumberjackSwift */, 487 | 7259FCB7299EAD3300BF8309 /* Pulse */, 488 | 7259FCB9299EAD3300BF8309 /* PulseUI */, 489 | ); 490 | productName = "boilerplate-ios-swiftui"; 491 | productReference = 7259FCE4299EAD3300BF8309 /* BoilerPlateSwiftUI-Pulse.app */; 492 | productType = "com.apple.product-type.application"; 493 | }; 494 | /* End PBXNativeTarget section */ 495 | 496 | /* Begin PBXProject section */ 497 | 2FCDE0EA2565722400203445 /* Project object */ = { 498 | isa = PBXProject; 499 | attributes = { 500 | LastSwiftUpdateCheck = 1130; 501 | LastUpgradeCheck = 1420; 502 | ORGANIZATIONNAME = "Adesso Turkey"; 503 | TargetAttributes = { 504 | 2FCDE0F12565722400203445 = { 505 | CreatedOnToolsVersion = 11.3.1; 506 | }; 507 | 2FCDE1072565722600203445 = { 508 | CreatedOnToolsVersion = 11.3.1; 509 | TestTargetID = 2FCDE0F12565722400203445; 510 | }; 511 | 2FCDE1122565722600203445 = { 512 | CreatedOnToolsVersion = 11.3.1; 513 | LastSwiftMigration = 1340; 514 | TestTargetID = 2FCDE0F12565722400203445; 515 | }; 516 | }; 517 | }; 518 | buildConfigurationList = 2FCDE0ED2565722400203445 /* Build configuration list for PBXProject "BoilerPlateSwiftUI" */; 519 | compatibilityVersion = "Xcode 9.3"; 520 | developmentRegion = en; 521 | hasScannedForEncodings = 0; 522 | knownRegions = ( 523 | en, 524 | Base, 525 | de, 526 | tr, 527 | ); 528 | mainGroup = 2FCDE0E92565722400203445; 529 | packageReferences = ( 530 | D1703A4D28C9CDA70071EF00 /* XCRemoteSwiftPackageReference "CocoaLumberjack" */, 531 | 72EB016E299E310000DF6C24 /* XCRemoteSwiftPackageReference "Pulse" */, 532 | ); 533 | productRefGroup = 2FCDE0F32565722400203445 /* Products */; 534 | projectDirPath = ""; 535 | projectRoot = ""; 536 | targets = ( 537 | 2FCDE0F12565722400203445 /* BoilerPlateSwiftUI */, 538 | 7259FCB4299EAD3300BF8309 /* BoilerPlateSwiftUI-Pulse */, 539 | 2FCDE1072565722600203445 /* BoilerPlateSwiftUITests */, 540 | 2FCDE1122565722600203445 /* BoilerPlateSwiftUIUITests */, 541 | ); 542 | }; 543 | /* End PBXProject section */ 544 | 545 | /* Begin PBXResourcesBuildPhase section */ 546 | 2FCDE0F02565722400203445 /* Resources */ = { 547 | isa = PBXResourcesBuildPhase; 548 | buildActionMask = 2147483647; 549 | files = ( 550 | 2F56AE92256E4CD30007D0A2 /* Colors.xcassets in Resources */, 551 | 26C4C7012578BFE600358DAE /* sample-data.json in Resources */, 552 | 2F56AE94256E65910007D0A2 /* Images.xcassets in Resources */, 553 | F856462D28D12DC90015D3DF /* Localizable.strings in Resources */, 554 | 2FCDE0FF2565722600203445 /* Assets.xcassets in Resources */, 555 | 2F56AE9C256E6EF70007D0A2 /* Icons.xcassets in Resources */, 556 | ); 557 | runOnlyForDeploymentPostprocessing = 0; 558 | }; 559 | 2FCDE1062565722600203445 /* Resources */ = { 560 | isa = PBXResourcesBuildPhase; 561 | buildActionMask = 2147483647; 562 | files = ( 563 | ); 564 | runOnlyForDeploymentPostprocessing = 0; 565 | }; 566 | 2FCDE1112565722600203445 /* Resources */ = { 567 | isa = PBXResourcesBuildPhase; 568 | buildActionMask = 2147483647; 569 | files = ( 570 | ); 571 | runOnlyForDeploymentPostprocessing = 0; 572 | }; 573 | 7259FCD7299EAD3300BF8309 /* Resources */ = { 574 | isa = PBXResourcesBuildPhase; 575 | buildActionMask = 2147483647; 576 | files = ( 577 | 7259FCD8299EAD3300BF8309 /* Colors.xcassets in Resources */, 578 | 7259FCD9299EAD3300BF8309 /* sample-data.json in Resources */, 579 | 7259FCDA299EAD3300BF8309 /* Images.xcassets in Resources */, 580 | 7259FCDB299EAD3300BF8309 /* Localizable.strings in Resources */, 581 | 7259FCDD299EAD3300BF8309 /* Assets.xcassets in Resources */, 582 | 7259FCDE299EAD3300BF8309 /* Icons.xcassets in Resources */, 583 | ); 584 | runOnlyForDeploymentPostprocessing = 0; 585 | }; 586 | /* End PBXResourcesBuildPhase section */ 587 | 588 | /* Begin PBXShellScriptBuildPhase section */ 589 | 26C4C4452575230A00358DAE /* Swiftlint */ = { 590 | isa = PBXShellScriptBuildPhase; 591 | alwaysOutOfDate = 1; 592 | buildActionMask = 2147483647; 593 | files = ( 594 | ); 595 | inputFileListPaths = ( 596 | ); 597 | inputPaths = ( 598 | ); 599 | name = Swiftlint; 600 | outputFileListPaths = ( 601 | ); 602 | outputPaths = ( 603 | ); 604 | runOnlyForDeploymentPostprocessing = 0; 605 | shellPath = /bin/sh; 606 | shellScript = "export PATH=${PATH}:/opt/homebrew/bin:/usr/local/bin\nif which swiftlint > /dev/null; then\n swiftlint\nelse\n echo \"warning: SwiftLint not installed, download from https://github.com/realm/SwiftLint\"\nfi\n"; 607 | }; 608 | 7259FCDF299EAD3300BF8309 /* Swiftlint */ = { 609 | isa = PBXShellScriptBuildPhase; 610 | alwaysOutOfDate = 1; 611 | buildActionMask = 2147483647; 612 | files = ( 613 | ); 614 | inputFileListPaths = ( 615 | ); 616 | inputPaths = ( 617 | ); 618 | name = Swiftlint; 619 | outputFileListPaths = ( 620 | ); 621 | outputPaths = ( 622 | ); 623 | runOnlyForDeploymentPostprocessing = 0; 624 | shellPath = /bin/sh; 625 | shellScript = "export PATH=${PATH}:/opt/homebrew/bin:/usr/local/bin\nif which swiftlint > /dev/null; then\n swiftlint\nelse\n echo \"warning: SwiftLint not installed, download from https://github.com/realm/SwiftLint\"\nfi\n"; 626 | }; 627 | /* End PBXShellScriptBuildPhase section */ 628 | 629 | /* Begin PBXSourcesBuildPhase section */ 630 | 2FCDE0EE2565722400203445 /* Sources */ = { 631 | isa = PBXSourcesBuildPhase; 632 | buildActionMask = 2147483647; 633 | files = ( 634 | 72A7BE1F2A1CA9C300D66097 /* URLDefinitions.swift in Sources */, 635 | 2F56AE8C256E44F00007D0A2 /* UIViewControllerExtensions.swift in Sources */, 636 | 2F56AE86256E44730007D0A2 /* UICollectionViewExtensions.swift in Sources */, 637 | 727273812A1CBAB60050D236 /* MapApplication.swift in Sources */, 638 | 72A7BE1C2A1CA5E000D66097 /* URLExtensions.swift in Sources */, 639 | 72B4409029965134004D1FC5 /* ImagePicker.swift in Sources */, 640 | 2F56AE8E256E487F0007D0A2 /* StringExtensions.swift in Sources */, 641 | 18CADB3228A92CDC007FC2C8 /* MainView.swift in Sources */, 642 | 2F56AE8A256E44BB0007D0A2 /* UICollectionViewCellExtensions.swift in Sources */, 643 | 72C4BE3E29A6376C0032CFF2 /* AppDelegate.swift in Sources */, 644 | 720A19F829E6BCF600265401 /* ArrayExtensions.swift in Sources */, 645 | 26BCDA2A2579857E00096894 /* UIApplicationExtension.swift in Sources */, 646 | 72B4409629966B1C004D1FC5 /* NewPhotoPickerView.swift in Sources */, 647 | 26C4C62525769BE400358DAE /* Configuration.swift in Sources */, 648 | 26BCDA252579852700096894 /* LoggingService.swift in Sources */, 649 | 26BCDA102579826700096894 /* LoggerManager.swift in Sources */, 650 | 72EB01A6299E39D700DF6C24 /* URLSessionAutoLogging.swift in Sources */, 651 | 72B44092299654B5004D1FC5 /* ImagePickerView.swift in Sources */, 652 | 26BCDA202579833600096894 /* Logger.swift in Sources */, 653 | 18CADB3528A932FE007FC2C8 /* BoilerPlateSwiftUIApp.swift in Sources */, 654 | 72B4409829967738004D1FC5 /* UIImagePickerControllerSourceTypeExtension.swift in Sources */, 655 | 72B440942996688B004D1FC5 /* BigButtonTextModifier.swift in Sources */, 656 | D1AC819728F69C4500E5B0AE /* OnFirstAppearModifier.swift in Sources */, 657 | 2FCDE1572566AE2700203445 /* UITableViewExtensions.swift in Sources */, 658 | 2F56AE88256E44A10007D0A2 /* UITableViewCellExtensions.swift in Sources */, 659 | 26BCDA2F2579859500096894 /* UIDeviceExtension.swift in Sources */, 660 | 18CADB3828A93B4F007FC2C8 /* HomeView.swift in Sources */, 661 | ); 662 | runOnlyForDeploymentPostprocessing = 0; 663 | }; 664 | 2FCDE1042565722600203445 /* Sources */ = { 665 | isa = PBXSourcesBuildPhase; 666 | buildActionMask = 2147483647; 667 | files = ( 668 | 18CADB3A28A97CC8007FC2C8 /* BoilerPlateSwiftUITests.swift in Sources */, 669 | ); 670 | runOnlyForDeploymentPostprocessing = 0; 671 | }; 672 | 2FCDE10F2565722600203445 /* Sources */ = { 673 | isa = PBXSourcesBuildPhase; 674 | buildActionMask = 2147483647; 675 | files = ( 676 | 18CADB3C28A97CDF007FC2C8 /* BoilerPlateSwiftUIUITests.swift in Sources */, 677 | ); 678 | runOnlyForDeploymentPostprocessing = 0; 679 | }; 680 | 7259FCBA299EAD3300BF8309 /* Sources */ = { 681 | isa = PBXSourcesBuildPhase; 682 | buildActionMask = 2147483647; 683 | files = ( 684 | 7259FCBB299EAD3300BF8309 /* UIViewControllerExtensions.swift in Sources */, 685 | 7259FCBC299EAD3300BF8309 /* UICollectionViewExtensions.swift in Sources */, 686 | 7259FCBD299EAD3300BF8309 /* ImagePicker.swift in Sources */, 687 | 7259FCBE299EAD3300BF8309 /* StringExtensions.swift in Sources */, 688 | 7259FCBF299EAD3300BF8309 /* MainView.swift in Sources */, 689 | 7259FCC0299EAD3300BF8309 /* UICollectionViewCellExtensions.swift in Sources */, 690 | 7259FCC1299EAD3300BF8309 /* UIApplicationExtension.swift in Sources */, 691 | 7259FCC2299EAD3300BF8309 /* NewPhotoPickerView.swift in Sources */, 692 | 7259FCC3299EAD3300BF8309 /* Configuration.swift in Sources */, 693 | 7259FCC5299EAD3300BF8309 /* LoggingService.swift in Sources */, 694 | 7259FCC6299EAD3300BF8309 /* LoggerManager.swift in Sources */, 695 | 7259FCC8299EAD3300BF8309 /* URLSessionAutoLogging.swift in Sources */, 696 | 7259FCC9299EAD3300BF8309 /* ImagePickerView.swift in Sources */, 697 | 7259FCCA299EAD3300BF8309 /* Logger.swift in Sources */, 698 | 7259FCCB299EAD3300BF8309 /* BoilerPlateSwiftUIApp.swift in Sources */, 699 | 7259FCCC299EAD3300BF8309 /* UIImagePickerControllerSourceTypeExtension.swift in Sources */, 700 | 7259FCCD299EAD3300BF8309 /* BigButtonTextModifier.swift in Sources */, 701 | 7259FCCE299EAD3300BF8309 /* OnFirstAppearModifier.swift in Sources */, 702 | 7259FCCF299EAD3300BF8309 /* UITableViewExtensions.swift in Sources */, 703 | 7259FCD0299EAD3300BF8309 /* UITableViewCellExtensions.swift in Sources */, 704 | 7259FCD1299EAD3300BF8309 /* UIDeviceExtension.swift in Sources */, 705 | 7259FCD2299EAD3300BF8309 /* HomeView.swift in Sources */, 706 | 72C4BE3F29A637E20032CFF2 /* AppDelegate.swift in Sources */, 707 | ); 708 | runOnlyForDeploymentPostprocessing = 0; 709 | }; 710 | /* End PBXSourcesBuildPhase section */ 711 | 712 | /* Begin PBXTargetDependency section */ 713 | 2FCDE10A2565722600203445 /* PBXTargetDependency */ = { 714 | isa = PBXTargetDependency; 715 | target = 2FCDE0F12565722400203445 /* BoilerPlateSwiftUI */; 716 | targetProxy = 2FCDE1092565722600203445 /* PBXContainerItemProxy */; 717 | }; 718 | 2FCDE1152565722600203445 /* PBXTargetDependency */ = { 719 | isa = PBXTargetDependency; 720 | target = 2FCDE0F12565722400203445 /* BoilerPlateSwiftUI */; 721 | targetProxy = 2FCDE1142565722600203445 /* PBXContainerItemProxy */; 722 | }; 723 | /* End PBXTargetDependency section */ 724 | 725 | /* Begin PBXVariantGroup section */ 726 | F856462F28D12DC90015D3DF /* Localizable.strings */ = { 727 | isa = PBXVariantGroup; 728 | children = ( 729 | F856462E28D12DC90015D3DF /* en */, 730 | F856463028D12DDD0015D3DF /* de */, 731 | F856463128D12DE80015D3DF /* tr */, 732 | ); 733 | name = Localizable.strings; 734 | sourceTree = ""; 735 | }; 736 | /* End PBXVariantGroup section */ 737 | 738 | /* Begin XCBuildConfiguration section */ 739 | 2F56AE97256E68000007D0A2 /* Development */ = { 740 | isa = XCBuildConfiguration; 741 | baseConfigurationReference = 2FCDE1292566444C00203445 /* Development.xcconfig */; 742 | buildSettings = { 743 | ALWAYS_SEARCH_USER_PATHS = NO; 744 | CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; 745 | CLANG_ANALYZER_NONNULL = YES; 746 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 747 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 748 | CLANG_CXX_LIBRARY = "libc++"; 749 | CLANG_ENABLE_MODULES = YES; 750 | CLANG_ENABLE_OBJC_ARC = YES; 751 | CLANG_ENABLE_OBJC_WEAK = YES; 752 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 753 | CLANG_WARN_BOOL_CONVERSION = YES; 754 | CLANG_WARN_COMMA = YES; 755 | CLANG_WARN_CONSTANT_CONVERSION = YES; 756 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 757 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 758 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 759 | CLANG_WARN_EMPTY_BODY = YES; 760 | CLANG_WARN_ENUM_CONVERSION = YES; 761 | CLANG_WARN_INFINITE_RECURSION = YES; 762 | CLANG_WARN_INT_CONVERSION = YES; 763 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 764 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 765 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 766 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 767 | CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; 768 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 769 | CLANG_WARN_STRICT_PROTOTYPES = YES; 770 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 771 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 772 | CLANG_WARN_UNREACHABLE_CODE = YES; 773 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 774 | COPY_PHASE_STRIP = NO; 775 | DEBUG_INFORMATION_FORMAT = dwarf; 776 | ENABLE_STRICT_OBJC_MSGSEND = YES; 777 | ENABLE_TESTABILITY = YES; 778 | ENABLE_TESTING_SEARCH_PATHS = NO; 779 | GCC_C_LANGUAGE_STANDARD = gnu11; 780 | GCC_DYNAMIC_NO_PIC = NO; 781 | GCC_NO_COMMON_BLOCKS = YES; 782 | GCC_OPTIMIZATION_LEVEL = 0; 783 | GCC_PREPROCESSOR_DEFINITIONS = ( 784 | "DEBUG=1", 785 | "$(inherited)", 786 | ); 787 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 788 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 789 | GCC_WARN_UNDECLARED_SELECTOR = YES; 790 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 791 | GCC_WARN_UNUSED_FUNCTION = YES; 792 | GCC_WARN_UNUSED_VARIABLE = YES; 793 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 794 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 795 | MTL_FAST_MATH = YES; 796 | ONLY_ACTIVE_ARCH = YES; 797 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 798 | SDKROOT = iphoneos; 799 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 800 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 801 | }; 802 | name = Development; 803 | }; 804 | 2F56AE98256E68000007D0A2 /* Development */ = { 805 | isa = XCBuildConfiguration; 806 | buildSettings = { 807 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 808 | CODE_SIGN_STYLE = Automatic; 809 | DEVELOPMENT_TEAM = K8J8CUXWK9; 810 | ENABLE_TESTABILITY = YES; 811 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 812 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 813 | LD_RUNPATH_SEARCH_PATHS = ( 814 | "$(inherited)", 815 | "@executable_path/Frameworks", 816 | ); 817 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 818 | PRODUCT_NAME = "$(TARGET_NAME)"; 819 | SWIFT_VERSION = 5.0; 820 | TARGETED_DEVICE_FAMILY = "1,2"; 821 | }; 822 | name = Development; 823 | }; 824 | 2F56AE99256E68000007D0A2 /* Development */ = { 825 | isa = XCBuildConfiguration; 826 | buildSettings = { 827 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 828 | BUNDLE_LOADER = "$(TEST_HOST)"; 829 | CODE_SIGN_STYLE = Automatic; 830 | DEVELOPMENT_TEAM = K8J8CUXWK9; 831 | ENABLE_TESTING_SEARCH_PATHS = YES; 832 | INFOPLIST_FILE = BoilerPlateSwiftUITests/Info.plist; 833 | IPHONEOS_DEPLOYMENT_TARGET = 14.0; 834 | LD_RUNPATH_SEARCH_PATHS = ( 835 | "$(inherited)", 836 | "@executable_path/Frameworks", 837 | "@loader_path/Frameworks", 838 | ); 839 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiTests"; 840 | PRODUCT_NAME = "$(TARGET_NAME)"; 841 | SWIFT_VERSION = 5.0; 842 | TARGETED_DEVICE_FAMILY = "1,2"; 843 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/BoilerPlateSwiftUI.app/BoilerPlateSwiftUI"; 844 | }; 845 | name = Development; 846 | }; 847 | 2F56AE9A256E68000007D0A2 /* Development */ = { 848 | isa = XCBuildConfiguration; 849 | buildSettings = { 850 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 851 | CLANG_ENABLE_MODULES = YES; 852 | CODE_SIGN_STYLE = Automatic; 853 | DEVELOPMENT_TEAM = K8J8CUXWK9; 854 | ENABLE_TESTING_SEARCH_PATHS = YES; 855 | INFOPLIST_FILE = BoilerPlateSwiftUIUITests/Info.plist; 856 | LD_RUNPATH_SEARCH_PATHS = ( 857 | "$(inherited)", 858 | "@executable_path/Frameworks", 859 | "@loader_path/Frameworks", 860 | ); 861 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiUITests"; 862 | PRODUCT_NAME = "$(TARGET_NAME)"; 863 | PROVISIONING_PROFILE = ""; 864 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 865 | SWIFT_VERSION = 5.0; 866 | TARGETED_DEVICE_FAMILY = "1,2"; 867 | TEST_TARGET_NAME = BoilerPlateSwiftUI; 868 | }; 869 | name = Development; 870 | }; 871 | 2FCDE11A2565722600203445 /* Production */ = { 872 | isa = XCBuildConfiguration; 873 | baseConfigurationReference = 2FCDE134256651EF00203445 /* Production.xcconfig */; 874 | buildSettings = { 875 | ALWAYS_SEARCH_USER_PATHS = NO; 876 | CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; 877 | CLANG_ANALYZER_NONNULL = YES; 878 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 879 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 880 | CLANG_CXX_LIBRARY = "libc++"; 881 | CLANG_ENABLE_MODULES = YES; 882 | CLANG_ENABLE_OBJC_ARC = YES; 883 | CLANG_ENABLE_OBJC_WEAK = YES; 884 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 885 | CLANG_WARN_BOOL_CONVERSION = YES; 886 | CLANG_WARN_COMMA = YES; 887 | CLANG_WARN_CONSTANT_CONVERSION = YES; 888 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 889 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 890 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 891 | CLANG_WARN_EMPTY_BODY = YES; 892 | CLANG_WARN_ENUM_CONVERSION = YES; 893 | CLANG_WARN_INFINITE_RECURSION = YES; 894 | CLANG_WARN_INT_CONVERSION = YES; 895 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 896 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 897 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 898 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 899 | CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; 900 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 901 | CLANG_WARN_STRICT_PROTOTYPES = YES; 902 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 903 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 904 | CLANG_WARN_UNREACHABLE_CODE = YES; 905 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 906 | COPY_PHASE_STRIP = NO; 907 | DEBUG_INFORMATION_FORMAT = dwarf; 908 | ENABLE_STRICT_OBJC_MSGSEND = YES; 909 | ENABLE_TESTABILITY = YES; 910 | ENABLE_TESTING_SEARCH_PATHS = NO; 911 | GCC_C_LANGUAGE_STANDARD = gnu11; 912 | GCC_DYNAMIC_NO_PIC = NO; 913 | GCC_NO_COMMON_BLOCKS = YES; 914 | GCC_OPTIMIZATION_LEVEL = 0; 915 | GCC_PREPROCESSOR_DEFINITIONS = ( 916 | "DEBUG=1", 917 | "$(inherited)", 918 | ); 919 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 920 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 921 | GCC_WARN_UNDECLARED_SELECTOR = YES; 922 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 923 | GCC_WARN_UNUSED_FUNCTION = YES; 924 | GCC_WARN_UNUSED_VARIABLE = YES; 925 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 926 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 927 | MTL_FAST_MATH = YES; 928 | ONLY_ACTIVE_ARCH = YES; 929 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 930 | SDKROOT = iphoneos; 931 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 932 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 933 | }; 934 | name = Production; 935 | }; 936 | 2FCDE11B2565722600203445 /* AppStore */ = { 937 | isa = XCBuildConfiguration; 938 | baseConfigurationReference = 2FCDE1352566520A00203445 /* AppStore.xcconfig */; 939 | buildSettings = { 940 | ALWAYS_SEARCH_USER_PATHS = NO; 941 | CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; 942 | CLANG_ANALYZER_NONNULL = YES; 943 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 944 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 945 | CLANG_CXX_LIBRARY = "libc++"; 946 | CLANG_ENABLE_MODULES = YES; 947 | CLANG_ENABLE_OBJC_ARC = YES; 948 | CLANG_ENABLE_OBJC_WEAK = YES; 949 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 950 | CLANG_WARN_BOOL_CONVERSION = YES; 951 | CLANG_WARN_COMMA = YES; 952 | CLANG_WARN_CONSTANT_CONVERSION = YES; 953 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 954 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 955 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 956 | CLANG_WARN_EMPTY_BODY = YES; 957 | CLANG_WARN_ENUM_CONVERSION = YES; 958 | CLANG_WARN_INFINITE_RECURSION = YES; 959 | CLANG_WARN_INT_CONVERSION = YES; 960 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 961 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 962 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 963 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 964 | CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; 965 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 966 | CLANG_WARN_STRICT_PROTOTYPES = YES; 967 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 968 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 969 | CLANG_WARN_UNREACHABLE_CODE = YES; 970 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 971 | COPY_PHASE_STRIP = NO; 972 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 973 | ENABLE_NS_ASSERTIONS = NO; 974 | ENABLE_STRICT_OBJC_MSGSEND = YES; 975 | ENABLE_TESTING_SEARCH_PATHS = NO; 976 | GCC_C_LANGUAGE_STANDARD = gnu11; 977 | GCC_NO_COMMON_BLOCKS = YES; 978 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 979 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 980 | GCC_WARN_UNDECLARED_SELECTOR = YES; 981 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 982 | GCC_WARN_UNUSED_FUNCTION = YES; 983 | GCC_WARN_UNUSED_VARIABLE = YES; 984 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 985 | MTL_ENABLE_DEBUG_INFO = NO; 986 | MTL_FAST_MATH = YES; 987 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 988 | SDKROOT = iphoneos; 989 | SWIFT_COMPILATION_MODE = wholemodule; 990 | SWIFT_OPTIMIZATION_LEVEL = "-O"; 991 | VALIDATE_PRODUCT = YES; 992 | }; 993 | name = AppStore; 994 | }; 995 | 2FCDE11D2565722600203445 /* Production */ = { 996 | isa = XCBuildConfiguration; 997 | buildSettings = { 998 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 999 | CODE_SIGN_STYLE = Automatic; 1000 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1001 | ENABLE_TESTABILITY = YES; 1002 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 1003 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 1004 | LD_RUNPATH_SEARCH_PATHS = ( 1005 | "$(inherited)", 1006 | "@executable_path/Frameworks", 1007 | ); 1008 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 1009 | PRODUCT_NAME = "$(TARGET_NAME)"; 1010 | SWIFT_VERSION = 5.0; 1011 | TARGETED_DEVICE_FAMILY = "1,2"; 1012 | }; 1013 | name = Production; 1014 | }; 1015 | 2FCDE11E2565722600203445 /* AppStore */ = { 1016 | isa = XCBuildConfiguration; 1017 | buildSettings = { 1018 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 1019 | CODE_SIGN_STYLE = Automatic; 1020 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1021 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 1022 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 1023 | LD_RUNPATH_SEARCH_PATHS = ( 1024 | "$(inherited)", 1025 | "@executable_path/Frameworks", 1026 | ); 1027 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 1028 | PRODUCT_NAME = "$(TARGET_NAME)"; 1029 | SWIFT_VERSION = 5.0; 1030 | TARGETED_DEVICE_FAMILY = "1,2"; 1031 | }; 1032 | name = AppStore; 1033 | }; 1034 | 2FCDE1202565722600203445 /* Production */ = { 1035 | isa = XCBuildConfiguration; 1036 | buildSettings = { 1037 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 1038 | BUNDLE_LOADER = "$(TEST_HOST)"; 1039 | CODE_SIGN_STYLE = Automatic; 1040 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1041 | ENABLE_TESTING_SEARCH_PATHS = YES; 1042 | INFOPLIST_FILE = BoilerPlateSwiftUITests/Info.plist; 1043 | IPHONEOS_DEPLOYMENT_TARGET = 14.0; 1044 | LD_RUNPATH_SEARCH_PATHS = ( 1045 | "$(inherited)", 1046 | "@executable_path/Frameworks", 1047 | "@loader_path/Frameworks", 1048 | ); 1049 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiTests"; 1050 | PRODUCT_NAME = "$(TARGET_NAME)"; 1051 | SWIFT_VERSION = 5.0; 1052 | TARGETED_DEVICE_FAMILY = "1,2"; 1053 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/BoilerPlateSwiftUI.app/BoilerPlateSwiftUI"; 1054 | }; 1055 | name = Production; 1056 | }; 1057 | 2FCDE1212565722600203445 /* AppStore */ = { 1058 | isa = XCBuildConfiguration; 1059 | buildSettings = { 1060 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 1061 | BUNDLE_LOADER = "$(TEST_HOST)"; 1062 | CODE_SIGN_STYLE = Automatic; 1063 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1064 | ENABLE_TESTING_SEARCH_PATHS = YES; 1065 | INFOPLIST_FILE = BoilerPlateSwiftUITests/Info.plist; 1066 | IPHONEOS_DEPLOYMENT_TARGET = 14.0; 1067 | LD_RUNPATH_SEARCH_PATHS = ( 1068 | "$(inherited)", 1069 | "@executable_path/Frameworks", 1070 | "@loader_path/Frameworks", 1071 | ); 1072 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiTests"; 1073 | PRODUCT_NAME = "$(TARGET_NAME)"; 1074 | SWIFT_VERSION = 5.0; 1075 | TARGETED_DEVICE_FAMILY = "1,2"; 1076 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/BoilerPlateSwiftUI.app/BoilerPlateSwiftUI"; 1077 | }; 1078 | name = AppStore; 1079 | }; 1080 | 2FCDE1232565722600203445 /* Production */ = { 1081 | isa = XCBuildConfiguration; 1082 | buildSettings = { 1083 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 1084 | CLANG_ENABLE_MODULES = YES; 1085 | CODE_SIGN_STYLE = Automatic; 1086 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1087 | ENABLE_TESTING_SEARCH_PATHS = YES; 1088 | INFOPLIST_FILE = BoilerPlateSwiftUIUITests/Info.plist; 1089 | LD_RUNPATH_SEARCH_PATHS = ( 1090 | "$(inherited)", 1091 | "@executable_path/Frameworks", 1092 | "@loader_path/Frameworks", 1093 | ); 1094 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiUITests"; 1095 | PRODUCT_NAME = "$(TARGET_NAME)"; 1096 | PROVISIONING_PROFILE = ""; 1097 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 1098 | SWIFT_VERSION = 5.0; 1099 | TARGETED_DEVICE_FAMILY = "1,2"; 1100 | TEST_TARGET_NAME = BoilerPlateSwiftUI; 1101 | }; 1102 | name = Production; 1103 | }; 1104 | 2FCDE1242565722600203445 /* AppStore */ = { 1105 | isa = XCBuildConfiguration; 1106 | buildSettings = { 1107 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 1108 | CLANG_ENABLE_MODULES = YES; 1109 | CODE_SIGN_STYLE = Automatic; 1110 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1111 | ENABLE_TESTING_SEARCH_PATHS = YES; 1112 | INFOPLIST_FILE = BoilerPlateSwiftUIUITests/Info.plist; 1113 | LD_RUNPATH_SEARCH_PATHS = ( 1114 | "$(inherited)", 1115 | "@executable_path/Frameworks", 1116 | "@loader_path/Frameworks", 1117 | ); 1118 | PRODUCT_BUNDLE_IDENTIFIER = "com.adesso.boilerplate-ios-swiftuiUITests"; 1119 | PRODUCT_NAME = "$(TARGET_NAME)"; 1120 | PROVISIONING_PROFILE = ""; 1121 | SWIFT_VERSION = 5.0; 1122 | TARGETED_DEVICE_FAMILY = "1,2"; 1123 | TEST_TARGET_NAME = BoilerPlateSwiftUI; 1124 | }; 1125 | name = AppStore; 1126 | }; 1127 | 7259FCE1299EAD3300BF8309 /* Development */ = { 1128 | isa = XCBuildConfiguration; 1129 | buildSettings = { 1130 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 1131 | CODE_SIGN_STYLE = Automatic; 1132 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1133 | ENABLE_TESTABILITY = YES; 1134 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 1135 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 1136 | LD_RUNPATH_SEARCH_PATHS = ( 1137 | "$(inherited)", 1138 | "@executable_path/Frameworks", 1139 | ); 1140 | OTHER_SWIFT_FLAGS = "-D PULSE"; 1141 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 1142 | PRODUCT_NAME = "$(TARGET_NAME)"; 1143 | SWIFT_VERSION = 5.0; 1144 | TARGETED_DEVICE_FAMILY = "1,2"; 1145 | }; 1146 | name = Development; 1147 | }; 1148 | 7259FCE2299EAD3300BF8309 /* Production */ = { 1149 | isa = XCBuildConfiguration; 1150 | buildSettings = { 1151 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 1152 | CODE_SIGN_STYLE = Automatic; 1153 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1154 | ENABLE_TESTABILITY = YES; 1155 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 1156 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 1157 | LD_RUNPATH_SEARCH_PATHS = ( 1158 | "$(inherited)", 1159 | "@executable_path/Frameworks", 1160 | ); 1161 | OTHER_SWIFT_FLAGS = "-D PULSE"; 1162 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 1163 | PRODUCT_NAME = "$(TARGET_NAME)"; 1164 | SWIFT_VERSION = 5.0; 1165 | TARGETED_DEVICE_FAMILY = "1,2"; 1166 | }; 1167 | name = Production; 1168 | }; 1169 | 7259FCE3299EAD3300BF8309 /* AppStore */ = { 1170 | isa = XCBuildConfiguration; 1171 | buildSettings = { 1172 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 1173 | CODE_SIGN_STYLE = Automatic; 1174 | DEVELOPMENT_TEAM = K8J8CUXWK9; 1175 | INFOPLIST_FILE = BoilerPlateSwiftUI/Resources/Info.plist; 1176 | IPHONEOS_DEPLOYMENT_TARGET = 15.0; 1177 | LD_RUNPATH_SEARCH_PATHS = ( 1178 | "$(inherited)", 1179 | "@executable_path/Frameworks", 1180 | ); 1181 | OTHER_SWIFT_FLAGS = "-D PULSE"; 1182 | PRODUCT_BUNDLE_IDENTIFIER = "$(PRODUCT_BUNDLE_IDENTIFIER)"; 1183 | PRODUCT_NAME = "$(TARGET_NAME)"; 1184 | SWIFT_VERSION = 5.0; 1185 | TARGETED_DEVICE_FAMILY = "1,2"; 1186 | }; 1187 | name = AppStore; 1188 | }; 1189 | /* End XCBuildConfiguration section */ 1190 | 1191 | /* Begin XCConfigurationList section */ 1192 | 2FCDE0ED2565722400203445 /* Build configuration list for PBXProject "BoilerPlateSwiftUI" */ = { 1193 | isa = XCConfigurationList; 1194 | buildConfigurations = ( 1195 | 2F56AE97256E68000007D0A2 /* Development */, 1196 | 2FCDE11A2565722600203445 /* Production */, 1197 | 2FCDE11B2565722600203445 /* AppStore */, 1198 | ); 1199 | defaultConfigurationIsVisible = 0; 1200 | defaultConfigurationName = AppStore; 1201 | }; 1202 | 2FCDE11C2565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUI" */ = { 1203 | isa = XCConfigurationList; 1204 | buildConfigurations = ( 1205 | 2F56AE98256E68000007D0A2 /* Development */, 1206 | 2FCDE11D2565722600203445 /* Production */, 1207 | 2FCDE11E2565722600203445 /* AppStore */, 1208 | ); 1209 | defaultConfigurationIsVisible = 0; 1210 | defaultConfigurationName = AppStore; 1211 | }; 1212 | 2FCDE11F2565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUITests" */ = { 1213 | isa = XCConfigurationList; 1214 | buildConfigurations = ( 1215 | 2F56AE99256E68000007D0A2 /* Development */, 1216 | 2FCDE1202565722600203445 /* Production */, 1217 | 2FCDE1212565722600203445 /* AppStore */, 1218 | ); 1219 | defaultConfigurationIsVisible = 0; 1220 | defaultConfigurationName = AppStore; 1221 | }; 1222 | 2FCDE1222565722600203445 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUIUITests" */ = { 1223 | isa = XCConfigurationList; 1224 | buildConfigurations = ( 1225 | 2F56AE9A256E68000007D0A2 /* Development */, 1226 | 2FCDE1232565722600203445 /* Production */, 1227 | 2FCDE1242565722600203445 /* AppStore */, 1228 | ); 1229 | defaultConfigurationIsVisible = 0; 1230 | defaultConfigurationName = AppStore; 1231 | }; 1232 | 7259FCE0299EAD3300BF8309 /* Build configuration list for PBXNativeTarget "BoilerPlateSwiftUI-Pulse" */ = { 1233 | isa = XCConfigurationList; 1234 | buildConfigurations = ( 1235 | 7259FCE1299EAD3300BF8309 /* Development */, 1236 | 7259FCE2299EAD3300BF8309 /* Production */, 1237 | 7259FCE3299EAD3300BF8309 /* AppStore */, 1238 | ); 1239 | defaultConfigurationIsVisible = 0; 1240 | defaultConfigurationName = AppStore; 1241 | }; 1242 | /* End XCConfigurationList section */ 1243 | 1244 | /* Begin XCRemoteSwiftPackageReference section */ 1245 | 7259FCB6299EAD3300BF8309 /* XCRemoteSwiftPackageReference "CocoaLumberjack" */ = { 1246 | isa = XCRemoteSwiftPackageReference; 1247 | repositoryURL = "https://github.com/CocoaLumberjack/CocoaLumberjack"; 1248 | requirement = { 1249 | kind = upToNextMajorVersion; 1250 | minimumVersion = 3.7.0; 1251 | }; 1252 | }; 1253 | 7259FCB8299EAD3300BF8309 /* XCRemoteSwiftPackageReference "Pulse" */ = { 1254 | isa = XCRemoteSwiftPackageReference; 1255 | repositoryURL = "https://github.com/kean/Pulse"; 1256 | requirement = { 1257 | kind = upToNextMajorVersion; 1258 | minimumVersion = 3.0.0; 1259 | }; 1260 | }; 1261 | 72EB016E299E310000DF6C24 /* XCRemoteSwiftPackageReference "Pulse" */ = { 1262 | isa = XCRemoteSwiftPackageReference; 1263 | repositoryURL = "https://github.com/kean/Pulse"; 1264 | requirement = { 1265 | kind = upToNextMajorVersion; 1266 | minimumVersion = 3.0.0; 1267 | }; 1268 | }; 1269 | D1703A4D28C9CDA70071EF00 /* XCRemoteSwiftPackageReference "CocoaLumberjack" */ = { 1270 | isa = XCRemoteSwiftPackageReference; 1271 | repositoryURL = "https://github.com/CocoaLumberjack/CocoaLumberjack"; 1272 | requirement = { 1273 | kind = upToNextMajorVersion; 1274 | minimumVersion = 3.7.0; 1275 | }; 1276 | }; 1277 | /* End XCRemoteSwiftPackageReference section */ 1278 | 1279 | /* Begin XCSwiftPackageProductDependency section */ 1280 | 7259FCB5299EAD3300BF8309 /* CocoaLumberjackSwift */ = { 1281 | isa = XCSwiftPackageProductDependency; 1282 | package = 7259FCB6299EAD3300BF8309 /* XCRemoteSwiftPackageReference "CocoaLumberjack" */; 1283 | productName = CocoaLumberjackSwift; 1284 | }; 1285 | 7259FCB7299EAD3300BF8309 /* Pulse */ = { 1286 | isa = XCSwiftPackageProductDependency; 1287 | package = 7259FCB8299EAD3300BF8309 /* XCRemoteSwiftPackageReference "Pulse" */; 1288 | productName = Pulse; 1289 | }; 1290 | 7259FCB9299EAD3300BF8309 /* PulseUI */ = { 1291 | isa = XCSwiftPackageProductDependency; 1292 | package = 7259FCB8299EAD3300BF8309 /* XCRemoteSwiftPackageReference "Pulse" */; 1293 | productName = PulseUI; 1294 | }; 1295 | 72EB01B3299E57AB00DF6C24 /* Pulse */ = { 1296 | isa = XCSwiftPackageProductDependency; 1297 | package = 72EB016E299E310000DF6C24 /* XCRemoteSwiftPackageReference "Pulse" */; 1298 | productName = Pulse; 1299 | }; 1300 | 72EB01B5299E57AB00DF6C24 /* PulseUI */ = { 1301 | isa = XCSwiftPackageProductDependency; 1302 | package = 72EB016E299E310000DF6C24 /* XCRemoteSwiftPackageReference "Pulse" */; 1303 | productName = PulseUI; 1304 | }; 1305 | D1703A4E28C9CDA70071EF00 /* CocoaLumberjackSwift */ = { 1306 | isa = XCSwiftPackageProductDependency; 1307 | package = D1703A4D28C9CDA70071EF00 /* XCRemoteSwiftPackageReference "CocoaLumberjack" */; 1308 | productName = CocoaLumberjackSwift; 1309 | }; 1310 | /* End XCSwiftPackageProductDependency section */ 1311 | }; 1312 | rootObject = 2FCDE0EA2565722400203445 /* Project object */; 1313 | } 1314 | --------------------------------------------------------------------------------