├── KYPushTransitionDemo ├── KYPushTransitionDemo.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcuserdata │ │ │ └── KittenYang.xcuserdatad │ │ │ └── UserInterfaceState.xcuserstate │ └── xcuserdata │ │ └── KittenYang.xcuserdatad │ │ ├── xcdebugger │ │ └── Breakpoints_v2.xcbkptlist │ │ └── xcschemes │ │ ├── KYPushTransitionDemo.xcscheme │ │ └── xcschememanagement.plist ├── KYPushTransitionDemo │ ├── AppDelegate.h │ ├── AppDelegate.m │ ├── Base.lproj │ │ ├── LaunchScreen.xib │ │ └── Main.storyboard │ ├── FirstViewController.h │ ├── FirstViewController.m │ ├── Images.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ └── Home.imageset │ │ │ ├── Contents.json │ │ │ ├── IMG_4087-1.JPG │ │ │ ├── IMG_4087-2.JPG │ │ │ └── IMG_4087.JPG │ ├── Info.plist │ ├── KYPopInteractiveTransition.h │ ├── KYPopInteractiveTransition.m │ ├── KYPopTransition.h │ ├── KYPopTransition.m │ ├── KYPushTransition.h │ ├── KYPushTransition.m │ ├── SecondViewController.h │ ├── SecondViewController.m │ └── main.m └── KYPushTransitionDemoTests │ ├── Info.plist │ └── KYPushTransitionDemoTests.m ├── README.md └── demo.gif /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 46; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 5F3362CB1AE294C600D574A1 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362CA1AE294C600D574A1 /* main.m */; }; 11 | 5F3362CE1AE294C600D574A1 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362CD1AE294C600D574A1 /* AppDelegate.m */; }; 12 | 5F3362D11AE294C600D574A1 /* FirstViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362D01AE294C600D574A1 /* FirstViewController.m */; }; 13 | 5F3362D41AE294C600D574A1 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 5F3362D21AE294C600D574A1 /* Main.storyboard */; }; 14 | 5F3362D61AE294C600D574A1 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 5F3362D51AE294C600D574A1 /* Images.xcassets */; }; 15 | 5F3362D91AE294C600D574A1 /* LaunchScreen.xib in Resources */ = {isa = PBXBuildFile; fileRef = 5F3362D71AE294C600D574A1 /* LaunchScreen.xib */; }; 16 | 5F3362E51AE294C700D574A1 /* KYPushTransitionDemoTests.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362E41AE294C700D574A1 /* KYPushTransitionDemoTests.m */; }; 17 | 5F3362F01AE2950900D574A1 /* KYPushTransition.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362EF1AE2950900D574A1 /* KYPushTransition.m */; }; 18 | 5F3362F51AE2A94C00D574A1 /* SecondViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362F41AE2A94C00D574A1 /* SecondViewController.m */; }; 19 | 5F3362F81AE2BB9000D574A1 /* KYPopTransition.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3362F71AE2BB9000D574A1 /* KYPopTransition.m */; }; 20 | 5F3363011AE3E5B900D574A1 /* KYPopInteractiveTransition.m in Sources */ = {isa = PBXBuildFile; fileRef = 5F3363001AE3E5B900D574A1 /* KYPopInteractiveTransition.m */; }; 21 | /* End PBXBuildFile section */ 22 | 23 | /* Begin PBXContainerItemProxy section */ 24 | 5F3362DF1AE294C700D574A1 /* PBXContainerItemProxy */ = { 25 | isa = PBXContainerItemProxy; 26 | containerPortal = 5F3362BD1AE294C600D574A1 /* Project object */; 27 | proxyType = 1; 28 | remoteGlobalIDString = 5F3362C41AE294C600D574A1; 29 | remoteInfo = KYPushTransitionDemo; 30 | }; 31 | /* End PBXContainerItemProxy section */ 32 | 33 | /* Begin PBXFileReference section */ 34 | 5F3362C51AE294C600D574A1 /* KYPushTransitionDemo.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = KYPushTransitionDemo.app; sourceTree = BUILT_PRODUCTS_DIR; }; 35 | 5F3362C91AE294C600D574A1 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 36 | 5F3362CA1AE294C600D574A1 /* main.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = ""; }; 37 | 5F3362CC1AE294C600D574A1 /* AppDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = ""; }; 38 | 5F3362CD1AE294C600D574A1 /* AppDelegate.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = ""; }; 39 | 5F3362CF1AE294C600D574A1 /* FirstViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = FirstViewController.h; sourceTree = ""; }; 40 | 5F3362D01AE294C600D574A1 /* FirstViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = FirstViewController.m; sourceTree = ""; }; 41 | 5F3362D31AE294C600D574A1 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 42 | 5F3362D51AE294C600D574A1 /* Images.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Images.xcassets; sourceTree = ""; }; 43 | 5F3362D81AE294C600D574A1 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/LaunchScreen.xib; sourceTree = ""; }; 44 | 5F3362DE1AE294C700D574A1 /* KYPushTransitionDemoTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = KYPushTransitionDemoTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 45 | 5F3362E31AE294C700D574A1 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 46 | 5F3362E41AE294C700D574A1 /* KYPushTransitionDemoTests.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = KYPushTransitionDemoTests.m; sourceTree = ""; }; 47 | 5F3362EE1AE2950900D574A1 /* KYPushTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KYPushTransition.h; sourceTree = ""; }; 48 | 5F3362EF1AE2950900D574A1 /* KYPushTransition.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KYPushTransition.m; sourceTree = ""; }; 49 | 5F3362F31AE2A94C00D574A1 /* SecondViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SecondViewController.h; sourceTree = ""; }; 50 | 5F3362F41AE2A94C00D574A1 /* SecondViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SecondViewController.m; sourceTree = ""; }; 51 | 5F3362F61AE2BB9000D574A1 /* KYPopTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KYPopTransition.h; sourceTree = ""; }; 52 | 5F3362F71AE2BB9000D574A1 /* KYPopTransition.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KYPopTransition.m; sourceTree = ""; }; 53 | 5F3362FF1AE3E5B900D574A1 /* KYPopInteractiveTransition.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KYPopInteractiveTransition.h; sourceTree = ""; }; 54 | 5F3363001AE3E5B900D574A1 /* KYPopInteractiveTransition.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KYPopInteractiveTransition.m; sourceTree = ""; }; 55 | /* End PBXFileReference section */ 56 | 57 | /* Begin PBXFrameworksBuildPhase section */ 58 | 5F3362C21AE294C600D574A1 /* Frameworks */ = { 59 | isa = PBXFrameworksBuildPhase; 60 | buildActionMask = 2147483647; 61 | files = ( 62 | ); 63 | runOnlyForDeploymentPostprocessing = 0; 64 | }; 65 | 5F3362DB1AE294C700D574A1 /* Frameworks */ = { 66 | isa = PBXFrameworksBuildPhase; 67 | buildActionMask = 2147483647; 68 | files = ( 69 | ); 70 | runOnlyForDeploymentPostprocessing = 0; 71 | }; 72 | /* End PBXFrameworksBuildPhase section */ 73 | 74 | /* Begin PBXGroup section */ 75 | 5F3362BC1AE294C600D574A1 = { 76 | isa = PBXGroup; 77 | children = ( 78 | 5F3362C71AE294C600D574A1 /* KYPushTransitionDemo */, 79 | 5F3362E11AE294C700D574A1 /* KYPushTransitionDemoTests */, 80 | 5F3362C61AE294C600D574A1 /* Products */, 81 | ); 82 | sourceTree = ""; 83 | }; 84 | 5F3362C61AE294C600D574A1 /* Products */ = { 85 | isa = PBXGroup; 86 | children = ( 87 | 5F3362C51AE294C600D574A1 /* KYPushTransitionDemo.app */, 88 | 5F3362DE1AE294C700D574A1 /* KYPushTransitionDemoTests.xctest */, 89 | ); 90 | name = Products; 91 | sourceTree = ""; 92 | }; 93 | 5F3362C71AE294C600D574A1 /* KYPushTransitionDemo */ = { 94 | isa = PBXGroup; 95 | children = ( 96 | 5F3362CC1AE294C600D574A1 /* AppDelegate.h */, 97 | 5F3362CD1AE294C600D574A1 /* AppDelegate.m */, 98 | 5F3362CF1AE294C600D574A1 /* FirstViewController.h */, 99 | 5F3362D01AE294C600D574A1 /* FirstViewController.m */, 100 | 5F3362F31AE2A94C00D574A1 /* SecondViewController.h */, 101 | 5F3362F41AE2A94C00D574A1 /* SecondViewController.m */, 102 | 5F3362F11AE2951800D574A1 /* class */, 103 | 5F3362D21AE294C600D574A1 /* Main.storyboard */, 104 | 5F3362D51AE294C600D574A1 /* Images.xcassets */, 105 | 5F3362D71AE294C600D574A1 /* LaunchScreen.xib */, 106 | 5F3362C81AE294C600D574A1 /* Supporting Files */, 107 | ); 108 | path = KYPushTransitionDemo; 109 | sourceTree = ""; 110 | }; 111 | 5F3362C81AE294C600D574A1 /* Supporting Files */ = { 112 | isa = PBXGroup; 113 | children = ( 114 | 5F3362C91AE294C600D574A1 /* Info.plist */, 115 | 5F3362CA1AE294C600D574A1 /* main.m */, 116 | ); 117 | name = "Supporting Files"; 118 | sourceTree = ""; 119 | }; 120 | 5F3362E11AE294C700D574A1 /* KYPushTransitionDemoTests */ = { 121 | isa = PBXGroup; 122 | children = ( 123 | 5F3362E41AE294C700D574A1 /* KYPushTransitionDemoTests.m */, 124 | 5F3362E21AE294C700D574A1 /* Supporting Files */, 125 | ); 126 | path = KYPushTransitionDemoTests; 127 | sourceTree = ""; 128 | }; 129 | 5F3362E21AE294C700D574A1 /* Supporting Files */ = { 130 | isa = PBXGroup; 131 | children = ( 132 | 5F3362E31AE294C700D574A1 /* Info.plist */, 133 | ); 134 | name = "Supporting Files"; 135 | sourceTree = ""; 136 | }; 137 | 5F3362F11AE2951800D574A1 /* class */ = { 138 | isa = PBXGroup; 139 | children = ( 140 | 5F3362EE1AE2950900D574A1 /* KYPushTransition.h */, 141 | 5F3362EF1AE2950900D574A1 /* KYPushTransition.m */, 142 | 5F3362F61AE2BB9000D574A1 /* KYPopTransition.h */, 143 | 5F3362F71AE2BB9000D574A1 /* KYPopTransition.m */, 144 | 5F3362FF1AE3E5B900D574A1 /* KYPopInteractiveTransition.h */, 145 | 5F3363001AE3E5B900D574A1 /* KYPopInteractiveTransition.m */, 146 | ); 147 | name = class; 148 | sourceTree = ""; 149 | }; 150 | /* End PBXGroup section */ 151 | 152 | /* Begin PBXNativeTarget section */ 153 | 5F3362C41AE294C600D574A1 /* KYPushTransitionDemo */ = { 154 | isa = PBXNativeTarget; 155 | buildConfigurationList = 5F3362E81AE294C700D574A1 /* Build configuration list for PBXNativeTarget "KYPushTransitionDemo" */; 156 | buildPhases = ( 157 | 5F3362C11AE294C600D574A1 /* Sources */, 158 | 5F3362C21AE294C600D574A1 /* Frameworks */, 159 | 5F3362C31AE294C600D574A1 /* Resources */, 160 | ); 161 | buildRules = ( 162 | ); 163 | dependencies = ( 164 | ); 165 | name = KYPushTransitionDemo; 166 | productName = KYPushTransitionDemo; 167 | productReference = 5F3362C51AE294C600D574A1 /* KYPushTransitionDemo.app */; 168 | productType = "com.apple.product-type.application"; 169 | }; 170 | 5F3362DD1AE294C700D574A1 /* KYPushTransitionDemoTests */ = { 171 | isa = PBXNativeTarget; 172 | buildConfigurationList = 5F3362EB1AE294C700D574A1 /* Build configuration list for PBXNativeTarget "KYPushTransitionDemoTests" */; 173 | buildPhases = ( 174 | 5F3362DA1AE294C700D574A1 /* Sources */, 175 | 5F3362DB1AE294C700D574A1 /* Frameworks */, 176 | 5F3362DC1AE294C700D574A1 /* Resources */, 177 | ); 178 | buildRules = ( 179 | ); 180 | dependencies = ( 181 | 5F3362E01AE294C700D574A1 /* PBXTargetDependency */, 182 | ); 183 | name = KYPushTransitionDemoTests; 184 | productName = KYPushTransitionDemoTests; 185 | productReference = 5F3362DE1AE294C700D574A1 /* KYPushTransitionDemoTests.xctest */; 186 | productType = "com.apple.product-type.bundle.unit-test"; 187 | }; 188 | /* End PBXNativeTarget section */ 189 | 190 | /* Begin PBXProject section */ 191 | 5F3362BD1AE294C600D574A1 /* Project object */ = { 192 | isa = PBXProject; 193 | attributes = { 194 | LastUpgradeCheck = 0630; 195 | ORGANIZATIONNAME = "Kitten Yang"; 196 | TargetAttributes = { 197 | 5F3362C41AE294C600D574A1 = { 198 | CreatedOnToolsVersion = 6.3; 199 | }; 200 | 5F3362DD1AE294C700D574A1 = { 201 | CreatedOnToolsVersion = 6.3; 202 | TestTargetID = 5F3362C41AE294C600D574A1; 203 | }; 204 | }; 205 | }; 206 | buildConfigurationList = 5F3362C01AE294C600D574A1 /* Build configuration list for PBXProject "KYPushTransitionDemo" */; 207 | compatibilityVersion = "Xcode 3.2"; 208 | developmentRegion = English; 209 | hasScannedForEncodings = 0; 210 | knownRegions = ( 211 | en, 212 | Base, 213 | ); 214 | mainGroup = 5F3362BC1AE294C600D574A1; 215 | productRefGroup = 5F3362C61AE294C600D574A1 /* Products */; 216 | projectDirPath = ""; 217 | projectRoot = ""; 218 | targets = ( 219 | 5F3362C41AE294C600D574A1 /* KYPushTransitionDemo */, 220 | 5F3362DD1AE294C700D574A1 /* KYPushTransitionDemoTests */, 221 | ); 222 | }; 223 | /* End PBXProject section */ 224 | 225 | /* Begin PBXResourcesBuildPhase section */ 226 | 5F3362C31AE294C600D574A1 /* Resources */ = { 227 | isa = PBXResourcesBuildPhase; 228 | buildActionMask = 2147483647; 229 | files = ( 230 | 5F3362D41AE294C600D574A1 /* Main.storyboard in Resources */, 231 | 5F3362D91AE294C600D574A1 /* LaunchScreen.xib in Resources */, 232 | 5F3362D61AE294C600D574A1 /* Images.xcassets in Resources */, 233 | ); 234 | runOnlyForDeploymentPostprocessing = 0; 235 | }; 236 | 5F3362DC1AE294C700D574A1 /* Resources */ = { 237 | isa = PBXResourcesBuildPhase; 238 | buildActionMask = 2147483647; 239 | files = ( 240 | ); 241 | runOnlyForDeploymentPostprocessing = 0; 242 | }; 243 | /* End PBXResourcesBuildPhase section */ 244 | 245 | /* Begin PBXSourcesBuildPhase section */ 246 | 5F3362C11AE294C600D574A1 /* Sources */ = { 247 | isa = PBXSourcesBuildPhase; 248 | buildActionMask = 2147483647; 249 | files = ( 250 | 5F3362F81AE2BB9000D574A1 /* KYPopTransition.m in Sources */, 251 | 5F3362F51AE2A94C00D574A1 /* SecondViewController.m in Sources */, 252 | 5F3362F01AE2950900D574A1 /* KYPushTransition.m in Sources */, 253 | 5F3362D11AE294C600D574A1 /* FirstViewController.m in Sources */, 254 | 5F3362CE1AE294C600D574A1 /* AppDelegate.m in Sources */, 255 | 5F3363011AE3E5B900D574A1 /* KYPopInteractiveTransition.m in Sources */, 256 | 5F3362CB1AE294C600D574A1 /* main.m in Sources */, 257 | ); 258 | runOnlyForDeploymentPostprocessing = 0; 259 | }; 260 | 5F3362DA1AE294C700D574A1 /* Sources */ = { 261 | isa = PBXSourcesBuildPhase; 262 | buildActionMask = 2147483647; 263 | files = ( 264 | 5F3362E51AE294C700D574A1 /* KYPushTransitionDemoTests.m in Sources */, 265 | ); 266 | runOnlyForDeploymentPostprocessing = 0; 267 | }; 268 | /* End PBXSourcesBuildPhase section */ 269 | 270 | /* Begin PBXTargetDependency section */ 271 | 5F3362E01AE294C700D574A1 /* PBXTargetDependency */ = { 272 | isa = PBXTargetDependency; 273 | target = 5F3362C41AE294C600D574A1 /* KYPushTransitionDemo */; 274 | targetProxy = 5F3362DF1AE294C700D574A1 /* PBXContainerItemProxy */; 275 | }; 276 | /* End PBXTargetDependency section */ 277 | 278 | /* Begin PBXVariantGroup section */ 279 | 5F3362D21AE294C600D574A1 /* Main.storyboard */ = { 280 | isa = PBXVariantGroup; 281 | children = ( 282 | 5F3362D31AE294C600D574A1 /* Base */, 283 | ); 284 | name = Main.storyboard; 285 | sourceTree = ""; 286 | }; 287 | 5F3362D71AE294C600D574A1 /* LaunchScreen.xib */ = { 288 | isa = PBXVariantGroup; 289 | children = ( 290 | 5F3362D81AE294C600D574A1 /* Base */, 291 | ); 292 | name = LaunchScreen.xib; 293 | sourceTree = ""; 294 | }; 295 | /* End PBXVariantGroup section */ 296 | 297 | /* Begin XCBuildConfiguration section */ 298 | 5F3362E61AE294C700D574A1 /* Debug */ = { 299 | isa = XCBuildConfiguration; 300 | buildSettings = { 301 | ALWAYS_SEARCH_USER_PATHS = NO; 302 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 303 | CLANG_CXX_LIBRARY = "libc++"; 304 | CLANG_ENABLE_MODULES = YES; 305 | CLANG_ENABLE_OBJC_ARC = YES; 306 | CLANG_WARN_BOOL_CONVERSION = YES; 307 | CLANG_WARN_CONSTANT_CONVERSION = YES; 308 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 309 | CLANG_WARN_EMPTY_BODY = YES; 310 | CLANG_WARN_ENUM_CONVERSION = YES; 311 | CLANG_WARN_INT_CONVERSION = YES; 312 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 313 | CLANG_WARN_UNREACHABLE_CODE = YES; 314 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 315 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 316 | COPY_PHASE_STRIP = NO; 317 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 318 | ENABLE_STRICT_OBJC_MSGSEND = YES; 319 | GCC_C_LANGUAGE_STANDARD = gnu99; 320 | GCC_DYNAMIC_NO_PIC = NO; 321 | GCC_NO_COMMON_BLOCKS = YES; 322 | GCC_OPTIMIZATION_LEVEL = 0; 323 | GCC_PREPROCESSOR_DEFINITIONS = ( 324 | "DEBUG=1", 325 | "$(inherited)", 326 | ); 327 | GCC_SYMBOLS_PRIVATE_EXTERN = NO; 328 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 329 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 330 | GCC_WARN_UNDECLARED_SELECTOR = YES; 331 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 332 | GCC_WARN_UNUSED_FUNCTION = YES; 333 | GCC_WARN_UNUSED_VARIABLE = YES; 334 | IPHONEOS_DEPLOYMENT_TARGET = 8.3; 335 | MTL_ENABLE_DEBUG_INFO = YES; 336 | ONLY_ACTIVE_ARCH = YES; 337 | SDKROOT = iphoneos; 338 | TARGETED_DEVICE_FAMILY = "1,2"; 339 | }; 340 | name = Debug; 341 | }; 342 | 5F3362E71AE294C700D574A1 /* Release */ = { 343 | isa = XCBuildConfiguration; 344 | buildSettings = { 345 | ALWAYS_SEARCH_USER_PATHS = NO; 346 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; 347 | CLANG_CXX_LIBRARY = "libc++"; 348 | CLANG_ENABLE_MODULES = YES; 349 | CLANG_ENABLE_OBJC_ARC = YES; 350 | CLANG_WARN_BOOL_CONVERSION = YES; 351 | CLANG_WARN_CONSTANT_CONVERSION = YES; 352 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 353 | CLANG_WARN_EMPTY_BODY = YES; 354 | CLANG_WARN_ENUM_CONVERSION = YES; 355 | CLANG_WARN_INT_CONVERSION = YES; 356 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 357 | CLANG_WARN_UNREACHABLE_CODE = YES; 358 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 359 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; 360 | COPY_PHASE_STRIP = NO; 361 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 362 | ENABLE_NS_ASSERTIONS = NO; 363 | ENABLE_STRICT_OBJC_MSGSEND = YES; 364 | GCC_C_LANGUAGE_STANDARD = gnu99; 365 | GCC_NO_COMMON_BLOCKS = YES; 366 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 367 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 368 | GCC_WARN_UNDECLARED_SELECTOR = YES; 369 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 370 | GCC_WARN_UNUSED_FUNCTION = YES; 371 | GCC_WARN_UNUSED_VARIABLE = YES; 372 | IPHONEOS_DEPLOYMENT_TARGET = 8.3; 373 | MTL_ENABLE_DEBUG_INFO = NO; 374 | SDKROOT = iphoneos; 375 | TARGETED_DEVICE_FAMILY = "1,2"; 376 | VALIDATE_PRODUCT = YES; 377 | }; 378 | name = Release; 379 | }; 380 | 5F3362E91AE294C700D574A1 /* Debug */ = { 381 | isa = XCBuildConfiguration; 382 | buildSettings = { 383 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 384 | CODE_SIGN_IDENTITY = "iPhone Developer: Xinyu Li (XWYND9KE57)"; 385 | INFOPLIST_FILE = KYPushTransitionDemo/Info.plist; 386 | IPHONEOS_DEPLOYMENT_TARGET = 7.0; 387 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 388 | PRODUCT_NAME = "$(TARGET_NAME)"; 389 | }; 390 | name = Debug; 391 | }; 392 | 5F3362EA1AE294C700D574A1 /* Release */ = { 393 | isa = XCBuildConfiguration; 394 | buildSettings = { 395 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 396 | INFOPLIST_FILE = KYPushTransitionDemo/Info.plist; 397 | IPHONEOS_DEPLOYMENT_TARGET = 7.0; 398 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; 399 | PRODUCT_NAME = "$(TARGET_NAME)"; 400 | }; 401 | name = Release; 402 | }; 403 | 5F3362EC1AE294C700D574A1 /* Debug */ = { 404 | isa = XCBuildConfiguration; 405 | buildSettings = { 406 | BUNDLE_LOADER = "$(TEST_HOST)"; 407 | FRAMEWORK_SEARCH_PATHS = ( 408 | "$(SDKROOT)/Developer/Library/Frameworks", 409 | "$(inherited)", 410 | ); 411 | GCC_PREPROCESSOR_DEFINITIONS = ( 412 | "DEBUG=1", 413 | "$(inherited)", 414 | ); 415 | INFOPLIST_FILE = KYPushTransitionDemoTests/Info.plist; 416 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; 417 | PRODUCT_NAME = "$(TARGET_NAME)"; 418 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/KYPushTransitionDemo.app/KYPushTransitionDemo"; 419 | }; 420 | name = Debug; 421 | }; 422 | 5F3362ED1AE294C700D574A1 /* Release */ = { 423 | isa = XCBuildConfiguration; 424 | buildSettings = { 425 | BUNDLE_LOADER = "$(TEST_HOST)"; 426 | FRAMEWORK_SEARCH_PATHS = ( 427 | "$(SDKROOT)/Developer/Library/Frameworks", 428 | "$(inherited)", 429 | ); 430 | INFOPLIST_FILE = KYPushTransitionDemoTests/Info.plist; 431 | LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks"; 432 | PRODUCT_NAME = "$(TARGET_NAME)"; 433 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/KYPushTransitionDemo.app/KYPushTransitionDemo"; 434 | }; 435 | name = Release; 436 | }; 437 | /* End XCBuildConfiguration section */ 438 | 439 | /* Begin XCConfigurationList section */ 440 | 5F3362C01AE294C600D574A1 /* Build configuration list for PBXProject "KYPushTransitionDemo" */ = { 441 | isa = XCConfigurationList; 442 | buildConfigurations = ( 443 | 5F3362E61AE294C700D574A1 /* Debug */, 444 | 5F3362E71AE294C700D574A1 /* Release */, 445 | ); 446 | defaultConfigurationIsVisible = 0; 447 | defaultConfigurationName = Release; 448 | }; 449 | 5F3362E81AE294C700D574A1 /* Build configuration list for PBXNativeTarget "KYPushTransitionDemo" */ = { 450 | isa = XCConfigurationList; 451 | buildConfigurations = ( 452 | 5F3362E91AE294C700D574A1 /* Debug */, 453 | 5F3362EA1AE294C700D574A1 /* Release */, 454 | ); 455 | defaultConfigurationIsVisible = 0; 456 | }; 457 | 5F3362EB1AE294C700D574A1 /* Build configuration list for PBXNativeTarget "KYPushTransitionDemoTests" */ = { 458 | isa = XCConfigurationList; 459 | buildConfigurations = ( 460 | 5F3362EC1AE294C700D574A1 /* Debug */, 461 | 5F3362ED1AE294C700D574A1 /* Release */, 462 | ); 463 | defaultConfigurationIsVisible = 0; 464 | }; 465 | /* End XCConfigurationList section */ 466 | }; 467 | rootObject = 5F3362BD1AE294C600D574A1 /* Project object */; 468 | } 469 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/project.xcworkspace/xcuserdata/KittenYang.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/KittenYang/KYPushTransition/6baaa22c78e26c958488f2686c123c94a52f7825/KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/project.xcworkspace/xcuserdata/KittenYang.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/xcuserdata/KittenYang.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/xcuserdata/KittenYang.xcuserdatad/xcschemes/KYPushTransitionDemo.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 29 | 35 | 36 | 37 | 38 | 39 | 44 | 45 | 47 | 53 | 54 | 55 | 56 | 57 | 63 | 64 | 65 | 66 | 75 | 77 | 83 | 84 | 85 | 86 | 87 | 88 | 94 | 96 | 102 | 103 | 104 | 105 | 107 | 108 | 111 | 112 | 113 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo.xcodeproj/xcuserdata/KittenYang.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | KYPushTransitionDemo.xcscheme 8 | 9 | orderHint 10 | 0 11 | 12 | 13 | SuppressBuildableAutocreation 14 | 15 | 5F3362C41AE294C600D574A1 16 | 17 | primary 18 | 19 | 20 | 5F3362DD1AE294C700D574A1 21 | 22 | primary 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow *window; 14 | 15 | 16 | @end 17 | 18 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "AppDelegate.h" 10 | 11 | @interface AppDelegate () 12 | 13 | @end 14 | 15 | @implementation AppDelegate 16 | 17 | 18 | - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { 19 | // Override point for customization after application launch. 20 | return YES; 21 | } 22 | 23 | - (void)applicationWillResignActive:(UIApplication *)application { 24 | // 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. 25 | // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game. 26 | } 27 | 28 | - (void)applicationDidEnterBackground:(UIApplication *)application { 29 | // 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. 30 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 31 | } 32 | 33 | - (void)applicationWillEnterForeground:(UIApplication *)application { 34 | // Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background. 35 | } 36 | 37 | - (void)applicationDidBecomeActive:(UIApplication *)application { 38 | // 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. 39 | } 40 | 41 | - (void)applicationWillTerminate:(UIApplication *)application { 42 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 43 | } 44 | 45 | @end 46 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Base.lproj/LaunchScreen.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 20 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/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 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/FirstViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface FirstViewController : UIViewController 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/FirstViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // FirstViewController.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "FirstViewController.h" 10 | #import "SecondViewController.h" 11 | #import "KYPushTransition.h" 12 | #import "KYPopTransition.h" 13 | #import "KYPopInteractiveTransition.h" 14 | 15 | 16 | @interface FirstViewController () 17 | 18 | //@property(nonatomic,strong)KYPushTransition *pushTransition; 19 | 20 | @end 21 | 22 | @implementation FirstViewController{ 23 | KYPopInteractiveTransition *popInteractive; 24 | } 25 | 26 | - (void)viewDidLoad { 27 | [super viewDidLoad]; 28 | self.navigationController.delegate = self; 29 | self.title = @"First"; 30 | 31 | } 32 | 33 | - (void)didReceiveMemoryWarning { 34 | [super didReceiveMemoryWarning]; 35 | // Dispose of any resources that can be recreated. 36 | } 37 | 38 | -(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{ 39 | 40 | SecondViewController *secVC = (SecondViewController *)segue.destinationViewController; 41 | secVC.transitioningDelegate = self; 42 | popInteractive = [KYPopInteractiveTransition new]; 43 | [popInteractive addPopGesture:secVC]; 44 | 45 | 46 | } 47 | 48 | //#pragma mark -- 直接两个VC之间的present和dismiss的情况下 49 | //- (id )animationControllerForPresentedController:(UIViewController *)presented presentingController:(UIViewController *)presenting sourceController:(UIViewController *)source{ 50 | // 51 | // KYPushTransition *flip = [KYPushTransition new]; 52 | // 53 | // return flip; 54 | //} 55 | // 56 | //- (id )animationControllerForDismissedController:(UIViewController *)dismissed{ 57 | // KYPopTransition *flip = [KYPopTransition new]; 58 | // return flip; 59 | // 60 | //} 61 | // 62 | // 63 | //- (id )interactionControllerForDismissal:(id )animator{ 64 | // return popInteractive.interacting ? popInteractive : nil; 65 | // 66 | //} 67 | 68 | 69 | #pragma mark -- UINavigationController 控制两个VC的情况下 70 | 71 | - (id )navigationController:(UINavigationController *)navigationController 72 | animationControllerForOperation:(UINavigationControllerOperation)operation 73 | fromViewController:(UIViewController *)fromVC 74 | toViewController:(UIViewController *)toVC{ 75 | if (operation == UINavigationControllerOperationPush) { 76 | 77 | KYPushTransition *flip = [KYPushTransition new]; 78 | return flip; 79 | 80 | }else if (operation == UINavigationControllerOperationPop){ 81 | 82 | KYPopTransition *flip = [KYPopTransition new]; 83 | return flip; 84 | 85 | }else{ 86 | return nil; 87 | } 88 | } 89 | 90 | 91 | - (id )navigationController:(UINavigationController *)navigationController 92 | interactionControllerForAnimationController:(id ) animationController{ 93 | return popInteractive.interacting ? popInteractive : nil; 94 | } 95 | 96 | 97 | @end 98 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "29x29", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "29x29", 11 | "scale" : "3x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "40x40", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "size" : "40x40", 21 | "scale" : "3x" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "size" : "60x60", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "size" : "60x60", 31 | "scale" : "3x" 32 | }, 33 | { 34 | "idiom" : "ipad", 35 | "size" : "29x29", 36 | "scale" : "1x" 37 | }, 38 | { 39 | "idiom" : "ipad", 40 | "size" : "29x29", 41 | "scale" : "2x" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "size" : "40x40", 46 | "scale" : "1x" 47 | }, 48 | { 49 | "idiom" : "ipad", 50 | "size" : "40x40", 51 | "scale" : "2x" 52 | }, 53 | { 54 | "idiom" : "ipad", 55 | "size" : "76x76", 56 | "scale" : "1x" 57 | }, 58 | { 59 | "idiom" : "ipad", 60 | "size" : "76x76", 61 | "scale" : "2x" 62 | } 63 | ], 64 | "info" : { 65 | "version" : 1, 66 | "author" : "xcode" 67 | } 68 | } -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "IMG_4087-1.JPG" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "IMG_4087.JPG" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x", 16 | "filename" : "IMG_4087-2.JPG" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087-1.JPG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/KittenYang/KYPushTransition/6baaa22c78e26c958488f2686c123c94a52f7825/KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087-1.JPG -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087-2.JPG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/KittenYang/KYPushTransition/6baaa22c78e26c958488f2686c123c94a52f7825/KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087-2.JPG -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087.JPG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/KittenYang/KYPushTransition/6baaa22c78e26c958488f2686c123c94a52f7825/KYPushTransitionDemo/KYPushTransitionDemo/Images.xcassets/Home.imageset/IMG_4087.JPG -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | com.$(PRODUCT_NAME:rfc1034identifier) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | APPL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleSignature 20 | ???? 21 | CFBundleVersion 22 | 1 23 | LSRequiresIPhoneOS 24 | 25 | UILaunchStoryboardName 26 | LaunchScreen 27 | UIMainStoryboardFile 28 | Main 29 | UIRequiredDeviceCapabilities 30 | 31 | armv7 32 | 33 | UISupportedInterfaceOrientations 34 | 35 | UIInterfaceOrientationPortrait 36 | UIInterfaceOrientationLandscapeLeft 37 | UIInterfaceOrientationLandscapeRight 38 | 39 | UISupportedInterfaceOrientations~ipad 40 | 41 | UIInterfaceOrientationPortrait 42 | UIInterfaceOrientationPortraitUpsideDown 43 | UIInterfaceOrientationLandscapeLeft 44 | UIInterfaceOrientationLandscapeRight 45 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPopInteractiveTransition.h: -------------------------------------------------------------------------------- 1 | // 2 | // KYPopInteractiveTransition.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/19/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | #import 11 | 12 | @interface KYPopInteractiveTransition : UIPercentDrivenInteractiveTransition 13 | 14 | @property(nonatomic,assign)BOOL interacting; 15 | -(void)addPopGesture:(UIViewController *)viewController; 16 | 17 | @end 18 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPopInteractiveTransition.m: -------------------------------------------------------------------------------- 1 | // 2 | // KYPopInteractiveTransition.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/19/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "KYPopInteractiveTransition.h" 10 | 11 | @implementation KYPopInteractiveTransition{ 12 | UIViewController *presentedVC; 13 | } 14 | 15 | 16 | -(void)addPopGesture:(UIViewController *)viewController{ 17 | 18 | presentedVC = viewController; 19 | UIScreenEdgePanGestureRecognizer *edgeGes = [[UIScreenEdgePanGestureRecognizer alloc]initWithTarget:self action:@selector(edgeGesPan:)]; 20 | edgeGes.edges = UIRectEdgeLeft; 21 | [viewController.view addGestureRecognizer:edgeGes]; 22 | 23 | } 24 | 25 | -(void)edgeGesPan:(UIScreenEdgePanGestureRecognizer *)edgeGes{ 26 | CGFloat translation =[edgeGes translationInView:presentedVC.view].x; 27 | CGFloat percent = translation / (presentedVC.view.bounds.size.width/2); 28 | percent = MIN(0.99, MAX(0.0, percent)); 29 | NSLog(@"%f",percent); 30 | 31 | switch (edgeGes.state) { 32 | case UIGestureRecognizerStateBegan:{ 33 | self.interacting = YES; 34 | // [presentedVC dismissViewControllerAnimated:YES completion:nil]; 35 | // 如果是navigationController控制,这里应该是 36 | [presentedVC.navigationController popViewControllerAnimated:YES]; 37 | break; 38 | } 39 | case UIGestureRecognizerStateChanged:{ 40 | 41 | [self updateInteractiveTransition:percent]; 42 | break; 43 | } 44 | 45 | case UIGestureRecognizerStateEnded:{ 46 | 47 | self.interacting = NO; 48 | if (percent > 0.5) { 49 | [self finishInteractiveTransition]; 50 | }else{ 51 | [self cancelInteractiveTransition]; 52 | } 53 | break; 54 | } 55 | 56 | default: 57 | break; 58 | } 59 | } 60 | 61 | 62 | @end 63 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPopTransition.h: -------------------------------------------------------------------------------- 1 | // 2 | // KYPopTransition.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/19/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | #import 11 | 12 | @interface KYPopTransition : NSObject 13 | 14 | @end 15 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPopTransition.m: -------------------------------------------------------------------------------- 1 | // 2 | // KYPopTransition.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/19/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "KYPopTransition.h" 10 | 11 | @interface KYPopTransition() 12 | 13 | @property (nonatomic,strong)id transitionContext; 14 | 15 | @end 16 | 17 | @implementation KYPopTransition 18 | 19 | - (NSTimeInterval)transitionDuration:(id )transitionContext{ 20 | 21 | return 0.6f; 22 | } 23 | 24 | 25 | - (void)animateTransition:(id )transitionContext{ 26 | 27 | 28 | UIViewController *fromVC = [transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey]; 29 | UIViewController *toVC = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey]; 30 | UIView *fromView = fromVC.view; 31 | UIView *toView = toVC.view; 32 | 33 | UIView *containerView = [transitionContext containerView]; 34 | [containerView addSubview:toView]; 35 | 36 | //增加透视的transform 37 | CATransform3D transform = CATransform3DIdentity; 38 | transform.m34 = -0.002; 39 | containerView.layer.sublayerTransform = transform; 40 | 41 | //给fromVC和toVC分别设置相同的起始frame 42 | CGRect initialFrame = [transitionContext initialFrameForViewController:fromVC]; 43 | fromView.frame = initialFrame; 44 | toView.frame = initialFrame; 45 | 46 | //改变View的锚点 47 | [self updateAnchorPointAndOffset:CGPointMake(0.0, 0.5) view:toView]; 48 | 49 | //让toView的截图旋转90度 50 | toView.layer.transform = CATransform3DMakeRotation(-M_PI_2, 0.0, 1.0, 0.0); 51 | 52 | 53 | [UIView animateWithDuration:[self transitionDuration:transitionContext] delay:0.0 options:UIViewAnimationOptionCurveEaseIn animations:^{ 54 | 55 | //旋转fromView 90度 56 | toView.layer.transform = CATransform3DMakeRotation(0, 0, 1.0, 0); 57 | 58 | } completion:^(BOOL finished) { 59 | 60 | toView.layer.anchorPoint = CGPointMake(0.5, 0.5); 61 | toView.layer.position = CGPointMake(CGRectGetMidX([UIScreen mainScreen].bounds), CGRectGetMidY([UIScreen mainScreen].bounds)); 62 | [transitionContext completeTransition:![transitionContext transitionWasCancelled]]; 63 | 64 | }]; 65 | 66 | } 67 | 68 | //给传入的View改变锚点 69 | -(void)updateAnchorPointAndOffset:(CGPoint)anchorPoint view:(UIView *)view{ 70 | view.layer.anchorPoint = anchorPoint; 71 | view.layer.position = CGPointMake(0, CGRectGetMidY([UIScreen mainScreen].bounds)); 72 | } 73 | 74 | 75 | 76 | 77 | @end 78 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPushTransition.h: -------------------------------------------------------------------------------- 1 | // 2 | // KYPushTransition.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | #import 11 | 12 | @interface KYPushTransition : NSObject 13 | 14 | @end 15 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/KYPushTransition.m: -------------------------------------------------------------------------------- 1 | // 2 | // KYPushTransition.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "FirstViewController.h" 10 | #import "SecondViewController.h" 11 | 12 | #import "KYPushTransition.h" 13 | 14 | @interface KYPushTransition() 15 | 16 | @property (nonatomic,strong)id transitionContext; 17 | 18 | @end 19 | 20 | @implementation KYPushTransition 21 | 22 | - (NSTimeInterval)transitionDuration:(id )transitionContext{ 23 | return 0.6f; 24 | } 25 | 26 | 27 | 28 | - (void)animateTransition:(id )transitionContext{ 29 | 30 | 31 | //把toView加到containerView上 32 | FirstViewController *fromVC = (FirstViewController *)[transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey]; 33 | SecondViewController *toVC = (SecondViewController *)[transitionContext viewControllerForKey:UITransitionContextToViewControllerKey]; 34 | UIView *fromView = fromVC.view; 35 | UIView *toView = toVC.view; 36 | 37 | UIView *containerView = [transitionContext containerView]; 38 | 39 | [containerView addSubview:toView]; 40 | [containerView sendSubviewToBack:toView]; 41 | 42 | //增加透视的transform 43 | CATransform3D transform = CATransform3DIdentity; 44 | transform.m34 = -0.002; 45 | containerView.layer.sublayerTransform = transform; 46 | 47 | //给fromVC和toVC分别设置相同的起始frame 48 | CGRect initialFrame = [transitionContext initialFrameForViewController:fromVC]; 49 | fromView.frame = initialFrame; 50 | toView.frame = initialFrame; 51 | 52 | [self updateAnchorPointAndOffset:CGPointMake(0.0, 0.5) view:fromView]; 53 | 54 | //增加阴影 55 | CAGradientLayer *gradient = [CAGradientLayer layer]; 56 | gradient.frame = fromView.bounds; 57 | gradient.colors = @[(id)[UIColor colorWithWhite:0.0 alpha:0.5].CGColor, 58 | (id)[UIColor colorWithWhite:0.0 alpha:0.0].CGColor]; 59 | gradient.startPoint = CGPointMake(0.0, 0.5); 60 | gradient.endPoint = CGPointMake(0.8, 0.5); 61 | 62 | UIView *shadow = [[UIView alloc]initWithFrame:fromView.bounds]; 63 | shadow.backgroundColor = [UIColor clearColor]; 64 | [shadow.layer insertSublayer:gradient atIndex:1]; 65 | shadow.alpha = 0.0; 66 | 67 | [fromView addSubview:shadow]; 68 | 69 | 70 | 71 | [UIView animateWithDuration:[self transitionDuration:transitionContext] delay:0.0 options:UIViewAnimationOptionCurveEaseOut animations:^{ 72 | 73 | //旋转fromView 90度 74 | fromView.layer.transform = CATransform3DMakeRotation(-M_PI_2, 0, 1.0, 0); 75 | shadow.alpha = 1.0; 76 | 77 | } completion:^(BOOL finished) { 78 | 79 | fromView.layer.anchorPoint = CGPointMake(0.5, 0.5); 80 | fromView.layer.position = CGPointMake(CGRectGetMidX([UIScreen mainScreen].bounds), CGRectGetMidY([UIScreen mainScreen].bounds)); 81 | fromView.layer.transform = CATransform3DIdentity; 82 | [shadow removeFromSuperview]; 83 | [transitionContext completeTransition:YES]; 84 | 85 | }]; 86 | 87 | } 88 | 89 | 90 | //给传入的View改变锚点 91 | -(void)updateAnchorPointAndOffset:(CGPoint)anchorPoint view:(UIView *)view{ 92 | view.layer.anchorPoint = anchorPoint; 93 | view.layer.position = CGPointMake(0, CGRectGetMidY([UIScreen mainScreen].bounds)); 94 | } 95 | 96 | @end 97 | 98 | 99 | 100 | 101 | 102 | 103 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/SecondViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // SecondViewController.h 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface SecondViewController : UIViewController 12 | @property (strong, nonatomic) IBOutlet UIButton *backButton; 13 | 14 | @end 15 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/SecondViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // SecondViewController.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import "SecondViewController.h" 10 | 11 | @interface SecondViewController () 12 | 13 | @end 14 | 15 | @implementation SecondViewController 16 | 17 | - (void)viewDidLoad { 18 | [super viewDidLoad]; 19 | self.title = @"Second"; 20 | } 21 | 22 | - (void)didReceiveMemoryWarning { 23 | [super didReceiveMemoryWarning]; 24 | // Dispose of any resources that can be recreated. 25 | } 26 | 27 | 28 | - (IBAction)dismissAction:(id)sender { 29 | [self dismissViewControllerAnimated:YES completion:nil]; 30 | 31 | } 32 | 33 | 34 | 35 | @end 36 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemo/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // KYPushTransitionDemo 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | @autoreleasepool { 14 | return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemoTests/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | com.$(PRODUCT_NAME:rfc1034identifier) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | BNDL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleSignature 20 | ???? 21 | CFBundleVersion 22 | 1 23 | 24 | 25 | -------------------------------------------------------------------------------- /KYPushTransitionDemo/KYPushTransitionDemoTests/KYPushTransitionDemoTests.m: -------------------------------------------------------------------------------- 1 | // 2 | // KYPushTransitionDemoTests.m 3 | // KYPushTransitionDemoTests 4 | // 5 | // Created by Kitten Yang on 4/18/15. 6 | // Copyright (c) 2015 Kitten Yang. All rights reserved. 7 | // 8 | 9 | #import 10 | #import 11 | 12 | @interface KYPushTransitionDemoTests : XCTestCase 13 | 14 | @end 15 | 16 | @implementation KYPushTransitionDemoTests 17 | 18 | - (void)setUp { 19 | [super setUp]; 20 | // Put setup code here. This method is called before the invocation of each test method in the class. 21 | } 22 | 23 | - (void)tearDown { 24 | // Put teardown code here. This method is called after the invocation of each test method in the class. 25 | [super tearDown]; 26 | } 27 | 28 | - (void)testExample { 29 | // This is an example of a functional test case. 30 | XCTAssert(YES, @"Pass"); 31 | } 32 | 33 | - (void)testPerformanceExample { 34 | // This is an example of a performance test case. 35 | [self measureBlock:^{ 36 | // Put the code you want to measure the time of here. 37 | }]; 38 | } 39 | 40 | @end 41 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # KYPushTransition 2 | 一个3D翻转的转场动画,可以手势百分比控制。 3 | 4 | ![](demo.gif) 5 | 6 | ###Usage 7 | 8 | 以下代码全在第一个视图控制器中实现: 9 | 10 | 进入第一个控制器。在跳转之前,设置后一个控制器的代理,比如我用Segue的话,就在`-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender`里设置后一个控制器的代理为前一个控制器,并且让后一个控制器实现手势返回的交互: 11 | 12 | ``` 13 | -(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{ 14 | 15 | SecondViewController *secVC = (SecondViewController *)segue.destinationViewController; 16 | secVC.transitioningDelegate = self; 17 | popInteractive = [KYPopInteractiveTransition new]; 18 | [popInteractive addPopGesture:secVC]; 19 | } 20 | ``` 21 | 22 | 23 | 然后分两种情况: 24 | 25 | ###1)如果只是一个VC present 到另一个 VC,那么你需要实现`UIViewControllerTransitioningDelegate`中的两个协议,分别对应`present`和`dismiss`,返回对应的动画: 26 | 27 | ``` 28 | - (id )animationControllerForPresentedController:(UIViewController *)presented presentingController:(UIViewController *)presenting sourceController:(UIViewController *)source{ 29 | 30 | KYPushTransition *flip = [KYPushTransition new]; 31 | 32 | return flip; 33 | } 34 | 35 | - (id )animationControllerForDismissedController:(UIViewController *)dismissed{ 36 | KYPopTransition *flip = [KYPopTransition new]; 37 | return flip; 38 | 39 | } 40 | ``` 41 | 42 | 然后是手势交互的方法,比较常用的情况是返回上一个VC采用手势,所以这里只实现了dismiss的方法: 43 | 44 | ``` 45 | - (id )interactionControllerForDismissal:(id )animator{ 46 | return popInteractive.interacting ? popInteractive : nil; 47 | 48 | } 49 | ``` 50 | 51 | 52 | ###2)如果你是用UINavigationController控制两个VC,那么需要实现`UINavigationControllerDelegate`中的: 53 | ``` 54 | - (id )navigationController:(UINavigationController *)navigationController 55 | animationControllerForOperation:(UINavigationControllerOperation)operation 56 | fromViewController:(UIViewController *)fromVC 57 | toViewController:(UIViewController *)toVC{ 58 | if (operation == UINavigationControllerOperationPush) { 59 | 60 | KYPushTransition *flip = [KYPushTransition new]; 61 | return flip; 62 | 63 | }else if (operation == UINavigationControllerOperationPop){ 64 | 65 | KYPopTransition *flip = [KYPopTransition new]; 66 | return flip; 67 | 68 | }else{ 69 | return nil; 70 | } 71 | } 72 | ``` 73 | 74 | UINaviagtionController控制VC的情况下,`UINavigationControllerDelegate`也有相应的手势交互的协议方法: 75 | ``` 76 | - (id )navigationController:(UINavigationController *)navigationController 77 | interactionControllerForAnimationController:(id ) animationController{ 78 | return popInteractive.interacting ? popInteractive : nil; 79 | 80 | ``` 81 | 82 | 83 | 点击[博客介绍](http://kittenyang.com/3dfliptransition/)阅读详细实现细节 84 | 85 | -------------------------------------------------------------------------------- /demo.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/KittenYang/KYPushTransition/6baaa22c78e26c958488f2686c123c94a52f7825/demo.gif --------------------------------------------------------------------------------