├── .gitignore ├── .swift-version ├── Example ├── Example.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata └── Example │ ├── AppDelegate.swift │ ├── Assets.xcassets │ ├── AppIcon.appiconset │ │ └── Contents.json │ ├── Contents.json │ └── jennie.imageset │ │ ├── Contents.json │ │ └── jennie.jpg │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Info.plist │ └── ViewController.swift ├── GradientLoading.podspec ├── GradientLoading.xcodeproj ├── project.pbxproj └── project.xcworkspace │ └── contents.xcworkspacedata ├── GradientLoading ├── Classes │ ├── Extensions.swift │ ├── GradientCollection.swift │ ├── GradientColors.swift │ ├── GradientLabel.swift │ ├── GradientLoading.swift │ └── GradientPoint.swift ├── GradientLoading.h └── Info.plist ├── Images └── GradientLoading.gif ├── LICENSE └── README.md /.gitignore: -------------------------------------------------------------------------------- 1 | # OS X 2 | .DS_Store 3 | 4 | # Xcode 5 | build/ 6 | Pods/ 7 | *.pbxuser 8 | !default.pbxuser 9 | *.mode1v3 10 | !default.mode1v3 11 | *.mode2v3 12 | !default.mode2v3 13 | *.perspectivev3 14 | !default.perspectivev3 15 | xcuserdata/ 16 | *.xccheckout 17 | profile 18 | *.moved-aside 19 | DerivedData 20 | *.hmap 21 | *.ipa 22 | 23 | # Bundler 24 | .bundle 25 | 26 | Carthage 27 | # We recommend against adding the Pods directory to your .gitignore. However 28 | # you should judge for yourself, the pros and cons are mentioned at: 29 | # http://guides.cocoapods.org/using/using-cocoapods.html#should-i-ignore-the-pods-directory-in-source-control 30 | # 31 | # Note: if you ignore the Pods directory, make sure to uncomment 32 | # `pod install` in .travis.yml 33 | # 34 | # Pods/ -------------------------------------------------------------------------------- /.swift-version: -------------------------------------------------------------------------------- 1 | 3.0 2 | -------------------------------------------------------------------------------- /Example/Example.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 46; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | AFE0BC6E1F5FADC90007D373 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC6D1F5FADC90007D373 /* AppDelegate.swift */; }; 11 | AFE0BC701F5FADC90007D373 /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC6F1F5FADC90007D373 /* ViewController.swift */; }; 12 | AFE0BC731F5FADC90007D373 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = AFE0BC711F5FADC90007D373 /* Main.storyboard */; }; 13 | AFE0BC751F5FADC90007D373 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = AFE0BC741F5FADC90007D373 /* Assets.xcassets */; }; 14 | AFE0BC781F5FADC90007D373 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = AFE0BC761F5FADC90007D373 /* LaunchScreen.storyboard */; }; 15 | AFE0BC851F5FADE50007D373 /* GradientLoading.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AFE0BC841F5FADDA0007D373 /* GradientLoading.framework */; }; 16 | AFE0BC861F5FADE50007D373 /* GradientLoading.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = AFE0BC841F5FADDA0007D373 /* GradientLoading.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; }; 17 | /* End PBXBuildFile section */ 18 | 19 | /* Begin PBXContainerItemProxy section */ 20 | AFE0BC831F5FADDA0007D373 /* PBXContainerItemProxy */ = { 21 | isa = PBXContainerItemProxy; 22 | containerPortal = AFE0BC7F1F5FADDA0007D373 /* GradientLoading.xcodeproj */; 23 | proxyType = 2; 24 | remoteGlobalIDString = AFE0BC561F5FADB70007D373; 25 | remoteInfo = GradientLoading; 26 | }; 27 | AFE0BC871F5FADE50007D373 /* PBXContainerItemProxy */ = { 28 | isa = PBXContainerItemProxy; 29 | containerPortal = AFE0BC7F1F5FADDA0007D373 /* GradientLoading.xcodeproj */; 30 | proxyType = 1; 31 | remoteGlobalIDString = AFE0BC551F5FADB70007D373; 32 | remoteInfo = GradientLoading; 33 | }; 34 | /* End PBXContainerItemProxy section */ 35 | 36 | /* Begin PBXCopyFilesBuildPhase section */ 37 | AFE0BC891F5FADE50007D373 /* Embed Frameworks */ = { 38 | isa = PBXCopyFilesBuildPhase; 39 | buildActionMask = 2147483647; 40 | dstPath = ""; 41 | dstSubfolderSpec = 10; 42 | files = ( 43 | AFE0BC861F5FADE50007D373 /* GradientLoading.framework in Embed Frameworks */, 44 | ); 45 | name = "Embed Frameworks"; 46 | runOnlyForDeploymentPostprocessing = 0; 47 | }; 48 | /* End PBXCopyFilesBuildPhase section */ 49 | 50 | /* Begin PBXFileReference section */ 51 | AFE0BC6A1F5FADC90007D373 /* Example.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Example.app; sourceTree = BUILT_PRODUCTS_DIR; }; 52 | AFE0BC6D1F5FADC90007D373 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; 53 | AFE0BC6F1F5FADC90007D373 /* ViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = ""; }; 54 | AFE0BC721F5FADC90007D373 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 55 | AFE0BC741F5FADC90007D373 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 56 | AFE0BC771F5FADC90007D373 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 57 | AFE0BC791F5FADC90007D373 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 58 | AFE0BC7F1F5FADDA0007D373 /* GradientLoading.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = GradientLoading.xcodeproj; path = ../GradientLoading.xcodeproj; sourceTree = ""; }; 59 | /* End PBXFileReference section */ 60 | 61 | /* Begin PBXFrameworksBuildPhase section */ 62 | AFE0BC671F5FADC90007D373 /* Frameworks */ = { 63 | isa = PBXFrameworksBuildPhase; 64 | buildActionMask = 2147483647; 65 | files = ( 66 | AFE0BC851F5FADE50007D373 /* GradientLoading.framework in Frameworks */, 67 | ); 68 | runOnlyForDeploymentPostprocessing = 0; 69 | }; 70 | /* End PBXFrameworksBuildPhase section */ 71 | 72 | /* Begin PBXGroup section */ 73 | AFE0BC611F5FADC90007D373 = { 74 | isa = PBXGroup; 75 | children = ( 76 | AFE0BC7F1F5FADDA0007D373 /* GradientLoading.xcodeproj */, 77 | AFE0BC6C1F5FADC90007D373 /* Example */, 78 | AFE0BC6B1F5FADC90007D373 /* Products */, 79 | ); 80 | sourceTree = ""; 81 | }; 82 | AFE0BC6B1F5FADC90007D373 /* Products */ = { 83 | isa = PBXGroup; 84 | children = ( 85 | AFE0BC6A1F5FADC90007D373 /* Example.app */, 86 | ); 87 | name = Products; 88 | sourceTree = ""; 89 | }; 90 | AFE0BC6C1F5FADC90007D373 /* Example */ = { 91 | isa = PBXGroup; 92 | children = ( 93 | AFE0BC6D1F5FADC90007D373 /* AppDelegate.swift */, 94 | AFE0BC6F1F5FADC90007D373 /* ViewController.swift */, 95 | AFE0BC711F5FADC90007D373 /* Main.storyboard */, 96 | AFE0BC741F5FADC90007D373 /* Assets.xcassets */, 97 | AFE0BC761F5FADC90007D373 /* LaunchScreen.storyboard */, 98 | AFE0BC791F5FADC90007D373 /* Info.plist */, 99 | ); 100 | path = Example; 101 | sourceTree = ""; 102 | }; 103 | AFE0BC801F5FADDA0007D373 /* Products */ = { 104 | isa = PBXGroup; 105 | children = ( 106 | AFE0BC841F5FADDA0007D373 /* GradientLoading.framework */, 107 | ); 108 | name = Products; 109 | sourceTree = ""; 110 | }; 111 | /* End PBXGroup section */ 112 | 113 | /* Begin PBXNativeTarget section */ 114 | AFE0BC691F5FADC90007D373 /* Example */ = { 115 | isa = PBXNativeTarget; 116 | buildConfigurationList = AFE0BC7C1F5FADC90007D373 /* Build configuration list for PBXNativeTarget "Example" */; 117 | buildPhases = ( 118 | AFE0BC661F5FADC90007D373 /* Sources */, 119 | AFE0BC671F5FADC90007D373 /* Frameworks */, 120 | AFE0BC681F5FADC90007D373 /* Resources */, 121 | AFE0BC891F5FADE50007D373 /* Embed Frameworks */, 122 | ); 123 | buildRules = ( 124 | ); 125 | dependencies = ( 126 | AFE0BC881F5FADE50007D373 /* PBXTargetDependency */, 127 | ); 128 | name = Example; 129 | productName = Example; 130 | productReference = AFE0BC6A1F5FADC90007D373 /* Example.app */; 131 | productType = "com.apple.product-type.application"; 132 | }; 133 | /* End PBXNativeTarget section */ 134 | 135 | /* Begin PBXProject section */ 136 | AFE0BC621F5FADC90007D373 /* Project object */ = { 137 | isa = PBXProject; 138 | attributes = { 139 | LastSwiftUpdateCheck = 0830; 140 | LastUpgradeCheck = 0830; 141 | ORGANIZATIONNAME = feather; 142 | TargetAttributes = { 143 | AFE0BC691F5FADC90007D373 = { 144 | CreatedOnToolsVersion = 8.3.3; 145 | DevelopmentTeam = R5DY89FR38; 146 | ProvisioningStyle = Manual; 147 | }; 148 | }; 149 | }; 150 | buildConfigurationList = AFE0BC651F5FADC90007D373 /* Build configuration list for PBXProject "Example" */; 151 | compatibilityVersion = "Xcode 3.2"; 152 | developmentRegion = English; 153 | hasScannedForEncodings = 0; 154 | knownRegions = ( 155 | en, 156 | Base, 157 | ); 158 | mainGroup = AFE0BC611F5FADC90007D373; 159 | productRefGroup = AFE0BC6B1F5FADC90007D373 /* Products */; 160 | projectDirPath = ""; 161 | projectReferences = ( 162 | { 163 | ProductGroup = AFE0BC801F5FADDA0007D373 /* Products */; 164 | ProjectRef = AFE0BC7F1F5FADDA0007D373 /* GradientLoading.xcodeproj */; 165 | }, 166 | ); 167 | projectRoot = ""; 168 | targets = ( 169 | AFE0BC691F5FADC90007D373 /* Example */, 170 | ); 171 | }; 172 | /* End PBXProject section */ 173 | 174 | /* Begin PBXReferenceProxy section */ 175 | AFE0BC841F5FADDA0007D373 /* GradientLoading.framework */ = { 176 | isa = PBXReferenceProxy; 177 | fileType = wrapper.framework; 178 | path = GradientLoading.framework; 179 | remoteRef = AFE0BC831F5FADDA0007D373 /* PBXContainerItemProxy */; 180 | sourceTree = BUILT_PRODUCTS_DIR; 181 | }; 182 | /* End PBXReferenceProxy section */ 183 | 184 | /* Begin PBXResourcesBuildPhase section */ 185 | AFE0BC681F5FADC90007D373 /* Resources */ = { 186 | isa = PBXResourcesBuildPhase; 187 | buildActionMask = 2147483647; 188 | files = ( 189 | AFE0BC781F5FADC90007D373 /* LaunchScreen.storyboard in Resources */, 190 | AFE0BC751F5FADC90007D373 /* Assets.xcassets in Resources */, 191 | AFE0BC731F5FADC90007D373 /* Main.storyboard in Resources */, 192 | ); 193 | runOnlyForDeploymentPostprocessing = 0; 194 | }; 195 | /* End PBXResourcesBuildPhase section */ 196 | 197 | /* Begin PBXSourcesBuildPhase section */ 198 | AFE0BC661F5FADC90007D373 /* Sources */ = { 199 | isa = PBXSourcesBuildPhase; 200 | buildActionMask = 2147483647; 201 | files = ( 202 | AFE0BC701F5FADC90007D373 /* ViewController.swift in Sources */, 203 | AFE0BC6E1F5FADC90007D373 /* AppDelegate.swift in Sources */, 204 | ); 205 | runOnlyForDeploymentPostprocessing = 0; 206 | }; 207 | /* End PBXSourcesBuildPhase section */ 208 | 209 | /* Begin PBXTargetDependency section */ 210 | AFE0BC881F5FADE50007D373 /* PBXTargetDependency */ = { 211 | isa = PBXTargetDependency; 212 | name = GradientLoading; 213 | targetProxy = AFE0BC871F5FADE50007D373 /* PBXContainerItemProxy */; 214 | }; 215 | /* End PBXTargetDependency section */ 216 | 217 | /* Begin PBXVariantGroup section */ 218 | AFE0BC711F5FADC90007D373 /* Main.storyboard */ = { 219 | isa = PBXVariantGroup; 220 | children = ( 221 | AFE0BC721F5FADC90007D373 /* Base */, 222 | ); 223 | name = Main.storyboard; 224 | sourceTree = ""; 225 | }; 226 | AFE0BC761F5FADC90007D373 /* LaunchScreen.storyboard */ = { 227 | isa = PBXVariantGroup; 228 | children = ( 229 | AFE0BC771F5FADC90007D373 /* Base */, 230 | ); 231 | name = LaunchScreen.storyboard; 232 | sourceTree = ""; 233 | }; 234 | /* End PBXVariantGroup section */ 235 | 236 | /* Begin XCBuildConfiguration section */ 237 | AFE0BC7A1F5FADC90007D373 /* Debug */ = { 238 | isa = XCBuildConfiguration; 239 | buildSettings = { 240 | ALWAYS_SEARCH_USER_PATHS = NO; 241 | CLANG_ANALYZER_NONNULL = YES; 242 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 243 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 244 | CLANG_CXX_LIBRARY = "libc++"; 245 | CLANG_ENABLE_MODULES = YES; 246 | CLANG_ENABLE_OBJC_ARC = YES; 247 | CLANG_WARN_BOOL_CONVERSION = YES; 248 | CLANG_WARN_CONSTANT_CONVERSION = YES; 249 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 250 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 251 | CLANG_WARN_EMPTY_BODY = YES; 252 | CLANG_WARN_ENUM_CONVERSION = YES; 253 | CLANG_WARN_INFINITE_RECURSION = YES; 254 | CLANG_WARN_INT_CONVERSION = YES; 255 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 256 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 257 | CLANG_WARN_UNREACHABLE_CODE = YES; 258 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 259 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 260 | COPY_PHASE_STRIP = NO; 261 | DEBUG_INFORMATION_FORMAT = dwarf; 262 | ENABLE_STRICT_OBJC_MSGSEND = YES; 263 | ENABLE_TESTABILITY = YES; 264 | GCC_C_LANGUAGE_STANDARD = gnu99; 265 | GCC_DYNAMIC_NO_PIC = NO; 266 | GCC_NO_COMMON_BLOCKS = YES; 267 | GCC_OPTIMIZATION_LEVEL = 0; 268 | GCC_PREPROCESSOR_DEFINITIONS = ( 269 | "DEBUG=1", 270 | "$(inherited)", 271 | ); 272 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 273 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 274 | GCC_WARN_UNDECLARED_SELECTOR = YES; 275 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 276 | GCC_WARN_UNUSED_FUNCTION = YES; 277 | GCC_WARN_UNUSED_VARIABLE = YES; 278 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 279 | MTL_ENABLE_DEBUG_INFO = YES; 280 | ONLY_ACTIVE_ARCH = YES; 281 | SDKROOT = iphoneos; 282 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 283 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 284 | TARGETED_DEVICE_FAMILY = "1,2"; 285 | }; 286 | name = Debug; 287 | }; 288 | AFE0BC7B1F5FADC90007D373 /* Release */ = { 289 | isa = XCBuildConfiguration; 290 | buildSettings = { 291 | ALWAYS_SEARCH_USER_PATHS = NO; 292 | CLANG_ANALYZER_NONNULL = YES; 293 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 294 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 295 | CLANG_CXX_LIBRARY = "libc++"; 296 | CLANG_ENABLE_MODULES = YES; 297 | CLANG_ENABLE_OBJC_ARC = YES; 298 | CLANG_WARN_BOOL_CONVERSION = YES; 299 | CLANG_WARN_CONSTANT_CONVERSION = YES; 300 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 301 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 302 | CLANG_WARN_EMPTY_BODY = YES; 303 | CLANG_WARN_ENUM_CONVERSION = YES; 304 | CLANG_WARN_INFINITE_RECURSION = YES; 305 | CLANG_WARN_INT_CONVERSION = YES; 306 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 307 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 308 | CLANG_WARN_UNREACHABLE_CODE = YES; 309 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 310 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 311 | COPY_PHASE_STRIP = NO; 312 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 313 | ENABLE_NS_ASSERTIONS = NO; 314 | ENABLE_STRICT_OBJC_MSGSEND = YES; 315 | GCC_C_LANGUAGE_STANDARD = gnu99; 316 | GCC_NO_COMMON_BLOCKS = YES; 317 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 318 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 319 | GCC_WARN_UNDECLARED_SELECTOR = YES; 320 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 321 | GCC_WARN_UNUSED_FUNCTION = YES; 322 | GCC_WARN_UNUSED_VARIABLE = YES; 323 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 324 | MTL_ENABLE_DEBUG_INFO = NO; 325 | SDKROOT = iphoneos; 326 | SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; 327 | TARGETED_DEVICE_FAMILY = "1,2"; 328 | VALIDATE_PRODUCT = YES; 329 | }; 330 | name = Release; 331 | }; 332 | AFE0BC7D1F5FADC90007D373 /* Debug */ = { 333 | isa = XCBuildConfiguration; 334 | buildSettings = { 335 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 336 | DEVELOPMENT_TEAM = R5DY89FR38; 337 | INFOPLIST_FILE = Example/Info.plist; 338 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 339 | PRODUCT_BUNDLE_IDENTIFIER = kr.feather.Example; 340 | PRODUCT_NAME = "$(TARGET_NAME)"; 341 | PROVISIONING_PROFILE = "52f7ae47-c585-4f13-9797-27eb00bfab79"; 342 | PROVISIONING_PROFILE_SPECIFIER = Develpopment_Provisioning; 343 | SWIFT_VERSION = 3.0; 344 | }; 345 | name = Debug; 346 | }; 347 | AFE0BC7E1F5FADC90007D373 /* Release */ = { 348 | isa = XCBuildConfiguration; 349 | buildSettings = { 350 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 351 | DEVELOPMENT_TEAM = ""; 352 | INFOPLIST_FILE = Example/Info.plist; 353 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 354 | PRODUCT_BUNDLE_IDENTIFIER = kr.feather.Example; 355 | PRODUCT_NAME = "$(TARGET_NAME)"; 356 | PROVISIONING_PROFILE_SPECIFIER = ""; 357 | SWIFT_VERSION = 3.0; 358 | }; 359 | name = Release; 360 | }; 361 | /* End XCBuildConfiguration section */ 362 | 363 | /* Begin XCConfigurationList section */ 364 | AFE0BC651F5FADC90007D373 /* Build configuration list for PBXProject "Example" */ = { 365 | isa = XCConfigurationList; 366 | buildConfigurations = ( 367 | AFE0BC7A1F5FADC90007D373 /* Debug */, 368 | AFE0BC7B1F5FADC90007D373 /* Release */, 369 | ); 370 | defaultConfigurationIsVisible = 0; 371 | defaultConfigurationName = Release; 372 | }; 373 | AFE0BC7C1F5FADC90007D373 /* Build configuration list for PBXNativeTarget "Example" */ = { 374 | isa = XCConfigurationList; 375 | buildConfigurations = ( 376 | AFE0BC7D1F5FADC90007D373 /* Debug */, 377 | AFE0BC7E1F5FADC90007D373 /* Release */, 378 | ); 379 | defaultConfigurationIsVisible = 0; 380 | defaultConfigurationName = Release; 381 | }; 382 | /* End XCConfigurationList section */ 383 | }; 384 | rootObject = AFE0BC621F5FADC90007D373 /* Project object */; 385 | } 386 | -------------------------------------------------------------------------------- /Example/Example.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Example/Example/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // Example 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | @UIApplicationMain 12 | class AppDelegate: UIResponder, UIApplicationDelegate { 13 | 14 | var window: UIWindow? 15 | 16 | 17 | func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { 18 | // Override point for customization after application launch. 19 | return true 20 | } 21 | 22 | func applicationWillResignActive(_ application: UIApplication) { 23 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 24 | // Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game. 25 | } 26 | 27 | func applicationDidEnterBackground(_ application: UIApplication) { 28 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 29 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 30 | } 31 | 32 | func applicationWillEnterForeground(_ application: UIApplication) { 33 | // Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background. 34 | } 35 | 36 | func applicationDidBecomeActive(_ application: UIApplication) { 37 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 38 | } 39 | 40 | func applicationWillTerminate(_ application: UIApplication) { 41 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 42 | } 43 | 44 | 45 | } 46 | 47 | -------------------------------------------------------------------------------- /Example/Example/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 | "info" : { 90 | "version" : 1, 91 | "author" : "xcode" 92 | } 93 | } -------------------------------------------------------------------------------- /Example/Example/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Example/Example/Assets.xcassets/jennie.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "jennie.jpg", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /Example/Example/Assets.xcassets/jennie.imageset/jennie.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/devfeather/GradientLoading/e3f754f781909a00f20431fa6097a5ab98b017e3/Example/Example/Assets.xcassets/jennie.imageset/jennie.jpg -------------------------------------------------------------------------------- /Example/Example/Base.lproj/LaunchScreen.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /Example/Example/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | -------------------------------------------------------------------------------- /Example/Example/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | APPL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | LSRequiresIPhoneOS 22 | 23 | UILaunchStoryboardName 24 | LaunchScreen 25 | UIMainStoryboardFile 26 | Main 27 | UIRequiredDeviceCapabilities 28 | 29 | armv7 30 | 31 | UISupportedInterfaceOrientations 32 | 33 | UIInterfaceOrientationPortrait 34 | UIInterfaceOrientationLandscapeLeft 35 | UIInterfaceOrientationLandscapeRight 36 | 37 | UISupportedInterfaceOrientations~ipad 38 | 39 | UIInterfaceOrientationPortrait 40 | UIInterfaceOrientationPortraitUpsideDown 41 | UIInterfaceOrientationLandscapeLeft 42 | UIInterfaceOrientationLandscapeRight 43 | 44 | 45 | 46 | -------------------------------------------------------------------------------- /Example/Example/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // Example 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | import GradientLoading 11 | 12 | class ViewController: UIViewController, CAAnimationDelegate { 13 | 14 | @IBOutlet weak var loadingButton: UIButton! { 15 | didSet { 16 | loadingButton.layer.cornerRadius = 5.0 17 | loadingButton.layer.borderWidth = 1.0 18 | loadingButton.layer.borderColor = UIColor.white.cgColor 19 | } 20 | } 21 | override func viewDidLoad() { 22 | super.viewDidLoad() 23 | 24 | // Setup Text, Font, Stroke Color, Stroke Width. 25 | GradientLoading.shared.setFontAttributes(text: "Jennie") 26 | 27 | // use setCollectionColors or setColors. 28 | GradientLoading.shared.setCollectionColors(.aurora) 29 | // GradientLoading.shared.setColors([#colorLiteral(red: 0.662745098, green: 0.7882352941, blue: 1, alpha: 1), #colorLiteral(red: 1, green: 0.4156862745, blue: 0.5333333333, alpha: 1), #colorLiteral(red: 1, green: 0.7333333333, blue: 0.9254901961, alpha: 1), #colorLiteral(red: 0.9333333333, green: 0.4549019608, blue: 0.8823529412, alpha: 1)]) 30 | } 31 | 32 | @IBAction func showLoading(_ sender: Any) { 33 | // Show Gradient Loading 34 | GradientLoading.shared.show() 35 | 36 | // Hide after 5 second 37 | DispatchQueue.main.asyncAfter(deadline: .now() + 5) { 38 | GradientLoading.shared.hide() 39 | } 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /GradientLoading.podspec: -------------------------------------------------------------------------------- 1 | # 2 | # Be sure to run `pod spec lint GradientLoading.podspec' to ensure this is a 3 | # valid spec and to remove all comments including this before submitting the spec. 4 | # 5 | # To learn more about Podspec attributes see http://docs.cocoapods.org/specification.html 6 | # To see working Podspecs in the CocoaPods repo see https://github.com/CocoaPods/Specs/ 7 | # 8 | 9 | Pod::Spec.new do |s| 10 | 11 | # ――― Spec Metadata ―――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 12 | # 13 | # These will help people to find your library, and whilst it 14 | # can feel like a chore to fill in it's definitely to your advantage. The 15 | # summary should be tweet-length, and the description more in depth. 16 | # 17 | 18 | s.name = "GradientLoading" 19 | s.version = "0.0.1" 20 | s.summary = "Easy to use Loading View in iOS" 21 | 22 | # This description is used to generate tags and improve search results. 23 | # * Think: What does it do? Why did you write it? What is the focus? 24 | # * Try to keep it short, snappy and to the point. 25 | # * Write the description between the DESC delimiters below. 26 | # * Finally, don't worry about the indent, CocoaPods strips it! 27 | s.description = "Easy to use Loading View in iOS, Install library into project." 28 | 29 | s.homepage = "https://github.com/devfeather/GradientLoading" 30 | # s.screenshots = "www.example.com/screenshots_1.gif", "www.example.com/screenshots_2.gif" 31 | 32 | 33 | # ――― Spec License ――――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 34 | # 35 | # Licensing your code is important. See http://choosealicense.com for more info. 36 | # CocoaPods will detect a license file if there is a named LICENSE* 37 | # Popular ones are 'MIT', 'BSD' and 'Apache License, Version 2.0'. 38 | # 39 | 40 | # s.license = "MIT (example)" 41 | s.license = { :type => "MIT", :file => "LICENSE" } 42 | 43 | 44 | # ――― Author Metadata ――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 45 | # 46 | # Specify the authors of the library, with email addresses. Email addresses 47 | # of the authors are extracted from the SCM log. E.g. $ git log. CocoaPods also 48 | # accepts just a name if you'd rather not provide an email address. 49 | # 50 | # Specify a social_media_url where others can refer to, for example a twitter 51 | # profile URL. 52 | # 53 | 54 | s.author = { "feather" => "email@address.com" } 55 | # Or just: s.author = "feather" 56 | # s.authors = { "feather" => "email@address.com" } 57 | # s.social_media_url = "http://twitter.com/feather" 58 | 59 | # ――― Platform Specifics ――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 60 | # 61 | # If this Pod runs only on iOS or OS X, then specify the platform and 62 | # the deployment target. You can optionally include the target after the platform. 63 | # 64 | 65 | # s.platform = :ios 66 | s.platform = :ios, "8.0" 67 | 68 | # When using multiple platforms 69 | # s.ios.deployment_target = "5.0" 70 | # s.osx.deployment_target = "10.7" 71 | # s.watchos.deployment_target = "2.0" 72 | # s.tvos.deployment_target = "9.0" 73 | 74 | 75 | # ――― Source Location ―――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 76 | # 77 | # Specify the location from where the source should be retrieved. 78 | # Supports git, hg, bzr, svn and HTTP. 79 | # 80 | 81 | s.source = { :git => "https://github.com/devfeather/GradientLoading.git", :tag => s.version.to_s } 82 | 83 | 84 | # ――― Source Code ―――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 85 | # 86 | # CocoaPods is smart about how it includes source code. For source files 87 | # giving a folder will include any swift, h, m, mm, c & cpp files. 88 | # For header files it will include any header in the folder. 89 | # Not including the public_header_files will make all headers public. 90 | # 91 | 92 | s.source_files = "GradientLoading/Classes/**/*.{swift}" 93 | s.exclude_files = "Classes/Exclude" 94 | 95 | # s.public_header_files = "Classes/**/*.h" 96 | 97 | 98 | # ――― Resources ―――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 99 | # 100 | # A list of resources included with the Pod. These are copied into the 101 | # target bundle with a build phase script. Anything else will be cleaned. 102 | # You can preserve files from being cleaned, please don't preserve 103 | # non-essential files like tests, examples and documentation. 104 | # 105 | 106 | # s.resource = "icon.png" 107 | # s.resources = "Resources/*.png" 108 | 109 | # s.preserve_paths = "FilesToSave", "MoreFilesToSave" 110 | 111 | 112 | # ――― Project Linking ―――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 113 | # 114 | # Link your library with frameworks, or libraries. Libraries do not include 115 | # the lib prefix of their name. 116 | # 117 | 118 | # s.framework = "SomeFramework" 119 | # s.frameworks = "SomeFramework", "AnotherFramework" 120 | 121 | # s.library = "iconv" 122 | # s.libraries = "iconv", "xml2" 123 | 124 | 125 | # ――― Project Settings ――――――――――――――――――――――――――――――――――――――――――――――――――――――――― # 126 | # 127 | # If your library depends on compiler flags you can set them in the xcconfig hash 128 | # where they will only apply to your library. If you depend on other Podspecs 129 | # you can include multiple dependencies to ensure it works. 130 | 131 | s.requires_arc = true 132 | 133 | # s.xcconfig = { "HEADER_SEARCH_PATHS" => "$(SDKROOT)/usr/include/libxml2" } 134 | # s.dependency "JSONKit", "~> 1.4" 135 | 136 | end 137 | -------------------------------------------------------------------------------- /GradientLoading.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 46; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | AFAD70031F625540009AEB3D /* Extensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFAD70021F625540009AEB3D /* Extensions.swift */; }; 11 | AFE0BC5B1F5FADB70007D373 /* GradientLoading.h in Headers */ = {isa = PBXBuildFile; fileRef = AFE0BC591F5FADB70007D373 /* GradientLoading.h */; settings = {ATTRIBUTES = (Public, ); }; }; 12 | AFE0BC8C1F5FAE250007D373 /* GradientLoading.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC8B1F5FAE250007D373 /* GradientLoading.swift */; }; 13 | AFE0BC8F1F5FB4550007D373 /* GradientLabel.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC8E1F5FB4550007D373 /* GradientLabel.swift */; }; 14 | AFE0BC911F5FB6CA0007D373 /* GradientColors.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC901F5FB6CA0007D373 /* GradientColors.swift */; }; 15 | AFE0BC961F5FD5A70007D373 /* GradientPoint.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC951F5FD5A70007D373 /* GradientPoint.swift */; }; 16 | AFE0BC981F6023420007D373 /* GradientCollection.swift in Sources */ = {isa = PBXBuildFile; fileRef = AFE0BC971F6023420007D373 /* GradientCollection.swift */; }; 17 | /* End PBXBuildFile section */ 18 | 19 | /* Begin PBXFileReference section */ 20 | AFAD70021F625540009AEB3D /* Extensions.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = Extensions.swift; path = Classes/Extensions.swift; sourceTree = ""; }; 21 | AFE0BC561F5FADB70007D373 /* GradientLoading.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = GradientLoading.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 22 | AFE0BC591F5FADB70007D373 /* GradientLoading.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GradientLoading.h; sourceTree = ""; }; 23 | AFE0BC5A1F5FADB70007D373 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 24 | AFE0BC8B1F5FAE250007D373 /* GradientLoading.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GradientLoading.swift; path = Classes/GradientLoading.swift; sourceTree = ""; }; 25 | AFE0BC8E1F5FB4550007D373 /* GradientLabel.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GradientLabel.swift; path = Classes/GradientLabel.swift; sourceTree = ""; }; 26 | AFE0BC901F5FB6CA0007D373 /* GradientColors.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GradientColors.swift; path = Classes/GradientColors.swift; sourceTree = ""; }; 27 | AFE0BC951F5FD5A70007D373 /* GradientPoint.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GradientPoint.swift; path = Classes/GradientPoint.swift; sourceTree = ""; }; 28 | AFE0BC971F6023420007D373 /* GradientCollection.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GradientCollection.swift; path = Classes/GradientCollection.swift; sourceTree = ""; }; 29 | /* End PBXFileReference section */ 30 | 31 | /* Begin PBXFrameworksBuildPhase section */ 32 | AFE0BC521F5FADB70007D373 /* Frameworks */ = { 33 | isa = PBXFrameworksBuildPhase; 34 | buildActionMask = 2147483647; 35 | files = ( 36 | ); 37 | runOnlyForDeploymentPostprocessing = 0; 38 | }; 39 | /* End PBXFrameworksBuildPhase section */ 40 | 41 | /* Begin PBXGroup section */ 42 | AFE0BC4C1F5FADB70007D373 = { 43 | isa = PBXGroup; 44 | children = ( 45 | AFE0BC581F5FADB70007D373 /* GradientLoading */, 46 | AFE0BC571F5FADB70007D373 /* Products */, 47 | ); 48 | sourceTree = ""; 49 | }; 50 | AFE0BC571F5FADB70007D373 /* Products */ = { 51 | isa = PBXGroup; 52 | children = ( 53 | AFE0BC561F5FADB70007D373 /* GradientLoading.framework */, 54 | ); 55 | name = Products; 56 | sourceTree = ""; 57 | }; 58 | AFE0BC581F5FADB70007D373 /* GradientLoading */ = { 59 | isa = PBXGroup; 60 | children = ( 61 | AFE0BC8A1F5FAE0C0007D373 /* Classes */, 62 | AFE0BC591F5FADB70007D373 /* GradientLoading.h */, 63 | AFE0BC5A1F5FADB70007D373 /* Info.plist */, 64 | ); 65 | path = GradientLoading; 66 | sourceTree = ""; 67 | }; 68 | AFE0BC8A1F5FAE0C0007D373 /* Classes */ = { 69 | isa = PBXGroup; 70 | children = ( 71 | AFE0BC8B1F5FAE250007D373 /* GradientLoading.swift */, 72 | AFE0BC8E1F5FB4550007D373 /* GradientLabel.swift */, 73 | AFE0BC951F5FD5A70007D373 /* GradientPoint.swift */, 74 | AFE0BC901F5FB6CA0007D373 /* GradientColors.swift */, 75 | AFE0BC971F6023420007D373 /* GradientCollection.swift */, 76 | AFAD70021F625540009AEB3D /* Extensions.swift */, 77 | ); 78 | name = Classes; 79 | sourceTree = ""; 80 | }; 81 | /* End PBXGroup section */ 82 | 83 | /* Begin PBXHeadersBuildPhase section */ 84 | AFE0BC531F5FADB70007D373 /* Headers */ = { 85 | isa = PBXHeadersBuildPhase; 86 | buildActionMask = 2147483647; 87 | files = ( 88 | AFE0BC5B1F5FADB70007D373 /* GradientLoading.h in Headers */, 89 | ); 90 | runOnlyForDeploymentPostprocessing = 0; 91 | }; 92 | /* End PBXHeadersBuildPhase section */ 93 | 94 | /* Begin PBXNativeTarget section */ 95 | AFE0BC551F5FADB70007D373 /* GradientLoading */ = { 96 | isa = PBXNativeTarget; 97 | buildConfigurationList = AFE0BC5E1F5FADB70007D373 /* Build configuration list for PBXNativeTarget "GradientLoading" */; 98 | buildPhases = ( 99 | AFE0BC511F5FADB70007D373 /* Sources */, 100 | AFE0BC521F5FADB70007D373 /* Frameworks */, 101 | AFE0BC531F5FADB70007D373 /* Headers */, 102 | AFE0BC541F5FADB70007D373 /* Resources */, 103 | ); 104 | buildRules = ( 105 | ); 106 | dependencies = ( 107 | ); 108 | name = GradientLoading; 109 | productName = GradientLoading; 110 | productReference = AFE0BC561F5FADB70007D373 /* GradientLoading.framework */; 111 | productType = "com.apple.product-type.framework"; 112 | }; 113 | /* End PBXNativeTarget section */ 114 | 115 | /* Begin PBXProject section */ 116 | AFE0BC4D1F5FADB70007D373 /* Project object */ = { 117 | isa = PBXProject; 118 | attributes = { 119 | LastUpgradeCheck = 0830; 120 | ORGANIZATIONNAME = feather; 121 | TargetAttributes = { 122 | AFE0BC551F5FADB70007D373 = { 123 | CreatedOnToolsVersion = 8.3.3; 124 | LastSwiftMigration = 0830; 125 | ProvisioningStyle = Automatic; 126 | }; 127 | }; 128 | }; 129 | buildConfigurationList = AFE0BC501F5FADB70007D373 /* Build configuration list for PBXProject "GradientLoading" */; 130 | compatibilityVersion = "Xcode 3.2"; 131 | developmentRegion = English; 132 | hasScannedForEncodings = 0; 133 | knownRegions = ( 134 | en, 135 | ); 136 | mainGroup = AFE0BC4C1F5FADB70007D373; 137 | productRefGroup = AFE0BC571F5FADB70007D373 /* Products */; 138 | projectDirPath = ""; 139 | projectRoot = ""; 140 | targets = ( 141 | AFE0BC551F5FADB70007D373 /* GradientLoading */, 142 | ); 143 | }; 144 | /* End PBXProject section */ 145 | 146 | /* Begin PBXResourcesBuildPhase section */ 147 | AFE0BC541F5FADB70007D373 /* Resources */ = { 148 | isa = PBXResourcesBuildPhase; 149 | buildActionMask = 2147483647; 150 | files = ( 151 | ); 152 | runOnlyForDeploymentPostprocessing = 0; 153 | }; 154 | /* End PBXResourcesBuildPhase section */ 155 | 156 | /* Begin PBXSourcesBuildPhase section */ 157 | AFE0BC511F5FADB70007D373 /* Sources */ = { 158 | isa = PBXSourcesBuildPhase; 159 | buildActionMask = 2147483647; 160 | files = ( 161 | AFE0BC911F5FB6CA0007D373 /* GradientColors.swift in Sources */, 162 | AFAD70031F625540009AEB3D /* Extensions.swift in Sources */, 163 | AFE0BC981F6023420007D373 /* GradientCollection.swift in Sources */, 164 | AFE0BC8F1F5FB4550007D373 /* GradientLabel.swift in Sources */, 165 | AFE0BC8C1F5FAE250007D373 /* GradientLoading.swift in Sources */, 166 | AFE0BC961F5FD5A70007D373 /* GradientPoint.swift in Sources */, 167 | ); 168 | runOnlyForDeploymentPostprocessing = 0; 169 | }; 170 | /* End PBXSourcesBuildPhase section */ 171 | 172 | /* Begin XCBuildConfiguration section */ 173 | AFE0BC5C1F5FADB70007D373 /* Debug */ = { 174 | isa = XCBuildConfiguration; 175 | buildSettings = { 176 | ALWAYS_SEARCH_USER_PATHS = NO; 177 | CLANG_ANALYZER_NONNULL = YES; 178 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 179 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 180 | CLANG_CXX_LIBRARY = "libc++"; 181 | CLANG_ENABLE_MODULES = YES; 182 | CLANG_ENABLE_OBJC_ARC = YES; 183 | CLANG_WARN_BOOL_CONVERSION = YES; 184 | CLANG_WARN_CONSTANT_CONVERSION = YES; 185 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 186 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 187 | CLANG_WARN_EMPTY_BODY = YES; 188 | CLANG_WARN_ENUM_CONVERSION = YES; 189 | CLANG_WARN_INFINITE_RECURSION = YES; 190 | CLANG_WARN_INT_CONVERSION = YES; 191 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 192 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 193 | CLANG_WARN_UNREACHABLE_CODE = YES; 194 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 195 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 196 | COPY_PHASE_STRIP = NO; 197 | CURRENT_PROJECT_VERSION = 1; 198 | DEBUG_INFORMATION_FORMAT = dwarf; 199 | ENABLE_STRICT_OBJC_MSGSEND = YES; 200 | ENABLE_TESTABILITY = YES; 201 | GCC_C_LANGUAGE_STANDARD = gnu99; 202 | GCC_DYNAMIC_NO_PIC = NO; 203 | GCC_NO_COMMON_BLOCKS = YES; 204 | GCC_OPTIMIZATION_LEVEL = 0; 205 | GCC_PREPROCESSOR_DEFINITIONS = ( 206 | "DEBUG=1", 207 | "$(inherited)", 208 | ); 209 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 210 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 211 | GCC_WARN_UNDECLARED_SELECTOR = YES; 212 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 213 | GCC_WARN_UNUSED_FUNCTION = YES; 214 | GCC_WARN_UNUSED_VARIABLE = YES; 215 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 216 | MTL_ENABLE_DEBUG_INFO = YES; 217 | ONLY_ACTIVE_ARCH = YES; 218 | SDKROOT = iphoneos; 219 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 220 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 221 | TARGETED_DEVICE_FAMILY = "1,2"; 222 | VERSIONING_SYSTEM = "apple-generic"; 223 | VERSION_INFO_PREFIX = ""; 224 | }; 225 | name = Debug; 226 | }; 227 | AFE0BC5D1F5FADB70007D373 /* Release */ = { 228 | isa = XCBuildConfiguration; 229 | buildSettings = { 230 | ALWAYS_SEARCH_USER_PATHS = NO; 231 | CLANG_ANALYZER_NONNULL = YES; 232 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 233 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 234 | CLANG_CXX_LIBRARY = "libc++"; 235 | CLANG_ENABLE_MODULES = YES; 236 | CLANG_ENABLE_OBJC_ARC = YES; 237 | CLANG_WARN_BOOL_CONVERSION = YES; 238 | CLANG_WARN_CONSTANT_CONVERSION = YES; 239 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 240 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 241 | CLANG_WARN_EMPTY_BODY = YES; 242 | CLANG_WARN_ENUM_CONVERSION = YES; 243 | CLANG_WARN_INFINITE_RECURSION = YES; 244 | CLANG_WARN_INT_CONVERSION = YES; 245 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 246 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 247 | CLANG_WARN_UNREACHABLE_CODE = YES; 248 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 249 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 250 | COPY_PHASE_STRIP = NO; 251 | CURRENT_PROJECT_VERSION = 1; 252 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 253 | ENABLE_NS_ASSERTIONS = NO; 254 | ENABLE_STRICT_OBJC_MSGSEND = YES; 255 | GCC_C_LANGUAGE_STANDARD = gnu99; 256 | GCC_NO_COMMON_BLOCKS = YES; 257 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 258 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 259 | GCC_WARN_UNDECLARED_SELECTOR = YES; 260 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 261 | GCC_WARN_UNUSED_FUNCTION = YES; 262 | GCC_WARN_UNUSED_VARIABLE = YES; 263 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 264 | MTL_ENABLE_DEBUG_INFO = NO; 265 | SDKROOT = iphoneos; 266 | SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; 267 | TARGETED_DEVICE_FAMILY = "1,2"; 268 | VALIDATE_PRODUCT = YES; 269 | VERSIONING_SYSTEM = "apple-generic"; 270 | VERSION_INFO_PREFIX = ""; 271 | }; 272 | name = Release; 273 | }; 274 | AFE0BC5F1F5FADB70007D373 /* Debug */ = { 275 | isa = XCBuildConfiguration; 276 | buildSettings = { 277 | CLANG_ENABLE_MODULES = YES; 278 | CODE_SIGN_IDENTITY = ""; 279 | DEFINES_MODULE = YES; 280 | DYLIB_COMPATIBILITY_VERSION = 1; 281 | DYLIB_CURRENT_VERSION = 1; 282 | DYLIB_INSTALL_NAME_BASE = "@rpath"; 283 | INFOPLIST_FILE = GradientLoading/Info.plist; 284 | INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; 285 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; 286 | PRODUCT_BUNDLE_IDENTIFIER = kr.feather.GradientLoading; 287 | PRODUCT_NAME = "$(TARGET_NAME)"; 288 | SKIP_INSTALL = YES; 289 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 290 | SWIFT_VERSION = 3.0; 291 | }; 292 | name = Debug; 293 | }; 294 | AFE0BC601F5FADB70007D373 /* Release */ = { 295 | isa = XCBuildConfiguration; 296 | buildSettings = { 297 | CLANG_ENABLE_MODULES = YES; 298 | CODE_SIGN_IDENTITY = ""; 299 | DEFINES_MODULE = YES; 300 | DYLIB_COMPATIBILITY_VERSION = 1; 301 | DYLIB_CURRENT_VERSION = 1; 302 | DYLIB_INSTALL_NAME_BASE = "@rpath"; 303 | INFOPLIST_FILE = GradientLoading/Info.plist; 304 | INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; 305 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; 306 | PRODUCT_BUNDLE_IDENTIFIER = kr.feather.GradientLoading; 307 | PRODUCT_NAME = "$(TARGET_NAME)"; 308 | SKIP_INSTALL = YES; 309 | SWIFT_VERSION = 3.0; 310 | }; 311 | name = Release; 312 | }; 313 | /* End XCBuildConfiguration section */ 314 | 315 | /* Begin XCConfigurationList section */ 316 | AFE0BC501F5FADB70007D373 /* Build configuration list for PBXProject "GradientLoading" */ = { 317 | isa = XCConfigurationList; 318 | buildConfigurations = ( 319 | AFE0BC5C1F5FADB70007D373 /* Debug */, 320 | AFE0BC5D1F5FADB70007D373 /* Release */, 321 | ); 322 | defaultConfigurationIsVisible = 0; 323 | defaultConfigurationName = Release; 324 | }; 325 | AFE0BC5E1F5FADB70007D373 /* Build configuration list for PBXNativeTarget "GradientLoading" */ = { 326 | isa = XCConfigurationList; 327 | buildConfigurations = ( 328 | AFE0BC5F1F5FADB70007D373 /* Debug */, 329 | AFE0BC601F5FADB70007D373 /* Release */, 330 | ); 331 | defaultConfigurationIsVisible = 0; 332 | defaultConfigurationName = Release; 333 | }; 334 | /* End XCConfigurationList section */ 335 | }; 336 | rootObject = AFE0BC4D1F5FADB70007D373 /* Project object */; 337 | } 338 | -------------------------------------------------------------------------------- /GradientLoading.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /GradientLoading/Classes/Extensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Extensions.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | public extension UIImage { 12 | public class func image(layer: CAGradientLayer) -> UIImage { 13 | UIGraphicsBeginImageContextWithOptions(layer.bounds.size, layer.isOpaque, 0.0) 14 | layer.render(in: UIGraphicsGetCurrentContext()!) 15 | let image = UIGraphicsGetImageFromCurrentImageContext()! 16 | UIGraphicsEndImageContext() 17 | return image 18 | } 19 | } 20 | 21 | extension UIColor { 22 | convenience init(hex: String, alpha: CGFloat = 1.0) { 23 | let scanner = Scanner(string: hex) 24 | scanner.scanLocation = 0 25 | 26 | var rgbValue: UInt64 = 0 27 | 28 | scanner.scanHexInt64(&rgbValue) 29 | 30 | let r = (rgbValue & 0xff0000) >> 16 31 | let g = (rgbValue & 0xff00) >> 8 32 | let b = rgbValue & 0xff 33 | 34 | self.init(red: CGFloat(r) / 0xff, green: CGFloat(g) / 0xff, blue: CGFloat(b) / 0xff, alpha: alpha) 35 | } 36 | } 37 | 38 | extension UIFont { 39 | class func HelveticaNeueBold(size: CGFloat) -> UIFont { 40 | return UIFont(name: "HelveticaNeue-Bold", size: size)! 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /GradientLoading/Classes/GradientCollection.swift: -------------------------------------------------------------------------------- 1 | // 2 | // GradientCollection.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | public enum GradientCollection { 12 | case cottonCandy 13 | case oldHat 14 | case starWine 15 | case aurora 16 | case sunSet 17 | 18 | public func colors() -> [UIColor] { 19 | switch self { 20 | case .cottonCandy: 21 | return [#colorLiteral(red: 0.9803921569, green: 0.6745098039, blue: 0.6588235294, alpha: 1), #colorLiteral(red: 0.8666666667, green: 0.8392156863, blue: 0.9529411765, alpha: 1), #colorLiteral(red: 1, green: 0.8705882353, blue: 0.9137254902, alpha: 1), #colorLiteral(red: 0.7098039216, green: 1, blue: 0.9882352941, alpha: 1)] 22 | case .oldHat: 23 | return [#colorLiteral(red: 0.8941176471, green: 0.6862745098, blue: 0.7960784314, alpha: 1), #colorLiteral(red: 0.7215686275, green: 0.7960784314, blue: 0.7215686275, alpha: 1), #colorLiteral(red: 0.8862745098, green: 0.7725490196, blue: 0.5450980392, alpha: 1), #colorLiteral(red: 0.7607843137, green: 0.8078431373, blue: 0.6117647059, alpha: 1), #colorLiteral(red: 0.4941176471, green: 0.8588235294, blue: 0.862745098, alpha: 1)] 24 | case .starWine: 25 | return [#colorLiteral(red: 0.7215686275, green: 0.7960784314, blue: 0.7215686275, alpha: 1), #colorLiteral(red: 0.7058823529, green: 0.3960784314, blue: 0.8549019608, alpha: 1), #colorLiteral(red: 0.8117647059, green: 0.4235294118, blue: 0.7882352941, alpha: 1), #colorLiteral(red: 0.9333333333, green: 0.3764705882, blue: 0.6117647059, alpha: 1)] 26 | case .aurora: 27 | return [#colorLiteral(red: 0.9803921569, green: 0.5450980392, blue: 1, alpha: 1), #colorLiteral(red: 0.168627451, green: 1, blue: 0.5333333333, alpha: 1), #colorLiteral(red: 0.168627451, green: 0.8235294118, blue: 1, alpha: 1), #colorLiteral(red: 0.9333333333, green: 0.4549019608, blue: 0.8823529412, alpha: 1), #colorLiteral(red: 0.2431372549, green: 0.9254901961, blue: 0.6745098039, alpha: 1)] 28 | case .sunSet: 29 | return [#colorLiteral(red: 0.662745098, green: 0.7882352941, blue: 1, alpha: 1), #colorLiteral(red: 1, green: 0.4156862745, blue: 0.5333333333, alpha: 1), #colorLiteral(red: 1, green: 0.7333333333, blue: 0.9254901961, alpha: 1), #colorLiteral(red: 0.9333333333, green: 0.4549019608, blue: 0.8823529412, alpha: 1)] 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /GradientLoading/Classes/GradientColors.swift: -------------------------------------------------------------------------------- 1 | // 2 | // GradientColors.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | public typealias Colors = [UIColor] 12 | public typealias GradientColors = [CGColor] 13 | -------------------------------------------------------------------------------- /GradientLoading/Classes/GradientLabel.swift: -------------------------------------------------------------------------------- 1 | // 2 | // GradientLabel.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | public class GradientLabel: UILabel { 12 | var gradientPoint: (start: CGPoint, end: CGPoint) = (GradientPoint.topLeft.point, GradientPoint.bottomRight.point) 13 | 14 | @nonobjc 15 | var gradientColors: GradientColors = GradientCollection.oldHat.colors().map {$0.cgColor} { 16 | didSet { 17 | guard bounds.size != .zero else { return } 18 | 19 | if let color = generateGradientColor() { 20 | textColor = color 21 | } 22 | } 23 | } 24 | 25 | var gradientFont: UIFont = .HelveticaNeueBold(size: 20) 26 | var gradientStrokeColor: UIColor = .black 27 | var gradientStrokeWidth: Float = -3.0 28 | 29 | // MARK: - Initializers 30 | public convenience init() { 31 | self.init(frame: .zero) 32 | } 33 | 34 | public override init(frame: CGRect) { 35 | super.init(frame: .zero) 36 | setup() 37 | } 38 | 39 | public override func layoutSubviews() { 40 | super.layoutSubviews() 41 | 42 | if let color = generateGradientColor() { 43 | textColor = color 44 | } 45 | } 46 | 47 | public required init?(coder aDecoder: NSCoder) { 48 | fatalError("init(coder:) has not been implemented") 49 | } 50 | 51 | func setup() { 52 | let attributes: [String : Any] = [NSFontAttributeName : gradientFont, 53 | NSStrokeColorAttributeName : gradientStrokeColor, 54 | NSStrokeWidthAttributeName : gradientStrokeWidth] 55 | 56 | attributedText = NSAttributedString(string: text ?? "Loading...", attributes: attributes) 57 | textAlignment = .center 58 | numberOfLines = 0 59 | } 60 | 61 | fileprivate func generateGradientColor() -> UIColor? { 62 | let gradientLayer = CAGradientLayer() 63 | gradientLayer.bounds = bounds 64 | gradientLayer.colors = gradientColors 65 | gradientLayer.startPoint = gradientPoint.start 66 | gradientLayer.endPoint = gradientPoint.end 67 | 68 | let gradientImage = UIImage.image(layer: gradientLayer) 69 | 70 | UIGraphicsBeginImageContext(frame.size) 71 | gradientImage.draw(in: bounds) 72 | let opImage = UIGraphicsGetImageFromCurrentImageContext() 73 | UIGraphicsEndImageContext() 74 | 75 | guard let image = opImage else { 76 | return nil 77 | } 78 | 79 | return UIColor(patternImage: image) 80 | } 81 | } 82 | -------------------------------------------------------------------------------- /GradientLoading/Classes/GradientLoading.swift: -------------------------------------------------------------------------------- 1 | // 2 | // GradientLoading.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | public class GradientLoading { 12 | public static let shared = GradientLoading() 13 | 14 | fileprivate lazy var containerView: UIView = { 15 | let view = UIView() 16 | view.backgroundColor = UIColor(hex: "000000", alpha: 0.7) 17 | view.translatesAutoresizingMaskIntoConstraints = false 18 | 19 | return view 20 | }() 21 | 22 | fileprivate lazy var gradientLabel: GradientLabel = { 23 | let label = GradientLabel() 24 | label.gradientPoint = self.point 25 | label.gradientColors = self.getGradientColors() 26 | label.translatesAutoresizingMaskIntoConstraints = false 27 | 28 | return label 29 | }() 30 | 31 | public var text: String = "Loading" { 32 | didSet { 33 | gradientLabel.text = text 34 | } 35 | } 36 | 37 | fileprivate var currentIndex: Int = 0 38 | fileprivate var colors: Colors = GradientCollection.starWine.colors() 39 | 40 | public var duration: TimeInterval = 1.5 41 | public var point: (start: CGPoint, end: CGPoint) = (GradientPoint.topLeft.point, GradientPoint.bottomRight.point) 42 | 43 | fileprivate var addtoKeyWindow: Bool = false 44 | fileprivate var continueAnimation: Bool = false 45 | 46 | // MARK: - Initializers 47 | private init() { 48 | setup() 49 | } 50 | 51 | // MARK: - Setup 52 | fileprivate func setup() { 53 | containerView.addSubview(gradientLabel) 54 | 55 | containerView.addConstraints([ NSLayoutConstraint(item: gradientLabel, 56 | attribute: .centerX, 57 | relatedBy: .equal, 58 | toItem: containerView, 59 | attribute: .centerX, 60 | multiplier: 1.0, 61 | constant: 0.0), 62 | 63 | NSLayoutConstraint(item: gradientLabel, 64 | attribute: .centerY, 65 | relatedBy: .equal, 66 | toItem: containerView, 67 | attribute: .centerY, 68 | multiplier: 1.0, 69 | constant: 0.0) ]) 70 | } 71 | 72 | public func setFontAttributes(text: String = "Loading...", font: UIFont = .HelveticaNeueBold(size: 20), strokecolor: UIColor = .black, strokeWidth: Float = -3.0) { 73 | gradientLabel.text = text 74 | gradientLabel.gradientFont = font 75 | gradientLabel.gradientStrokeColor = strokecolor 76 | gradientLabel.gradientStrokeWidth = strokeWidth 77 | 78 | gradientLabel.setup() 79 | } 80 | 81 | public func setDimColor(_ color: UIColor) { 82 | containerView.backgroundColor = color 83 | } 84 | 85 | public func setColors(_ colors: Colors) { 86 | guard colors.count > 0 else { return } 87 | self.colors = colors 88 | } 89 | 90 | public func setCollectionColors(_ collection: GradientCollection) { 91 | colors = collection.colors() 92 | } 93 | 94 | fileprivate func addToKeyWindowConstraint() { 95 | guard let keyWindow = UIApplication.shared.windows.first else { 96 | print("GradientLoading can not added to keyWindow. Please try again") 97 | return 98 | } 99 | 100 | DispatchQueue.main.async { 101 | keyWindow.addSubview(self.containerView) 102 | keyWindow.bringSubview(toFront: self.containerView) 103 | 104 | keyWindow.addConstraints([ NSLayoutConstraint(item: self.containerView, 105 | attribute: .top, 106 | relatedBy: .equal, 107 | toItem: keyWindow, 108 | attribute: .top, 109 | multiplier: 1.0, 110 | constant: 0.0), 111 | 112 | NSLayoutConstraint(item: self.containerView, 113 | attribute: .bottom, 114 | relatedBy: .equal, 115 | toItem: keyWindow, 116 | attribute: .bottom, 117 | multiplier: 1.0, 118 | constant: 0.0), 119 | 120 | NSLayoutConstraint(item: self.containerView, 121 | attribute: .leading, 122 | relatedBy: .equal, 123 | toItem: keyWindow, 124 | attribute: .leading, 125 | multiplier: 1.0, 126 | constant: 0.0), 127 | 128 | NSLayoutConstraint(item: self.containerView, 129 | attribute: .trailing, 130 | relatedBy: .equal, 131 | toItem: keyWindow, 132 | attribute: .trailing, 133 | multiplier: 1.0, 134 | constant: 0.0) ]) 135 | } 136 | 137 | addtoKeyWindow = true 138 | } 139 | 140 | // MARK: - Main Function 141 | public func show() { 142 | if addtoKeyWindow == false { 143 | addToKeyWindowConstraint() 144 | } 145 | 146 | if addtoKeyWindow { 147 | continueAnimation = true 148 | startAnimation() 149 | } 150 | } 151 | 152 | public func hide() { 153 | stopAnimation() 154 | containerView.removeFromSuperview() 155 | addtoKeyWindow = false 156 | } 157 | 158 | fileprivate func startAnimation() { 159 | currentIndex += 1 160 | UIView.transition(with: gradientLabel, duration: duration, options: .transitionCrossDissolve, animations: { 161 | self.gradientLabel.gradientColors = self.getGradientColors() 162 | }) { _ in 163 | if self.continueAnimation { self.startAnimation() } 164 | } 165 | } 166 | 167 | fileprivate func stopAnimation() { 168 | currentIndex = 0 169 | continueAnimation = false 170 | } 171 | 172 | // MARK: - Fetch Gradient Colors 173 | fileprivate func getGradientColors() -> GradientColors { 174 | guard colors.count > 0 else { return [] } 175 | 176 | return [colors[currentIndex % colors.count].cgColor, 177 | colors[(currentIndex + 1) % colors.count].cgColor, 178 | colors[currentIndex % colors.count].cgColor, 179 | colors[(currentIndex + 1) % colors.count].cgColor] 180 | } 181 | } 182 | -------------------------------------------------------------------------------- /GradientLoading/Classes/GradientPoint.swift: -------------------------------------------------------------------------------- 1 | // 2 | // GradientPoint.swift 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | public enum GradientPoint { 12 | case top 13 | case left 14 | case bottom 15 | case right 16 | case topLeft 17 | case topRight 18 | case bottomLeft 19 | case bottomRight 20 | 21 | var point: CGPoint { 22 | switch self { 23 | case .top: return CGPoint(x: 0.5, y: 0.0) 24 | case .left: return CGPoint(x: 0.0, y: 0.5) 25 | case .bottom: return CGPoint(x: 0.5, y: 1.0) 26 | case .right: return CGPoint(x: 1.0, y: 0.5) 27 | case .topLeft: return CGPoint(x: 0.0, y: 0.0) 28 | case .topRight: return CGPoint(x: 1.0, y: 0.0) 29 | case .bottomLeft: return CGPoint(x: 0.0, y: 1.0) 30 | case .bottomRight: return CGPoint(x: 1.0, y: 1.0) 31 | } 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /GradientLoading/GradientLoading.h: -------------------------------------------------------------------------------- 1 | // 2 | // GradientLoading.h 3 | // GradientLoading 4 | // 5 | // Created by nb0031 on 2017. 9. 6.. 6 | // Copyright © 2017년 feather. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | //! Project version number for GradientLoading. 12 | FOUNDATION_EXPORT double GradientLoadingVersionNumber; 13 | 14 | //! Project version string for GradientLoading. 15 | FOUNDATION_EXPORT const unsigned char GradientLoadingVersionString[]; 16 | 17 | // In this header, you should import all the public headers of your framework using statements like #import 18 | 19 | 20 | -------------------------------------------------------------------------------- /GradientLoading/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | FMWK 17 | CFBundleShortVersionString 18 | 0.0.1 19 | CFBundleVersion 20 | $(CURRENT_PROJECT_VERSION) 21 | NSPrincipalClass 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /Images/GradientLoading.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/devfeather/GradientLoading/e3f754f781909a00f20431fa6097a5ab98b017e3/Images/GradientLoading.gif -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2017 feather 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is 8 | furnished to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 15 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 16 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 17 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 18 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 19 | THE SOFTWARE. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # GradientLoading 2 | 3 | ![Swift](https://img.shields.io/badge/Swift-3.0-orange.svg) 4 | [![CocoaPods](http://img.shields.io/cocoapods/v/GradientLoading.svg?style=flat)](http://cocoapods.org/?q=name%3AGradientLoading%20author%3Afeather) 5 | 6 | - Easy to use Loading View in iOS 7 | 8 | ![image](Images/GradientLoading.gif) 9 | 10 | ## Requirements 11 | - iOS 8.0+ 12 | - Swift 3.0 13 | 14 | ## Example 15 | To run the example project, clone the repo, and run `pod install` from the Example directory first. 16 | 17 | ## Installation 18 | 19 | #### CocoaPods 20 | GradientLoading is available through [CocoaPods](http://cocoapods.org). To install 21 | it, simply add the following line to your Podfile: 22 | 23 | ```ruby 24 | pod 'GradientLoading' 25 | ``` 26 | 27 | ## Usage 28 | ```swift 29 | // Setup Text, Font, Stroke Color, Stroke Width. 30 | GradientLoading.shared.setFontAttributes(text: "Jennie") 31 | 32 | // use setCollectionColors or setColors. 33 | GradientLoading.shared.setCollectionColors(.aurora) 34 | // GradientLoading.shared.setColors([]) 35 | 36 | GradientLoading.shared.show() 37 | ``` 38 | 39 | ## Author 40 | 41 | feather, dev.thefeather@gmail.com 42 | 43 | ## License 44 | 45 | GradientLoading is available under the MIT license. See the LICENSE file for more info. 46 | --------------------------------------------------------------------------------