├── .gitignore ├── Contacts ├── Contacts.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcuserdata │ │ │ └── ShannonChen.xcuserdatad │ │ │ └── UserInterfaceState.xcuserstate │ └── xcuserdata │ │ └── ShannonChen.xcuserdatad │ │ ├── xcdebugger │ │ └── Breakpoints_v2.xcbkptlist │ │ └── xcschemes │ │ ├── Contacts.xcscheme │ │ └── xcschememanagement.plist └── Contacts │ ├── AppDelegate.h │ ├── AppDelegate.m │ ├── Assets.xcassets │ └── AppIcon.appiconset │ │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Contact.swift │ ├── ContactDetailViewController.swift │ ├── Contacts-Bridging-Header.h │ ├── ContactsViewController.h │ ├── ContactsViewController.m │ ├── ImageFactory.h │ ├── ImageFactory.m │ ├── Info.plist │ └── main.m ├── FoodTracker ├── FoodTracker.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ ├── xcshareddata │ │ │ └── IDEWorkspaceChecks.plist │ │ └── xcuserdata │ │ │ └── ShannonChen.xcuserdatad │ │ │ └── UserInterfaceState.xcuserstate │ └── xcuserdata │ │ └── ShannonChen.xcuserdatad │ │ ├── xcdebugger │ │ └── Breakpoints_v2.xcbkptlist │ │ └── xcschemes │ │ ├── FoodTracker.xcscheme │ │ └── xcschememanagement.plist ├── FoodTracker │ ├── AppDelegate.swift │ ├── Assets.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ ├── Contents.json │ │ ├── DefaultPhoto.imageset │ │ │ ├── Contents.json │ │ │ └── DefaultPhoto@2x.png │ │ ├── Rating Images │ │ │ ├── Contents.json │ │ │ ├── emptyStar.imageset │ │ │ │ ├── Contents.json │ │ │ │ └── emptyStar.png │ │ │ └── filledStar.imageset │ │ │ │ ├── Contents.json │ │ │ │ └── filledStar.png │ │ └── Sample Images │ │ │ ├── Contents.json │ │ │ ├── meal1.imageset │ │ │ ├── Contents.json │ │ │ └── meal1.png │ │ │ ├── meal2.imageset │ │ │ ├── Contents.json │ │ │ └── meal2.png │ │ │ └── meal3.imageset │ │ │ ├── Contents.json │ │ │ └── meal3.png │ ├── Base.lproj │ │ ├── LaunchScreen.storyboard │ │ └── Main.storyboard │ ├── Info.plist │ ├── Meal.swift │ ├── MealTableViewCell.swift │ ├── MealTableViewController.swift │ ├── MealViewController.swift │ └── RatingControl.swift └── FoodTrackerTests │ ├── FoodTrackerTests.swift │ └── Info.plist ├── MyFoodTracker ├── MyFoodTracker.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ └── IDEWorkspaceChecks.plist └── MyFoodTracker │ ├── AppDelegate.swift │ ├── Assets.xcassets │ └── AppIcon.appiconset │ │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Info.plist │ └── ViewController.swift ├── Playgrounds ├── BNRPlayground.playground │ ├── Contents.swift │ ├── contents.xcplayground │ ├── playground.xcworkspace │ │ └── contents.xcworkspacedata │ └── timeline.xctimeline └── TheSwiftProgrammingLanguage │ ├── GuidedTour.playground │ ├── Pages │ │ ├── Control Flow.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Enumerations and Structures.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Error Handling.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Functions and Closures.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Generics.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── License.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Objects and Classes.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Protocols and Extensions.xcplaygroundpage │ │ │ └── Contents.swift │ │ └── Simple Values.xcplaygroundpage │ │ │ └── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_10_Properties.playground │ ├── Contents.swift │ ├── contents.xcplayground │ ├── playground.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── IDEWorkspaceChecks.plist │ └── timeline.xctimeline │ ├── Swift_11_Methods.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ └── IDEWorkspaceChecks.plist │ ├── Swift_12_Subscripts.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_13_Inheritance.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_14_Initialization.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_15_Deinitialization.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_16_ARC.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_17_OptionalChaining.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_18_ErrorHandling.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_19_TypeCasting.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_1_TheBasics.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_20_NestedTypes.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_21_Extensions.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_22_Protocols.playground │ ├── Contents.swift │ ├── contents.xcplayground │ ├── playground.xcworkspace │ │ └── contents.xcworkspacedata │ └── timeline.xctimeline │ ├── Swift_23_Generics.playground │ ├── Contents.swift │ ├── contents.xcplayground │ ├── playground.xcworkspace │ │ └── contents.xcworkspacedata │ └── timeline.xctimeline │ ├── Swift_24_AccessControl.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_25_AdvancedOperators.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_2_BasicOperators.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_3_StringsAndCharacters.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_4_CollectionTypes.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_5_ControlFlow.playground │ ├── Contents.swift │ ├── contents.xcplayground │ ├── playground.xcworkspace │ │ └── contents.xcworkspacedata │ └── timeline.xctimeline │ ├── Swift_6_Functions.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ └── IDEWorkspaceChecks.plist │ ├── Swift_7_Closures.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ ├── Swift_8_Enumerations.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ │ └── contents.xcworkspacedata │ └── Swift_9_Classes and Structures.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── playground.xcworkspace │ └── contents.xcworkspacedata ├── Presentation ├── Demo │ ├── ASwiftTour.xcodeproj │ │ ├── project.pbxproj │ │ ├── project.xcworkspace │ │ │ ├── contents.xcworkspacedata │ │ │ └── xcshareddata │ │ │ │ └── IDEWorkspaceChecks.plist │ │ └── xcshareddata │ │ │ └── xcschemes │ │ │ └── Properties.xcscheme │ ├── KeyPath.swift │ ├── Methods │ │ ├── InstanceMethodsOfClasses.swift │ │ ├── InstanceMethodsOfEnumerations.swift │ │ ├── InstanceMethodsOfStructures.swift │ │ ├── Player.swift │ │ ├── TypeMethods.swift │ │ └── main.swift │ ├── Properties │ │ ├── AudioChannel.swift │ │ ├── ComputedProperties.swift │ │ ├── DataManager.swift │ │ ├── Global&LocalVariables.swift │ │ ├── KVO.swift │ │ ├── PropertyObservers.swift │ │ ├── ReadOnlyComputedProperties.swift │ │ ├── ShorthandSetter.swift │ │ ├── StoredProperties.swift │ │ ├── TypeProperties.swift │ │ └── main.swift │ ├── Protocols │ │ ├── AddingProtocolConformanceWithAnExtension.swift │ │ ├── CheckingForProtocolConformance.swift │ │ ├── ClassOnlyProtocol.swift │ │ ├── CollectionsOfProtocolTypes.swift │ │ ├── Delegation.swift │ │ ├── InitializerRequirements.swift │ │ ├── MethodDynamicDispatch.swift │ │ ├── MethodRequirements.swift │ │ ├── MutatingMethodRequirements.swift │ │ ├── OptionalProtocolRequirements.swift │ │ ├── PropertyRequirements.swift │ │ ├── ProtocolComposition.swift │ │ ├── ProtocolExtensions.swift │ │ ├── ProtocolInheritance.swift │ │ ├── ProtocolSyntax.swift │ │ ├── ProtocolsAsTypes.swift │ │ └── main.swift │ └── Runtime │ │ ├── AssociatedObjects.swift │ │ ├── Dynamic.swift │ │ ├── KVC.swift │ │ ├── MethodSwizzling.swift │ │ └── main.swift ├── LanguageInteroperability │ ├── CocoaDesignPatterns │ │ ├── AppDelegate.h │ │ ├── AppDelegate.m │ │ ├── Assets.xcassets │ │ │ ├── AppIcon.appiconset │ │ │ │ └── Contents.json │ │ │ └── Contents.json │ │ ├── Base.lproj │ │ │ ├── LaunchScreen.storyboard │ │ │ └── Main.storyboard │ │ ├── CocoaDesignPatterns-Bridging-Header.h │ │ ├── Info.plist │ │ ├── KVC.swift │ │ ├── KVO.swift │ │ ├── SceneDelegate.h │ │ ├── SceneDelegate.m │ │ ├── Singleton.swift │ │ ├── ViewController.h │ │ ├── ViewController.m │ │ └── main.m │ ├── LanguageInteroperability.xcodeproj │ │ ├── project.pbxproj │ │ ├── project.xcworkspace │ │ │ └── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── xcschemes │ │ │ └── ObjcCodeCustomization.xcscheme │ └── ObjcCodeCustomization │ │ ├── AppDelegate.h │ │ ├── AppDelegate.m │ │ ├── Assets.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ └── Contents.json │ │ ├── Base.lproj │ │ ├── LaunchScreen.storyboard │ │ └── Main.storyboard │ │ ├── Color.h │ │ ├── Color.m │ │ ├── File.swift │ │ ├── Info.plist │ │ ├── MyViewController.swift │ │ ├── ObjcCodeCustomization-Bridging-Header.h │ │ ├── SceneDelegate.h │ │ ├── SceneDelegate.m │ │ ├── ViewController.h │ │ ├── ViewController.m │ │ └── main.m ├── ObjC-Swift 混编在模块化:组件化项目中的实践 │ ├── README.md │ ├── images │ │ ├── adding_modulemap_to_import_paths.png │ │ ├── adding_umbrella_header_to_import_paths.png │ │ ├── always_embed_swift_standard_library.png │ │ ├── app_thining.png │ │ ├── build_libraries_for_distribution.png │ │ ├── copy_generated_header.png │ │ ├── debugging_variables.png │ │ ├── dyld_error.png │ │ ├── import_paths.png │ │ ├── integrate_swift_static_lib.png │ │ ├── module_stability.png │ │ ├── modulemap.png │ │ ├── objc_call_swift.png │ │ ├── optimization_level.png │ │ ├── project_structure.png │ │ ├── run_script_copy_header.png │ │ ├── runpath_search_path.png │ │ ├── static_linking_error.png │ │ ├── swift_call_swift.png │ │ ├── swift_dylib_dir.png │ │ ├── swiftinterface_file.png │ │ ├── swiftmodule_dir.png │ │ └── umbrella_header.png │ └── sample_projects │ │ ├── using_dependency_as_libs │ │ ├── MainProject.xcodeproj │ │ │ ├── project.pbxproj │ │ │ ├── project.xcworkspace │ │ │ │ └── contents.xcworkspacedata │ │ │ └── xcshareddata │ │ │ │ └── xcschemes │ │ │ │ └── MainProject.xcscheme │ │ ├── MainProject │ │ │ ├── AppDelegate.h │ │ │ ├── AppDelegate.m │ │ │ ├── Assets.xcassets │ │ │ │ ├── AppIcon.appiconset │ │ │ │ │ └── Contents.json │ │ │ │ └── Contents.json │ │ │ ├── Base.lproj │ │ │ │ ├── LaunchScreen.storyboard │ │ │ │ └── Main.storyboard │ │ │ ├── EmptyFile.swift │ │ │ ├── Info.plist │ │ │ ├── SceneDelegate.h │ │ │ ├── SceneDelegate.m │ │ │ ├── ViewController.h │ │ │ ├── ViewController.m │ │ │ └── main.m │ │ ├── Modules │ │ │ ├── ObjCLibA │ │ │ │ ├── ObjCLibA.xcodeproj │ │ │ │ │ ├── project.pbxproj │ │ │ │ │ └── project.xcworkspace │ │ │ │ │ │ └── contents.xcworkspacedata │ │ │ │ └── ObjCLibA │ │ │ │ │ ├── ObjCLibA.h │ │ │ │ │ └── ObjCLibA.m │ │ │ ├── ObjCLibB │ │ │ │ ├── ObjCLibB │ │ │ │ │ └── ObjCLibB.h │ │ │ │ ├── ObjcLibBUmbrellaHeader.h │ │ │ │ ├── libObjCLibB.a │ │ │ │ └── module.modulemap │ │ │ ├── SwiftLibA │ │ │ │ ├── SwiftLibA-Swift.h │ │ │ │ ├── SwiftLibA.xcodeproj │ │ │ │ │ ├── project.pbxproj │ │ │ │ │ └── project.xcworkspace │ │ │ │ │ │ └── contents.xcworkspacedata │ │ │ │ └── SwiftLibA │ │ │ │ │ └── SwiftLibA.swift │ │ │ └── SwiftLibB │ │ │ │ ├── SwiftLibB-Swift.h │ │ │ │ ├── SwiftLibB.swiftmodule │ │ │ │ ├── x86_64-apple-ios-simulator.swiftdoc │ │ │ │ ├── x86_64-apple-ios-simulator.swiftinterface │ │ │ │ ├── x86_64-apple-ios-simulator.swiftmodule │ │ │ │ ├── x86_64.swiftdoc │ │ │ │ ├── x86_64.swiftinterface │ │ │ │ └── x86_64.swiftmodule │ │ │ │ └── libSwiftLibB.a │ │ └── README.md │ │ └── using_dependency_as_source_code │ │ ├── MainProject.xcodeproj │ │ ├── project.pbxproj │ │ ├── project.xcworkspace │ │ │ └── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── xcschemes │ │ │ └── MainProject.xcscheme │ │ ├── MainProject │ │ ├── AppDelegate.h │ │ ├── AppDelegate.m │ │ ├── Assets.xcassets │ │ │ ├── AppIcon.appiconset │ │ │ │ └── Contents.json │ │ │ └── Contents.json │ │ ├── Base.lproj │ │ │ ├── LaunchScreen.storyboard │ │ │ └── Main.storyboard │ │ ├── EmptyFile.swift │ │ ├── Info.plist │ │ ├── SceneDelegate.h │ │ ├── SceneDelegate.m │ │ ├── ViewController.h │ │ ├── ViewController.m │ │ └── main.m │ │ ├── Modules │ │ ├── ObjCLibA │ │ │ ├── ObjCLibA.xcodeproj │ │ │ │ ├── project.pbxproj │ │ │ │ └── project.xcworkspace │ │ │ │ │ └── contents.xcworkspacedata │ │ │ └── ObjCLibA │ │ │ │ ├── ObjCLibA.h │ │ │ │ └── ObjCLibA.m │ │ ├── ObjCLibB │ │ │ ├── ObjCLibB.xcodeproj │ │ │ │ ├── project.pbxproj │ │ │ │ └── project.xcworkspace │ │ │ │ │ └── contents.xcworkspacedata │ │ │ ├── ObjCLibB │ │ │ │ ├── ObjCLibB.h │ │ │ │ └── ObjCLibB.m │ │ │ ├── ObjcLibBUmbrellaHeader.h │ │ │ └── module.modulemap │ │ ├── SwiftLibA │ │ │ ├── SwiftLibA-Swift.h │ │ │ ├── SwiftLibA.xcodeproj │ │ │ │ ├── project.pbxproj │ │ │ │ └── project.xcworkspace │ │ │ │ │ └── contents.xcworkspacedata │ │ │ └── SwiftLibA │ │ │ │ └── SwiftLibA.swift │ │ └── SwiftLibB │ │ │ ├── SwiftLibB-Swift.h │ │ │ ├── SwiftLibB.swiftmodule │ │ │ ├── x86_64-apple-ios-simulator.swiftdoc │ │ │ ├── x86_64-apple-ios-simulator.swiftinterface │ │ │ ├── x86_64-apple-ios-simulator.swiftmodule │ │ │ ├── x86_64.swiftdoc │ │ │ ├── x86_64.swiftinterface │ │ │ └── x86_64.swiftmodule │ │ │ ├── SwiftLibB.xcodeproj │ │ │ ├── project.pbxproj │ │ │ └── project.xcworkspace │ │ │ │ └── contents.xcworkspacedata │ │ │ ├── SwiftLibB │ │ │ └── SwiftLibB.swift │ │ │ └── 混编在模块化:组件化项目中的实践 │ │ │ └── sample_projects │ │ │ └── using_dependency_as_source_code │ │ │ └── Modules │ │ │ └── SwiftLibB │ │ │ └── SwiftLibB.swiftmodule │ │ │ ├── x86_64-apple-ios-simulator.swiftdoc │ │ │ ├── x86_64-apple-ios-simulator.swiftinterface │ │ │ ├── x86_64-apple-ios-simulator.swiftmodule │ │ │ ├── x86_64.swiftdoc │ │ │ ├── x86_64.swiftinterface │ │ │ └── x86_64.swiftmodule │ │ └── README.md ├── PropertyWrapper │ ├── AuditingPropertyAccess │ │ └── main.swift │ ├── ConstrainingValues │ │ └── main.swift │ ├── Intro01 │ │ └── main.swift │ ├── Intro02 │ │ └── main.swift │ ├── PropertyWrapper.xcodeproj │ │ ├── project.pbxproj │ │ ├── project.xcworkspace │ │ │ └── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── xcschemes │ │ │ └── SynthesizedEquality&ComparisonSemantics.xcscheme │ ├── README.md │ ├── SynthesizedEquality&ComparisonSemantics │ │ └── main.swift │ └── TransformingValues │ │ └── main.swift ├── Swift 中的属性和方法.md ├── SwiftProgramming.key ├── SwiftProgramming.pdf └── ValueTypes │ ├── EratosthenesSieve │ └── main.swift │ ├── Immutability │ └── main.swift │ ├── README.md │ ├── ReferenceType │ └── main.swift │ ├── ValueSemantics │ └── main.swift │ ├── ValueTypes.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata │ └── ValueTypesInPractice │ ├── AppDelegate.swift │ ├── Assets.xcassets │ ├── AppIcon.appiconset │ │ └── Contents.json │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── BezierPath.swift │ ├── Circle.swift │ ├── Diagram.swift │ ├── Drawable.swift │ ├── Info.plist │ ├── Polygon.swift │ ├── SceneDelegate.swift │ └── ViewController.swift ├── README.md ├── RangeSliderExample ├── README.md ├── RangeSliderExample.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata └── RangeSliderExample │ ├── AppDelegate.swift │ ├── Assets.xcassets │ └── AppIcon.appiconset │ │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Info.plist │ ├── RangeSlider.swift │ ├── RangeSliderThumbLayer.swift │ ├── RangeSliderTrackLayer.swift │ └── ViewController.swift ├── SwiftUI ├── Landmarks │ ├── Landmarks.xcodeproj │ │ ├── project.pbxproj │ │ └── project.xcworkspace │ │ │ ├── contents.xcworkspacedata │ │ │ └── xcshareddata │ │ │ └── IDEWorkspaceChecks.plist │ └── Landmarks │ │ ├── AppDelegate.swift │ │ ├── Assets.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ ├── Contents.json │ │ └── turtlerock.imageset │ │ │ ├── Contents.json │ │ │ └── turtlerock.jpg │ │ ├── Base.lproj │ │ └── LaunchScreen.storyboard │ │ ├── CircleImage.swift │ │ ├── Info.plist │ │ ├── LandmarkDetail.swift │ │ ├── LandmarkList.swift │ │ ├── LandmarkRow.swift │ │ ├── MapView.swift │ │ ├── Models │ │ ├── Data.swift │ │ └── Landmark.swift │ │ ├── Preview Content │ │ └── Preview Assets.xcassets │ │ │ └── Contents.json │ │ ├── Resources │ │ ├── chilkoottrail.jpg │ │ ├── chincoteague.jpg │ │ ├── hiddenlake.jpg │ │ ├── icybay.jpg │ │ ├── lakemcdonald.jpg │ │ ├── landmarkData.json │ │ ├── rainbowlake.jpg │ │ ├── silversalmoncreek.jpg │ │ ├── stmarylake.jpg │ │ ├── turtlerock.jpg │ │ ├── twinlake.jpg │ │ ├── umbagog.jpg │ │ └── yukon_charleyrivers.jpg │ │ └── SceneDelegate.swift └── README.md ├── TheSwiftProgrammingLanguage(Swift3.1).epub ├── VocalTextEdit ├── VocalTextEdit.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcuserdata │ │ │ └── ShannonChen.xcuserdatad │ │ │ └── UserInterfaceState.xcuserstate │ └── xcuserdata │ │ └── ShannonChen.xcuserdatad │ │ └── xcschemes │ │ ├── VocalTextEdit.xcscheme │ │ └── xcschememanagement.plist └── VocalTextEdit │ ├── AppDelegate.swift │ ├── Assets.xcassets │ ├── AppIcon.appiconset │ │ └── Contents.json │ └── Contents.json │ ├── Base.lproj │ └── Main.storyboard │ ├── Document.swift │ ├── Info.plist │ └── ViewController.swift ├── WorldTrotter ├── WorldTrotter.xcodeproj │ ├── project.pbxproj │ └── project.xcworkspace │ │ └── contents.xcworkspacedata └── WorldTrotter │ ├── AppDelegate.swift │ ├── Assets.xcassets │ └── AppIcon.appiconset │ │ └── Contents.json │ ├── Base.lproj │ ├── LaunchScreen.storyboard │ └── Main.storyboard │ ├── Info.plist │ └── ViewController.swift └── iTahDoodle ├── iTahDoodle.xcodeproj ├── project.pbxproj ├── project.xcworkspace │ ├── contents.xcworkspacedata │ └── xcuserdata │ │ └── ShannonChen.xcuserdatad │ │ └── UserInterfaceState.xcuserstate └── xcuserdata │ └── ShannonChen.xcuserdatad │ ├── xcdebugger │ └── Breakpoints_v2.xcbkptlist │ └── xcschemes │ ├── iTahDoodle.xcscheme │ └── xcschememanagement.plist └── iTahDoodle ├── AppDelegate.swift ├── Assets.xcassets └── AppIcon.appiconset │ └── Contents.json ├── Base.lproj ├── LaunchScreen.storyboard └── Main.storyboard ├── Info.plist ├── TodoList.swift └── ViewController.swift /.gitignore: -------------------------------------------------------------------------------- 1 | # Xcode 2 | .DS_Store 3 | */build/* 4 | *.pbxuser 5 | !default.pbxuser 6 | *.mode1v3 7 | !default.mode1v3 8 | *.mode2v3 9 | !default.mode2v3 10 | *.perspectivev3 11 | !default.perspectivev3 12 | xcuserdata 13 | profile 14 | *.moved-aside 15 | DerivedData 16 | .idea/ 17 | *.hmap 18 | *.xccheckout 19 | 20 | #CocoaPods 21 | Pods 22 | Podfile.lock 23 | -------------------------------------------------------------------------------- /Contacts/Contacts.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Contacts/Contacts.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Contacts/Contacts.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /Contacts/Contacts.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 8 | 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /Contacts/Contacts.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | Contacts.xcscheme 8 | 9 | orderHint 10 | 0 11 | 12 | 13 | SuppressBuildableAutocreation 14 | 15 | 58F9459D1E3B9C6400D31A70 16 | 17 | primary 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /Contacts/Contacts/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. 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 | -------------------------------------------------------------------------------- /Contacts/Contacts/Assets.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 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /Contacts/Contacts/Contact.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Contact.swift 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | class Contact: NSObject { 12 | // MARK: Properties 13 | let firstName: String? 14 | let lastName: String? 15 | let fullName: String 16 | 17 | 18 | 19 | init?(firstName: String, lastName: String) { 20 | self.firstName = firstName 21 | self.lastName = lastName 22 | self.fullName = "\(firstName) \(lastName)" 23 | if fullName.isEmpty { 24 | return nil 25 | } 26 | super.init() 27 | } 28 | 29 | } 30 | -------------------------------------------------------------------------------- /Contacts/Contacts/ContactDetailViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ContactDetailViewController.swift 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/28. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ContactDetailViewController: UIViewController { 12 | 13 | // MARK: Properties 14 | @IBOutlet weak var firstNameTextField: UITextField! 15 | @IBOutlet weak var lastNameTextField: UITextField! 16 | @IBOutlet weak var imageView: UIImageView! 17 | 18 | 19 | override func viewDidLoad() { 20 | 21 | imageView.image = ImageFactory.generateDefaultImage(of: imageView.frame.size) 22 | } 23 | 24 | // MARK: Navigation 25 | @IBAction func saveAction(_ sender: UIBarButtonItem) { 26 | 27 | } 28 | 29 | 30 | @IBAction func cancelAction(_ sender: UIBarButtonItem) { 31 | 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /Contacts/Contacts/Contacts-Bridging-Header.h: -------------------------------------------------------------------------------- 1 | // 2 | // Use this file to import your target's public headers that you would like to expose to Swift. 3 | // 4 | 5 | 6 | 7 | #import "ImageFactory.h" 8 | -------------------------------------------------------------------------------- /Contacts/Contacts/ContactsViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ContactsViewController.h 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ContactsViewController : UITableViewController 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Contacts/Contacts/ImageFactory.h: -------------------------------------------------------------------------------- 1 | // 2 | // ImageFactory.h 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/28. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ImageFactory : NSObject 12 | 13 | + (UIImage *)generateDefaultImageOfSize:(CGSize)size; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Contacts/Contacts/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 | 38 | 39 | -------------------------------------------------------------------------------- /Contacts/Contacts/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // Contacts 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. 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 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /FoodTracker/FoodTracker.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | FoodTracker.xcscheme 8 | 9 | orderHint 10 | 0 11 | 12 | 13 | SuppressBuildableAutocreation 14 | 15 | 58F945481E39088000D31A70 16 | 17 | primary 18 | 19 | 20 | 58F9455C1E39088000D31A70 21 | 22 | primary 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/DefaultPhoto.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "DefaultPhoto@2x.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/DefaultPhoto.imageset/DefaultPhoto@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/DefaultPhoto.imageset/DefaultPhoto@2x.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Rating Images/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Rating Images/emptyStar.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "emptyStar.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Rating Images/emptyStar.imageset/emptyStar.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/Rating Images/emptyStar.imageset/emptyStar.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Rating Images/filledStar.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "filledStar.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Rating Images/filledStar.imageset/filledStar.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/Rating Images/filledStar.imageset/filledStar.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal1.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "meal1.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal1.imageset/meal1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal1.imageset/meal1.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal2.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "meal2.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal2.imageset/meal2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal2.imageset/meal2.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal3.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x" 6 | }, 7 | { 8 | "idiom" : "universal", 9 | "filename" : "meal3.png", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal3.imageset/meal3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/FoodTracker/FoodTracker/Assets.xcassets/Sample Images/meal3.imageset/meal3.png -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/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 | NSPhotoLibraryUsageDescription 45 | NSPhotoLibraryUsageDescription 46 | 47 | 48 | -------------------------------------------------------------------------------- /FoodTracker/FoodTracker/MealTableViewCell.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MealTableViewCell.swift 3 | // FoodTracker 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class MealTableViewCell: UITableViewCell { 12 | 13 | // MARK: Properties 14 | @IBOutlet weak var nameLabel: UILabel! 15 | @IBOutlet weak var photoImageView: UIImageView! 16 | @IBOutlet weak var ratingControl: RatingControl! 17 | 18 | 19 | } 20 | -------------------------------------------------------------------------------- /FoodTracker/FoodTrackerTests/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 | BNDL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | 22 | 23 | -------------------------------------------------------------------------------- /MyFoodTracker/MyFoodTracker.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /MyFoodTracker/MyFoodTracker.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /MyFoodTracker/MyFoodTracker/Assets.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 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /MyFoodTracker/MyFoodTracker/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 | 38 | 39 | -------------------------------------------------------------------------------- /MyFoodTracker/MyFoodTracker/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // MyFoodTracker 4 | // 5 | // Created by ShannonChen on 2017/4/25. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController { 12 | 13 | override func viewDidLoad() { 14 | super.viewDidLoad() 15 | 16 | } 17 | 18 | 19 | 20 | } 21 | 22 | -------------------------------------------------------------------------------- /Playgrounds/BNRPlayground.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/BNRPlayground.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/BNRPlayground.playground/timeline.xctimeline: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/GuidedTour.playground/Pages/Generics.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | //: ## Generics 2 | //: 3 | //: Write a name inside angle brackets to make a generic function or type. 4 | //: 5 | func makeArray(repeating item: Item, numberOfTimes: Int) -> [Item] { 6 | var result = [Item]() 7 | for _ in 0.. { 18 | case none 19 | case some(Wrapped) 20 | } 21 | var possibleInteger: OptionalValue = .none 22 | possibleInteger = .some(100) 23 | 24 | //: Use `where` right before the body to specify a list of requirements—for example, to require the type to implement a protocol, to require two types to be the same, or to require a class to have a particular superclass. 25 | //: 26 | func anyCommonElements(_ lhs: T, _ rhs: U) -> Bool 27 | where T.Iterator.Element: Equatable, T.Iterator.Element == U.Iterator.Element { 28 | for lhsItem in lhs { 29 | for rhsItem in rhs { 30 | if lhsItem == rhsItem { 31 | return true 32 | } 33 | } 34 | } 35 | return false 36 | } 37 | anyCommonElements([1, 2, 3], [3]) 38 | 39 | //: - Experiment: 40 | //: Modify the `anyCommonElements(_:_:)` function to make a function that returns an array of the elements that any two sequences have in common. 41 | //: 42 | //: Writing `` is the same as writing ` ... where T: Equatable>`. 43 | //: 44 | 45 | 46 | //: [Previous](@previous) -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/GuidedTour.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/GuidedTour.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_10_Properties.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_10_Properties.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_10_Properties.playground/playground.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_10_Properties.playground/timeline.xctimeline: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_11_Methods.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_11_Methods.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_11_Methods.playground/playground.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_12_Subscripts.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_12_Subscripts.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_13_Inheritance.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_13_Inheritance.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_14_Initialization.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_14_Initialization.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_15_Deinitialization.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_15_Deinitialization.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_16_ARC.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_16_ARC.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_17_OptionalChaining.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_17_OptionalChaining.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_18_ErrorHandling.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_18_ErrorHandling.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_19_TypeCasting.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_19_TypeCasting.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_1_TheBasics.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_1_TheBasics.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_20_NestedTypes.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_20_NestedTypes.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_21_Extensions.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_21_Extensions.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_22_Protocols.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_22_Protocols.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_23_Generics.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_23_Generics.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_23_Generics.playground/timeline.xctimeline: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_24_AccessControl.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_24_AccessControl.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_25_AdvancedOperators.playground/Contents.swift: -------------------------------------------------------------------------------- 1 | //: Playground - noun: a place where people can play 2 | 3 | import UIKit 4 | 5 | ////////////////////////////// Advanced Operators ////////////////////////////// 6 | 7 | 8 | // ======================== Bitwise Operators ===================== 9 | 10 | 11 | // ======================== Overflow Operators ===================== 12 | 13 | // =================== Precedence and Associativity ==================== 14 | 15 | 16 | // =================== Operator Methods ==================== 17 | 18 | 19 | // ========================= Custom Operators ============================ 20 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_25_AdvancedOperators.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_25_AdvancedOperators.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_2_BasicOperators.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_2_BasicOperators.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_3_StringsAndCharacters.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_3_StringsAndCharacters.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_4_CollectionTypes.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_4_CollectionTypes.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_5_ControlFlow.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_5_ControlFlow.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_5_ControlFlow.playground/timeline.xctimeline: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_6_Functions.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_6_Functions.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_6_Functions.playground/playground.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_7_Closures.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_7_Closures.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_8_Enumerations.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_8_Enumerations.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_9_Classes and Structures.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Playgrounds/TheSwiftProgrammingLanguage/Swift_9_Classes and Structures.playground/playground.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/Demo/ASwiftTour.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/Demo/ASwiftTour.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Presentation/Demo/KeyPath.swift: -------------------------------------------------------------------------------- 1 | // 2 | // KeyPath.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | struct Address { 13 | var street: String 14 | var city: String 15 | var zipCode: Int 16 | } 17 | 18 | struct Customer { 19 | let name: String 20 | var address: Address 21 | } 22 | 23 | func runKeyPathExample() { 24 | let streetKeyPath = \Customer.address.street // WritableKeyPath 25 | let nameKeyPath = \Customer.name // KeyPath 26 | 27 | let simpsonResidence = Address(street: "1094 Evergreen Terrace", city: "Springfield", zipCode: 97475) 28 | var lisa = Customer(name: "Lisa Simpson", address: simpsonResidence) 29 | let lisaNameKeyPath = lisa[keyPath: nameKeyPath] // Lisa Simpson 30 | // lisaNameKeyPath = "Zak" // this will report an error 31 | lisa[keyPath: streetKeyPath] = "742 Evergreen Terrace" 32 | } 33 | 34 | 35 | -------------------------------------------------------------------------------- /Presentation/Demo/Methods/InstanceMethodsOfClasses.swift: -------------------------------------------------------------------------------- 1 | // 2 | // InstanceMethodsOfClasses.swift 3 | // Methods 4 | // 5 | // Created by ShannonChen on 2019/7/10. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | 13 | class Counter { 14 | 15 | var count = 0 16 | 17 | func incremnt() { 18 | count += 1 19 | } 20 | 21 | func incremnt(by amount: Int) { 22 | count += amount 23 | } 24 | 25 | func reset() { 26 | count = 0 27 | } 28 | 29 | } 30 | 31 | 32 | func createACounter() { 33 | let counter = Counter() 34 | counter.incremnt() 35 | counter.incremnt(by: 5) 36 | counter.reset() 37 | 38 | 39 | } 40 | 41 | 42 | -------------------------------------------------------------------------------- /Presentation/Demo/Methods/InstanceMethodsOfEnumerations.swift: -------------------------------------------------------------------------------- 1 | // 2 | // InstanceMethodsOfEnumerations.swift 3 | // Methods 4 | // 5 | // Created by ShannonChen on 2019/7/10. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | // Mutating methods for enumerations can set the implicit self parameter to be a different case from the same enumeration 13 | 14 | enum TriStateSwitch { 15 | case off, low, high 16 | 17 | mutating func next() { 18 | switch self { 19 | case .off: 20 | self = .low 21 | case .low: 22 | self = .high 23 | case .high: 24 | self = .off 25 | 26 | } 27 | } 28 | } 29 | 30 | func createASwich() { 31 | 32 | var ovenLight = TriStateSwitch.low 33 | ovenLight.next() 34 | ovenLight.next() 35 | 36 | } 37 | -------------------------------------------------------------------------------- /Presentation/Demo/Methods/TypeMethods.swift: -------------------------------------------------------------------------------- 1 | // 2 | // TypeMethods.swift 3 | // Methods 4 | // 5 | // Created by ShannonChen on 2019/7/10. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | // You indicate type methods by writing the `static` keyword before the method’s func keyword. Classes may also use the `class` keyword to allow subclasses to override the superclass’s implementation of that method. 13 | class SomeClass { 14 | static func someTypeMethod() { 15 | print("someTypeMethod got called.\n") 16 | } 17 | 18 | class func overrideableTypeMethod() { 19 | print("overrideableTypeMethod got called.\n") 20 | } 21 | 22 | } 23 | 24 | 25 | class Subclass: SomeClass { 26 | override class func overrideableTypeMethod() { 27 | print("overrideableTypeMethod got called in subclass.\n") 28 | } 29 | } 30 | 31 | func callTypeMethods() { 32 | SomeClass.someTypeMethod() 33 | SomeClass.overrideableTypeMethod() 34 | Subclass.overrideableTypeMethod() 35 | } 36 | 37 | -------------------------------------------------------------------------------- /Presentation/Demo/Methods/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Methods 4 | // 5 | // Created by ShannonChen on 2019/7/10. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /* 12 | 13 | Classes, structures, and enumerations can all define instance methods, which encapsulate specific tasks and functionality for working with an instance of a given type. 14 | 15 | */ 16 | 17 | 18 | createACounter() 19 | 20 | //createSomePoints() 21 | // 22 | //createASwich() 23 | // 24 | //callTypeMethods() 25 | // 26 | //createAPlayer() 27 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/DataManager.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // ASwiftTour 4 | // 5 | // Created by ShannonChen on 2019/7/8. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | // Lazy stored properties 13 | class DataImporter { 14 | /* 15 | DataImporter is a class to import data from an external file. 16 | The class is assumed to take a non-trivial amount of time to initialize. 17 | 18 | */ 19 | var filename = "data.txt" 20 | // the DataImporter class would provide data importing functionality here 21 | 22 | } 23 | 24 | 25 | class DataManager { 26 | lazy var imporer: Int? = foo() 27 | /* 28 | A lazy stored property is a property whose initial value is not calculated until the first time it is used. 29 | 30 | note: You must always declare a lazy property as a variable. Constant properties must always have a value before initialization completes, and therefore cannot be declared as lazy. 31 | */ 32 | 33 | var data = [String]() 34 | // the DataManager class would provide data management functionality here 35 | 36 | func foo() -> Int { 37 | return 4 38 | } 39 | 40 | } 41 | 42 | 43 | func runDataManager() { 44 | let manager = DataManager() 45 | manager.data.append("Some data") 46 | manager.data.append("Some more data") 47 | // the DataImporter instance for the importer property has not yet been created 48 | print(manager.imporer) 49 | manager.imporer = nil 50 | print(manager.imporer) 51 | // print("file \(manager.imporer.filename) has been imported\n") 52 | } 53 | 54 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/Global&LocalVariables.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Global&LocalVariables.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/10. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /* 12 | 13 | you can also define computed variables and define observers for stored variables, in either a global or local scope. 14 | */ 15 | 16 | 17 | func testVariables() { 18 | 19 | // var aNum: Int = 8 20 | // var computedVar: Int { 21 | // return aNum * 2 22 | // } 23 | // print(computedVar) 24 | // aNum = 10 25 | // print(computedVar) 26 | // 27 | // 28 | // var observedVar: Double = 1 { 29 | // willSet { 30 | // print(newValue) 31 | // } 32 | // } 33 | // observedVar = 8 34 | // print(observedVar) 35 | 36 | 37 | // 下面的 didSet 会被调用吗? 38 | var point = Point(x: 10, y: 10) { 39 | didSet { 40 | print("Point changed: \(point)") 41 | } 42 | } 43 | 44 | point.x = 20 45 | /* 46 | 理解值类型的关键就是理解为什么这里会被调用。对结构体进行改变,在语义上来说,与重新 为它进行赋值是相同的。即使在一个更大的结构体上只有某一个属性被改变了,也等同于整个 结构体被用一个新的值进行了替代。在一个嵌套的结构体的最深层的某个改变,将会一路向上 反映到最外层的实例上,并且一路上触发所有它遇到的 willSet 和 didSet。 47 | */ 48 | 49 | 50 | var person = Person(age: 20, sex: .female) { 51 | didSet { 52 | print("Person changed: \(person.age), \(person.sex)") 53 | } 54 | } 55 | person.age = 21 56 | // person = Person(age: 21, sex: .male) 57 | } 58 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/KVO.swift: -------------------------------------------------------------------------------- 1 | // 2 | // KVO.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | /* 13 | Note: You can only use key-value observing with classes that 14 | inherit from `NSObject`. 15 | */ 16 | 17 | class MyObjectToObserve: NSObject { 18 | 19 | @objc dynamic var myDate = NSDate(timeIntervalSince1970: 0) // 1970 20 | 21 | func updateDate() { 22 | myDate = myDate.addingTimeInterval(Double(2 << 30)) // Adds about 68 years. 23 | } 24 | } 25 | 26 | class MyObserver: NSObject { 27 | 28 | @objc var objectToObserve: MyObjectToObserve 29 | var observation: NSKeyValueObservation? 30 | 31 | init(object: MyObjectToObserve) { 32 | objectToObserve = object 33 | super.init() 34 | 35 | observation = observe( 36 | \.objectToObserve.myDate, 37 | options: [.old, .new] 38 | ) { object, change in 39 | print("myDate changed from: \(change.oldValue!), updated to: \(change.newValue!)") 40 | } 41 | } 42 | } 43 | 44 | 45 | func runObserver() { 46 | let observed = MyObjectToObserve() 47 | let observer = MyObserver(object: observed) 48 | 49 | observed.updateDate() // Triggers the observer's change handler. 50 | // Prints "myDate changed from: 1970-01-01 00:00:00 +0000, updated to: 2038-01-19 03:14:08 +0000" 51 | } 52 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/ReadOnlyComputedProperties.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ReadOnlyComputedProperties.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/9. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | struct Cuboid { 13 | var width = 0.0, height = 0.0, depth = 0.0 14 | 15 | var volume: Double { 16 | return width * height * depth 17 | } 18 | /* 19 | A computed property with a getter but no setter is known as a read-only computed property. 20 | */ 21 | 22 | } 23 | 24 | func createACuoid() { 25 | let fourByFiveByTwo = Cuboid.init(width: 4.0, height: 5.0, depth: 2.0) 26 | print("The volume of fourByFiveByTwo is \(fourByFiveByTwo.volume)") 27 | 28 | } 29 | 30 | 31 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/ShorthandSetter.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ShorthandSetter.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/9. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | // Shorthand setter declaration 12 | struct AlternativeRect { 13 | var origin = Point() 14 | var size = Size() 15 | var center: Point { 16 | get { 17 | let centerX = origin.x + (size.width / 2) 18 | let centerY = origin.y + (size.height / 2) 19 | return Point(x: centerX, y: centerY) 20 | } 21 | /* 22 | get { 23 | Point(x: origin.x + (size.width / 2), 24 | y: origin.y + (size.height / 2)) 25 | 26 | } 27 | 28 | (Swift 5.1+)If the entire body of a getter is a single expression, the getter implicitly returns that expression. 29 | */ 30 | 31 | set { 32 | // If a computed property’s setter does not define a name for the new value to be set, a default name of `newValue` is used. 33 | origin.x = newValue.x - (size.width / 2) 34 | origin.y = newValue.y - (size.height / 2) 35 | } 36 | } 37 | 38 | } 39 | 40 | 41 | -------------------------------------------------------------------------------- /Presentation/Demo/Properties/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Properties 4 | // 5 | // Created by ShannonChen on 2019/7/8. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /* 12 | 13 | Properties associate values with a particular class, structure, or enumeration. 14 | 15 | Computed properties are provided by classes, structures, and enumerations. 16 | Stored properties are provided only by classes and structures. 17 | 18 | */ 19 | 20 | //createASturcture() 21 | 22 | //runDataManager() 23 | // 24 | //createASquare() 25 | // 26 | //createACuoid() 27 | // 28 | //createStepCounter() 29 | // 30 | //testVariables() 31 | // 32 | //printTypeProperties() 33 | // 34 | //createAnAudioChannel() 35 | // 36 | //runKeyPathExample() 37 | // 38 | runObserver() 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/CheckingForProtocolConformance.swift: -------------------------------------------------------------------------------- 1 | // 2 | // CheckingForProtocolConformance.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | protocol HasArea { 13 | var area: Double { get } 14 | } 15 | 16 | class Circle: HasArea { 17 | let pi = 3.1415927 18 | var radius: Double 19 | var area: Double { 20 | return pi * radius * radius 21 | } 22 | 23 | init(radius: Double) { 24 | self.radius = radius 25 | } 26 | } 27 | 28 | class Country: HasArea { 29 | var area: Double 30 | init(area: Double) { 31 | self.area = area 32 | } 33 | } 34 | 35 | class Animal { 36 | var legs: Int 37 | 38 | init(legs: Int) { 39 | self.legs = legs 40 | } 41 | } 42 | 43 | func runExample13() { 44 | let objects: [AnyObject] = [ 45 | Circle.init(radius: 2.0), 46 | Country.init(area: 243_610), 47 | Animal.init(legs: 4) 48 | ] 49 | 50 | 51 | for object in objects { 52 | 53 | if object is HasArea { 54 | print("Area conforms to protocol HasArea") 55 | } 56 | 57 | if let objectWithArea = object as? HasArea { 58 | print("Area is \(objectWithArea.area)") 59 | } else { 60 | print("Something that doesn't have an area") 61 | } 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/ClassOnlyProtocol.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ClassOnlyProtocol.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | // `someClassOnlyProtocol` can only be adopted by class types 13 | protocol SomeClassOnlyProtocol: AnyObject, FirstProtocol { 14 | 15 | } 16 | 17 | 18 | class ClassType: SomeClassOnlyProtocol { 19 | 20 | } 21 | 22 | 23 | // error: Non-class type 'StructType' cannot conform to class protocol 'SomeClassOnlyProtocol' 24 | //struct StructType: SomeClassOnlyProtocol { 25 | // 26 | //} 27 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/CollectionsOfProtocolTypes.swift: -------------------------------------------------------------------------------- 1 | // 2 | // CollectionsOfProtocolTypes.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | func runExample09() { 13 | let game = SnakesAndLadders() 14 | let d12 = Dice.init(sides: 12, generator: LinearCongruentialGenerator()) 15 | let simonTheHamster = Hamster.init(name: "Simon") 16 | 17 | let things: [TextRepresentable] = [game, d12, simonTheHamster] 18 | 19 | // Note that the `thing` constant is of type `TextRepresentable`. 20 | for thing in things { 21 | print(thing.textualDescription) 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/InitializerRequirements.swift: -------------------------------------------------------------------------------- 1 | // 2 | // InitializerRequirements.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | class AnotherClass: SomeSuperClass, SomeProtocol { 13 | var mustBeSettable: Int = 1 14 | var doesNotNeedToBeSettable: Int = 1 15 | static var someTypeProperty: Int = 1 16 | 17 | func someMethod() { 18 | 19 | } 20 | static func someTypeMethod() { 21 | 22 | } 23 | 24 | // You can implement a protocol initializer requirement on a conforming class as either a designated initializer or a convenience initializer. In both cases, you must mark the initializer implementation with the required modifier 25 | required init(someParameter: Int) { 26 | 27 | 28 | } 29 | 30 | // "required" from SomeProtocol conformance; "override" from SomeSuperClass 31 | override required init() { 32 | 33 | } 34 | } 35 | 36 | 37 | //---------------------- Required Initializer --------------------------- 38 | 39 | class A { 40 | required init() { 41 | 42 | } 43 | } 44 | 45 | class B: A { 46 | // // 'required' modifier must be present on all overrides of a required initializer 47 | // init() { 48 | // 49 | // } 50 | } 51 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/MethodDynamicDispatch.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MethodDynamicDispatch.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/9/1. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | // https://mikeash.com/pyblog/friday-qa-2015-06-19-the-best-of-whats-new-in-swift.html 10 | 11 | import Foundation 12 | 13 | 14 | 15 | 16 | protocol P { 17 | func a() 18 | } 19 | 20 | extension P { 21 | // func a() { 22 | // 23 | // } 24 | } 25 | 26 | protocol P2 { 27 | func a() 28 | } 29 | 30 | extension P2 { 31 | func a() { 32 | 33 | } 34 | } 35 | 36 | //extension P { 37 | // func a() { 38 | // print("协议 P 的扩展,方法 A") 39 | // } 40 | // 41 | // // 如果只在 Protocol extension 中定义了这个方法,但是没有在 Protocol 42 | // // 中声明的话,那么实体类型在重写这个方法时就会变成静态派发而不是动态派发了 43 | // // http://lijun.xyz/2017/02/12/Protocol-Extension/ 44 | // func b() { 45 | // print("协议 P 的扩展,方法 B") 46 | // } 47 | //} 48 | 49 | class S: P, P2 { 50 | // func a() { 51 | // 52 | // // 调用super?? 53 | // print("结构体 S 中的 A 方法实现") 54 | // } 55 | 56 | func b() { 57 | print("结构体 S 中的 B 方法实现") 58 | } 59 | } 60 | 61 | 62 | func runExample18() { 63 | // let p: P = S() 64 | let p = S() 65 | p.a() 66 | p.b() 67 | } 68 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/MethodRequirements.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MethodRequirements.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | protocol RandomNumberGenerator { 12 | func random() -> Double 13 | } 14 | 15 | class LinearCongruentialGenerator: RandomNumberGenerator { 16 | var lastRandom = 42.0 17 | let m = 139968.0 18 | let a = 3877.0 19 | let c = 29573.0 20 | 21 | func random() -> Double { 22 | lastRandom = ((lastRandom * a) + c).truncatingRemainder(dividingBy: m) 23 | 24 | return lastRandom / m 25 | } 26 | } 27 | 28 | 29 | func runExample02() { 30 | let generator = LinearCongruentialGenerator() 31 | print("Here's a random number: \(generator.random())") 32 | 33 | print("And another one: \(generator.random())") 34 | 35 | } 36 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/MutatingMethodRequirements.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MutatingMethodRequirements.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | protocol Togglable { 13 | 14 | // The mutating keyword is only used by structures and enumerations. 15 | mutating func toggle() 16 | } 17 | 18 | enum OnOffSwitch: Togglable { 19 | case off, on 20 | 21 | mutating func toggle() { 22 | switch self { 23 | case .off: 24 | self = .on 25 | case .on: 26 | self = .off 27 | } 28 | } 29 | } 30 | 31 | 32 | func runExample03() { 33 | var lightSwitch = OnOffSwitch.off 34 | lightSwitch.toggle() 35 | } 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/PropertyRequirements.swift: -------------------------------------------------------------------------------- 1 | // 2 | // PropertyRequirements.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | protocol FullyNamed { 13 | var fullName: String { 14 | get 15 | } 16 | } 17 | 18 | struct Person: FullyNamed { 19 | var fullName: String 20 | 21 | } 22 | 23 | class Starship: FullyNamed { 24 | var prefix: String? 25 | var name: String 26 | 27 | init(name: String, prefix: String? = nil) { 28 | self.name = name 29 | self.prefix = prefix 30 | } 31 | 32 | var fullName: String { 33 | return (prefix != nil ? prefix! + " " : "") + name 34 | } 35 | } 36 | 37 | 38 | func runExample01() { 39 | 40 | let john = Person.init(fullName: "John Appleseed") 41 | print(john.fullName) 42 | 43 | var ncc1701 = Starship.init(name: "Enterprise", prefix: "USS") 44 | print(ncc1701.fullName) 45 | } 46 | 47 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/ProtocolExtensions.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ProtocolExtensions.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | extension RandomNumberGenerator { 13 | func randomBool() -> Bool { 14 | return random() > 0.5 15 | } 16 | } 17 | 18 | 19 | func runExample16() { 20 | let generator = LinearCongruentialGenerator() 21 | print("Here's a random number: \(generator.random())") 22 | print("And here's a random Boolean: \(generator.randomBool())") 23 | } 24 | 25 | //------------------- Providing default implementations ------------------- 26 | 27 | extension PrettyTextRepresentable { 28 | // var palaceholder = "xxx" // !! Extensions must not contain stored properties 29 | var prettyTextualDescription: String { 30 | return textualDescription 31 | } 32 | 33 | } 34 | 35 | //------------ Adding constraints to protocol extensions ----------------- 36 | extension Collection where Element: Equatable { 37 | func allEqual() -> Bool { 38 | for element in self { 39 | if element != self.first { 40 | return false 41 | } 42 | } 43 | return true 44 | } 45 | } 46 | 47 | 48 | func runExample17() { 49 | let equalNumbers = [100, 100, 100, 100, 100] 50 | let differentNumbers = [100, 100, 200, 100, 200] 51 | let generators = [LinearCongruentialGenerator(), LinearCongruentialGenerator()] 52 | 53 | print(equalNumbers.allEqual()) 54 | print(differentNumbers.allEqual()) 55 | // print(generators.allEqual()) 56 | } 57 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/ProtocolInheritance.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ProtocolInheritance.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | protocol InheritingProtocol: SomeProtocol, AnotherProtocol { 13 | // protocol definition goes here 14 | } 15 | 16 | 17 | // “ Anything that adopts PrettyTextRepresentable must satisfy all of the requirements enforced by TextRepresentable, plus the additional requirements enforced by PrettyTextRepresentable” 18 | protocol PrettyTextRepresentable: TextRepresentable { 19 | var prettyTextualDescription: String { get } 20 | 21 | } 22 | 23 | // The SnakesAndLadders class can be extended to adopt and conform to PrettyTextRepresentable 24 | extension SnakesAndLadders: PrettyTextRepresentable { 25 | var prettyTextualDescription: String { 26 | var output = textualDescription + ":\n" 27 | 28 | for index in 1...finalSquare { 29 | 30 | switch board[index] { 31 | 32 | case let ladder where ladder > 0: 33 | output += "▲ " 34 | case let snake where snake < 0: 35 | output += "▼ " 36 | default: 37 | output += "○ " 38 | } 39 | } 40 | 41 | return output 42 | } 43 | 44 | } 45 | 46 | 47 | func runExample10() { 48 | let game = SnakesAndLadders() 49 | print(game.prettyTextualDescription) 50 | } 51 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/ProtocolSyntax.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ProtocolSyntax.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | //--------------------- Define Protocols --------------------- 12 | 13 | protocol FirstProtocol { 14 | // protocol definition goes here 15 | } 16 | 17 | protocol AnotherProtocol { 18 | // protocol definition goes here 19 | } 20 | 21 | 22 | //--------------------- Define custom types --------------------- 23 | 24 | struct SomeStructure: FirstProtocol, AnotherProtocol { 25 | // structure definition goes here 26 | } 27 | 28 | class SomeSuperClass { 29 | // class definition goes here 30 | 31 | init() { 32 | 33 | } 34 | } 35 | 36 | /* “If a class has a superclass, list the superclass name before any protocols it adopts, followed by a comma” 37 | */ 38 | class SomeClass: SomeSuperClass, FirstProtocol, AnotherProtocol /* SomeSuperClass */ { 39 | // class definition goes here 40 | } 41 | 42 | //--------------------- properties and methods -------------------- 43 | 44 | protocol SomeProtocol { 45 | 46 | // gettable and settable property 47 | var mustBeSettable: Int { get set } 48 | 49 | // gettable property 50 | var doesNotNeedToBeSettable: Int { get } 51 | 52 | // type property 53 | static var someTypeProperty: Int { 54 | get set 55 | } 56 | 57 | // method 58 | func someMethod() 59 | 60 | // type method 61 | static func someTypeMethod() 62 | 63 | // initializer 64 | init(someParameter: Int) 65 | init() 66 | } 67 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/ProtocolsAsTypes.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ProtocolsAsTypes.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | class Dice { 13 | let sides: Int 14 | let generator: RandomNumberGenerator // generator's type is a Protocol 15 | 16 | init(sides: Int, generator: RandomNumberGenerator) { 17 | self.sides = sides 18 | self.generator = generator 19 | } 20 | 21 | func roll() -> Int { 22 | return Int(generator.random() * Double(sides)) + 1 23 | } 24 | } 25 | 26 | func runExample04() { 27 | let d6 = Dice.init(sides: 6, generator: LinearCongruentialGenerator()) 28 | 29 | for _ in 1...5 { 30 | print("Random dice roll is \(d6.roll())") 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /Presentation/Demo/Protocols/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Protocols 4 | // 5 | // Created by ShannonChen on 2019/8/25. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | //runExample01() 12 | //runExample02() 13 | //runExample03() 14 | //runExample04() 15 | //runExample05() 16 | //runExample06() 17 | //runExample07() 18 | //runExample08() 19 | //runExample09() 20 | //runExample10() 21 | //runExample11() 22 | //runExample12() 23 | //runExample13() 24 | //runExample14() 25 | //runExample15() 26 | //runExample16() 27 | //runExample17() 28 | runExample18() 29 | -------------------------------------------------------------------------------- /Presentation/Demo/Runtime/AssociatedObjects.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AssociatedObjects.swift 3 | // Runtime 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | extension NSDate { 12 | private struct AssociatedKeys { 13 | static var DescriptiveName = "DescriptiveName" 14 | // static var AnotherKey = "AnotherKey" 15 | } 16 | 17 | // var descriptiveName = "" 18 | var descriptiveName: String? { 19 | get { 20 | return objc_getAssociatedObject(self, &AssociatedKeys.DescriptiveName) as? String 21 | } 22 | 23 | set { 24 | if let newValue = newValue { 25 | objc_setAssociatedObject( 26 | self, 27 | &AssociatedKeys.DescriptiveName, 28 | newValue as NSString?, 29 | .OBJC_ASSOCIATION_RETAIN_NONATOMIC 30 | ) 31 | } 32 | } 33 | } 34 | } 35 | 36 | func runAssociatedObjectsExample() { 37 | let date = NSDate(timeIntervalSince1970: 0) 38 | date.descriptiveName = "Beijing" 39 | if let name = date.descriptiveName { 40 | print(name) 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /Presentation/Demo/Runtime/Dynamic.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Dynamic.swift 3 | // Runtime 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | class ParentClass { 13 | dynamic func method1() {} 14 | dynamic func method2() {} 15 | } 16 | class ChildClass: ParentClass { 17 | override func method2() {} 18 | dynamic func method3() {} 19 | 20 | 21 | } 22 | -------------------------------------------------------------------------------- /Presentation/Demo/Runtime/KVC.swift: -------------------------------------------------------------------------------- 1 | // 2 | // KVC.swift 3 | // Runtime 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | class Person: NSObject { 13 | @objc var name: String 14 | @objc var friends: [Person] = [] 15 | @objc var bestFriend: Person? = nil 16 | 17 | init(name: String) { 18 | self.name = name 19 | } 20 | } 21 | 22 | func runKeyPathExample() { 23 | 24 | let gabrielle = Person(name: "Gabrielle") 25 | let jim = Person(name: "Jim") 26 | let yuanyuan = Person(name: "Yuanyuan") 27 | gabrielle.friends = [jim, yuanyuan] 28 | gabrielle.bestFriend = yuanyuan 29 | 30 | 31 | print(gabrielle.value(forKey: #keyPath(Person.name)) ?? "") 32 | 33 | print(gabrielle.value(forKeyPath: #keyPath(Person.bestFriend.name)) ?? "") 34 | 35 | print(gabrielle.value(forKeyPath: #keyPath(Person.friends.name)) ?? "") 36 | 37 | } 38 | -------------------------------------------------------------------------------- /Presentation/Demo/Runtime/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Runtime 4 | // 5 | // Created by ShannonChen on 2019/7/15. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | //runKeyPathExample() 12 | 13 | //runAssociatedObjectsExample() 14 | 15 | runMethodSwizzlingExample() 16 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. 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 | 24 | #pragma mark - UISceneSession lifecycle 25 | 26 | 27 | - (UISceneConfiguration *)application:(UIApplication *)application configurationForConnectingSceneSession:(UISceneSession *)connectingSceneSession options:(UISceneConnectionOptions *)options { 28 | // Called when a new scene session is being created. 29 | // Use this method to select a configuration to create the new scene with. 30 | return [[UISceneConfiguration alloc] initWithName:@"Default Configuration" sessionRole:connectingSceneSession.role]; 31 | } 32 | 33 | 34 | - (void)application:(UIApplication *)application didDiscardSceneSessions:(NSSet *)sceneSessions { 35 | // Called when the user discards a scene session. 36 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 37 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 38 | } 39 | 40 | 41 | @end 42 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/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 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/CocoaDesignPatterns-Bridging-Header.h: -------------------------------------------------------------------------------- 1 | // 2 | // Use this file to import your target's public headers that you would like to expose to Swift. 3 | // 4 | 5 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/KVC.swift: -------------------------------------------------------------------------------- 1 | // 2 | // KVC.swift 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | class Person: NSObject { 12 | @objc var name: String 13 | @objc var friends: [Person] = [] 14 | @objc var bestFriend: Person? = nil 15 | 16 | init(name: String) { 17 | self.name = name 18 | } 19 | 20 | @objc func run() { 21 | print("🏃 run... 🏃") 22 | } 23 | } 24 | 25 | class KVCExample: NSObject { 26 | @objc static func run() { 27 | let gabrielle = Person(name: "Gabrielle") 28 | let jim = Person(name: "Jim") 29 | let yuanyuan = Person(name: "Yuanyuan") 30 | gabrielle.friends = [jim, yuanyuan] 31 | gabrielle.bestFriend = yuanyuan 32 | 33 | print(#keyPath(Person.name)) // "name" 34 | 35 | print(gabrielle.value(forKey: #keyPath(Person.name)) as? String ?? "") // "Gabrielle" 36 | 37 | print(#keyPath(Person.bestFriend.name)) // "bestFriend.name" 38 | 39 | print(gabrielle.value(forKeyPath: #keyPath(Person.bestFriend.name)) as? String ?? "") // "Yuanyuan" 40 | 41 | print(#keyPath(Person.friends.name)) // "friends.name" 42 | 43 | print(gabrielle.value(forKeyPath: #keyPath(Person.friends.name)) as? String ?? "") // ["Yuanyuan", "Jim"] 44 | 45 | 46 | let action = #selector(Person.run) 47 | jim.perform(action) 48 | } 49 | } 50 | 51 | 52 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/KVO.swift: -------------------------------------------------------------------------------- 1 | // 2 | // KVO.swift 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | class MyObjectToObserve: NSObject { 12 | @objc dynamic var myDate = NSDate(timeIntervalSince1970: 0) // 1970 13 | func updateDate() { 14 | myDate = myDate.addingTimeInterval(Double(2 << 30)) // Adds about 68 years. 15 | } 16 | } 17 | 18 | class MyObserver: NSObject { 19 | @objc var objectToObserve: MyObjectToObserve 20 | var observation: NSKeyValueObservation? 21 | 22 | init(object: MyObjectToObserve) { 23 | objectToObserve = object 24 | super.init() 25 | 26 | observation = observe( 27 | \.objectToObserve.myDate, 28 | options: [.old, .new] 29 | ) { object, change in 30 | print("myDate changed from: \(change.oldValue!), updated to: \(change.newValue!)") 31 | } 32 | } 33 | } 34 | 35 | @objc class KVOExample: NSObject { 36 | @objc static func run() { 37 | let observed = MyObjectToObserve() 38 | let observer = MyObserver(object: observed) 39 | observed.updateDate() 40 | 41 | } 42 | } 43 | 44 | 45 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/SceneDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SceneDelegate.h 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface SceneDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/Singleton.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Singleton.swift 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | class Singleton { 13 | // 1. 14 | // static let sharedInstance = Singleton() 15 | 16 | // 2. 17 | static let sharedInstance: Singleton = { 18 | let instance = Singleton() 19 | // setup code 20 | return instance 21 | }() 22 | } 23 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ViewController : UIViewController 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import "ViewController.h" 10 | #import "CocoaDesignPatterns-Swift.h" 11 | 12 | @interface ViewController () 13 | 14 | @end 15 | 16 | @implementation ViewController 17 | 18 | - (void)viewDidLoad { 19 | [super viewDidLoad]; 20 | [KVOExample run]; 21 | [KVCExample run]; 22 | } 23 | 24 | 25 | @end 26 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/CocoaDesignPatterns/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // CocoaDesignPatterns 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | NSString * appDelegateClassName; 14 | @autoreleasepool { 15 | // Setup code that might create autoreleased objects goes here. 16 | appDelegateClassName = NSStringFromClass([AppDelegate class]); 17 | } 18 | return UIApplicationMain(argc, argv, nil, appDelegateClassName); 19 | } 20 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/LanguageInteroperability.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // ObjcCodeCustomization 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // ObjcCodeCustomization 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. 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 | 24 | #pragma mark - UISceneSession lifecycle 25 | 26 | 27 | - (UISceneConfiguration *)application:(UIApplication *)application configurationForConnectingSceneSession:(UISceneSession *)connectingSceneSession options:(UISceneConnectionOptions *)options { 28 | // Called when a new scene session is being created. 29 | // Use this method to select a configuration to create the new scene with. 30 | return [[UISceneConfiguration alloc] initWithName:@"Default Configuration" sessionRole:connectingSceneSession.role]; 31 | } 32 | 33 | 34 | - (void)application:(UIApplication *)application didDiscardSceneSessions:(NSSet *)sceneSessions { 35 | // Called when the user discards a scene session. 36 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 37 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 38 | } 39 | 40 | 41 | @end 42 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/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 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/Color.h: -------------------------------------------------------------------------------- 1 | // 2 | // Color.h 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #ifndef Color_h 10 | #define Color_h 11 | 12 | #import 13 | 14 | struct Color { 15 | float r; 16 | float g; 17 | float b; 18 | float alpha; 19 | }; 20 | 21 | typedef struct Color Color; 22 | 23 | Color ColorCreateWithCMYK(float c, float m, float y, float k) CF_SWIFT_NAME(Color.init(c:m:y:k:)); // 构造器 24 | 25 | float ColorGetHue(Color color) CF_SWIFT_NAME(getter:Color.hue(self:)); // 实例属性 getter 26 | void ColorSetHue(Color color, float hue) CF_SWIFT_NAME(setter:Color.hue(self:newValue:)); // 实例属性 setter 27 | 28 | Color ColorDarkenColor(Color color, float amount) CF_SWIFT_NAME(Color.darken(self:amount:)); // 实例方法 29 | 30 | extern const Color ColorBondiBlue CF_SWIFT_NAME(Color.bondiBlue); // 常量 31 | 32 | Color ColorGetCalibrationColor(void) CF_SWIFT_NAME(getter:Color.calibration()); // 类属性 getter 33 | Color ColorSetCalibrationColor(Color color) CF_SWIFT_NAME(setter:Color.calibration(newValue:)); // 类属性 setter 34 | 35 | #endif /* Color_h */ 36 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/Color.m: -------------------------------------------------------------------------------- 1 | // 2 | // Color.m 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import "Color.h" 10 | 11 | Color ColorCreateWithCMYK(float c, float m, float y, float k) { 12 | Color color; 13 | color.r = c; 14 | color.g = m; 15 | color.b = y; 16 | color.alpha = k; 17 | return color; 18 | } 19 | 20 | float ColorGetHue(Color color) { 21 | return 1; 22 | } 23 | 24 | 25 | void ColorSetHue(Color color, float hue) { 26 | 27 | } 28 | 29 | Color ColorDarkenColor(Color color, float amount) { 30 | return ColorCreateWithCMYK(1, 1, 11, 1); 31 | } 32 | 33 | const Color ColorBondiBlue = {1, 1, 1, 1}; 34 | 35 | Color ColorGetCalibrationColor(void) { 36 | return ColorBondiBlue; 37 | } 38 | 39 | Color ColorSetCalibrationColor(Color color) { 40 | return ColorBondiBlue; 41 | } 42 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/File.swift: -------------------------------------------------------------------------------- 1 | // 2 | // File.swift 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | 13 | @objc(CTHotelFile) class File: NSObject { 14 | @objc static let timeoutInterval = 15.0 15 | @objc func save() { 16 | // var a: String? = nil 17 | // a = "xxx" 18 | // print(a?.lowercased()) 19 | // if let str = a?.lowercased() { 20 | // 21 | // } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/MyViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MyViewController.swift 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class MyViewController: UIViewController { 12 | 13 | override func viewDidLoad() { 14 | super.viewDidLoad() 15 | 16 | if #available(iOS 11, *) { 17 | // Use iOS 11 APIs. 18 | } else { 19 | // Alternative code for earlier versions of iOS. 20 | } 21 | 22 | let _ = Color.init(r: 1, g: 1, b: 1, alpha: 1) 23 | let color = Color.init(c: 2, m: 4, y: 5, k: 5) 24 | let darkenColor = color.darken(amount: 1) 25 | darkenColor.hue = 1 26 | print(darkenColor.hue) 27 | let bondiBlue = Color.bondiBlue 28 | let _ = Color.calibration 29 | Color.calibration = bondiBlue 30 | } 31 | 32 | 33 | @available(iOS 11, macOS 10.13, *) 34 | func newMethod() { 35 | // Use iOS 11 APIs. 36 | 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/ObjcCodeCustomization-Bridging-Header.h: -------------------------------------------------------------------------------- 1 | // 2 | // Use this file to import your target's public headers that you would like to expose to Swift. 3 | // 4 | 5 | #import "ViewController.h" 6 | #import "Color.h" 7 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/SceneDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SceneDelegate.h 3 | // ObjcCodeCustomization 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface SceneDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ViewController : UIViewController 12 | 13 | - (void)newMethod API_AVAILABLE(ios(11), macosx(10.13)); 14 | 15 | + (instancetype)collectionWithValues:(NSArray *)values forKeys:(NSArray *)keys NS_SWIFT_UNAVAILABLE("Use a dictionary literal instead."); // Swift 头文件中看不到这个方法 16 | 17 | - (void)unavailableMethod NS_UNAVAILABLE; // 调用该方法时,代码不会自动补全 18 | 19 | @end 20 | 21 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // LanguageInteroperability 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import "ViewController.h" 10 | #import 11 | 12 | @interface ViewController () 13 | 14 | @end 15 | 16 | @implementation ViewController 17 | 18 | + (instancetype)collectionWithValues:(NSArray *)values forKeys:(NSArray *)keys { 19 | return [ViewController new]; 20 | } 21 | 22 | - (void)newMethod { 23 | [[CTHotelFile new] save]; 24 | 25 | } 26 | 27 | - (void)viewDidLoad { 28 | [super viewDidLoad]; 29 | 30 | if (@available(iOS 11, *)) { 31 | // Use iOS 11 APIs. 32 | } else { 33 | // Alternative code for earlier versions of iOS. 34 | } 35 | } 36 | 37 | - (void)unavailableMethod { 38 | 39 | } 40 | 41 | @end 42 | -------------------------------------------------------------------------------- /Presentation/LanguageInteroperability/ObjcCodeCustomization/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // ObjcCodeCustomization 4 | // 5 | // Created by xianglongchen on 2019/11/21. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | NSString * appDelegateClassName; 14 | @autoreleasepool { 15 | // Setup code that might create autoreleased objects goes here. 16 | appDelegateClassName = NSStringFromClass([AppDelegate class]); 17 | } 18 | return UIApplicationMain(argc, argv, nil, appDelegateClassName); 19 | } 20 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/adding_modulemap_to_import_paths.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/adding_modulemap_to_import_paths.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/adding_umbrella_header_to_import_paths.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/adding_umbrella_header_to_import_paths.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/always_embed_swift_standard_library.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/always_embed_swift_standard_library.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/app_thining.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/app_thining.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/build_libraries_for_distribution.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/build_libraries_for_distribution.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/copy_generated_header.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/copy_generated_header.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/debugging_variables.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/debugging_variables.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/dyld_error.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/dyld_error.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/import_paths.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/import_paths.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/integrate_swift_static_lib.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/integrate_swift_static_lib.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/module_stability.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/module_stability.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/modulemap.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/modulemap.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/objc_call_swift.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/objc_call_swift.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/optimization_level.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/optimization_level.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/project_structure.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/project_structure.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/run_script_copy_header.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/run_script_copy_header.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/runpath_search_path.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/runpath_search_path.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/static_linking_error.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/static_linking_error.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swift_call_swift.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swift_call_swift.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swift_dylib_dir.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swift_dylib_dir.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swiftinterface_file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swiftinterface_file.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swiftmodule_dir.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/swiftmodule_dir.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/umbrella_header.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/images/umbrella_header.png -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. 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 | 24 | #pragma mark - UISceneSession lifecycle 25 | 26 | 27 | - (UISceneConfiguration *)application:(UIApplication *)application configurationForConnectingSceneSession:(UISceneSession *)connectingSceneSession options:(UISceneConnectionOptions *)options { 28 | // Called when a new scene session is being created. 29 | // Use this method to select a configuration to create the new scene with. 30 | return [[UISceneConfiguration alloc] initWithName:@"Default Configuration" sessionRole:connectingSceneSession.role]; 31 | } 32 | 33 | 34 | - (void)application:(UIApplication *)application didDiscardSceneSessions:(NSSet *)sceneSessions { 35 | // Called when the user discards a scene session. 36 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 37 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 38 | } 39 | 40 | 41 | @end 42 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/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 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/EmptyFile.swift: -------------------------------------------------------------------------------- 1 | // 2 | // EmptyFile.swift 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/30. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/SceneDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SceneDelegate.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface SceneDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ViewController : UIViewController 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import "ViewController.h" 10 | #import "ObjCLibA.h" 11 | 12 | @interface ViewController () 13 | 14 | @end 15 | 16 | @implementation ViewController 17 | 18 | - (void)viewDidLoad { 19 | [super viewDidLoad]; 20 | // Do any additional setup after loading the view. 21 | 22 | self.view.backgroundColor = [UIColor blueColor]; 23 | 24 | [[ObjCLibA new] sayHello]; 25 | } 26 | 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/MainProject/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | NSString * appDelegateClassName; 14 | @autoreleasepool { 15 | // Setup code that might create autoreleased objects goes here. 16 | appDelegateClassName = NSStringFromClass([AppDelegate class]); 17 | } 18 | return UIApplicationMain(argc, argv, nil, appDelegateClassName); 19 | } 20 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibA/ObjCLibA.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibA/ObjCLibA/ObjCLibA.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibA.h 3 | // ObjCLibA 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ObjCLibA : NSObject 12 | 13 | - (void)sayHello; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibA/ObjCLibA/ObjCLibA.m: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibA.m 3 | // ObjCLibA 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import "ObjCLibA.h" 10 | #import "SwiftLibA-Swift.h" 11 | 12 | @implementation ObjCLibA 13 | 14 | - (void)sayHello { 15 | [[SwiftLibA new] sayHelloWithName:@"ObjCLibA"]; 16 | } 17 | 18 | @end 19 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibB/ObjCLibB/ObjCLibB.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibB.h 3 | // ObjCLibB 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ObjCLibB : NSObject 12 | 13 | - (void)sayHello; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibB/ObjcLibBUmbrellaHeader.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjcLibBUmbrellaHeader.h 3 | // ObjCLibB 4 | // 5 | // Created by ShannonChen on 2020/3/29. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #ifndef ObjcLibBUmbrellaHeader_h 10 | #define ObjcLibBUmbrellaHeader_h 11 | 12 | #import "ObjCLibB.h" 13 | 14 | #endif /* ObjcLibBUmbrellaHeader_h */ 15 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibB/libObjCLibB.a: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibB/libObjCLibB.a -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/ObjCLibB/module.modulemap: -------------------------------------------------------------------------------- 1 | module ObjCLibB { 2 | header "ObjcLibBUmbrellaHeader.h" 3 | } 4 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibA/SwiftLibA.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibA/SwiftLibA/SwiftLibA.swift: -------------------------------------------------------------------------------- 1 | // 2 | // SwiftLibA.swift 3 | // SwiftLibA 4 | // 5 | // Created by ShannonChen on 2020/3/26. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | import SwiftLibB 11 | import ObjCLibB 12 | 13 | @objcMembers 14 | public class SwiftLibA: NSObject { 15 | 16 | public func sayHello(name: String) { 17 | SwiftLibB().sayHello(name: name) 18 | ObjCLibB().sayHello() 19 | print("-- Printed by SwiftLibA") 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/libSwiftLibB.a: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/Modules/SwiftLibB/libSwiftLibB.a -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_libs/README.md: -------------------------------------------------------------------------------- 1 | # 示例代码 2 | 3 | 这个 sample project 演示的是通过静态库(.a文件 + “头文件”)的方式依赖模块 SwiftLibB 和 ObjCLibB。 4 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. 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 | 24 | #pragma mark - UISceneSession lifecycle 25 | 26 | 27 | - (UISceneConfiguration *)application:(UIApplication *)application configurationForConnectingSceneSession:(UISceneSession *)connectingSceneSession options:(UISceneConnectionOptions *)options { 28 | // Called when a new scene session is being created. 29 | // Use this method to select a configuration to create the new scene with. 30 | return [[UISceneConfiguration alloc] initWithName:@"Default Configuration" sessionRole:connectingSceneSession.role]; 31 | } 32 | 33 | 34 | - (void)application:(UIApplication *)application didDiscardSceneSessions:(NSSet *)sceneSessions { 35 | // Called when the user discards a scene session. 36 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 37 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 38 | } 39 | 40 | 41 | @end 42 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/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 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/EmptyFile.swift: -------------------------------------------------------------------------------- 1 | // 2 | // EmptyFile.swift 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/30. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/SceneDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SceneDelegate.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface SceneDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow * window; 14 | 15 | @end 16 | 17 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ViewController : UIViewController 12 | 13 | 14 | @end 15 | 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import "ViewController.h" 10 | #import "ObjCLibA.h" 11 | 12 | @interface ViewController () 13 | 14 | @end 15 | 16 | @implementation ViewController 17 | 18 | - (void)viewDidLoad { 19 | [super viewDidLoad]; 20 | // Do any additional setup after loading the view. 21 | 22 | self.view.backgroundColor = [UIColor blueColor]; 23 | 24 | [[ObjCLibA new] sayHello]; 25 | } 26 | 27 | 28 | @end 29 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/MainProject/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // MainProject 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | NSString * appDelegateClassName; 14 | @autoreleasepool { 15 | // Setup code that might create autoreleased objects goes here. 16 | appDelegateClassName = NSStringFromClass([AppDelegate class]); 17 | } 18 | return UIApplicationMain(argc, argv, nil, appDelegateClassName); 19 | } 20 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibA/ObjCLibA.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibA/ObjCLibA/ObjCLibA.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibA.h 3 | // ObjCLibA 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ObjCLibA : NSObject 12 | 13 | - (void)sayHello; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibA/ObjCLibA/ObjCLibA.m: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibA.m 3 | // ObjCLibA 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import "ObjCLibA.h" 10 | #import "SwiftLibA-Swift.h" 11 | 12 | @implementation ObjCLibA 13 | 14 | - (void)sayHello { 15 | [[SwiftLibA new] sayHelloWithName:@"ObjCLibA"]; 16 | } 17 | 18 | @end 19 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibB/ObjCLibB.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibB/ObjCLibB/ObjCLibB.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibB.h 3 | // ObjCLibB 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface ObjCLibB : NSObject 12 | 13 | - (void)sayHello; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibB/ObjCLibB/ObjCLibB.m: -------------------------------------------------------------------------------- 1 | // 2 | // ObjCLibB.m 3 | // ObjCLibB 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #import "ObjCLibB.h" 10 | 11 | @implementation ObjCLibB 12 | 13 | - (void)sayHello { 14 | NSLog(@"This is ObjCLibB!"); 15 | } 16 | 17 | @end 18 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibB/ObjcLibBUmbrellaHeader.h: -------------------------------------------------------------------------------- 1 | // 2 | // ObjcLibBUmbrellaHeader.h 3 | // ObjCLibB 4 | // 5 | // Created by ShannonChen on 2020/3/29. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | #ifndef ObjcLibBUmbrellaHeader_h 10 | #define ObjcLibBUmbrellaHeader_h 11 | 12 | #import "ObjCLibB.h" 13 | 14 | #endif /* ObjcLibBUmbrellaHeader_h */ 15 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/ObjCLibB/module.modulemap: -------------------------------------------------------------------------------- 1 | module ObjCLibB { 2 | header "ObjcLibBUmbrellaHeader.h" 3 | } 4 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibA/SwiftLibA.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibA/SwiftLibA/SwiftLibA.swift: -------------------------------------------------------------------------------- 1 | // 2 | // SwiftLibA.swift 3 | // SwiftLibA 4 | // 5 | // Created by ShannonChen on 2020/3/26. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | import SwiftLibB 11 | import ObjCLibB 12 | 13 | @objcMembers 14 | public class SwiftLibA: NSObject { 15 | 16 | public func sayHello(name: String) { 17 | SwiftLibB().sayHello(name: name) 18 | ObjCLibB().sayHello() 19 | print("-- Printed by SwiftLibA") 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB/SwiftLibB.swift: -------------------------------------------------------------------------------- 1 | // 2 | // SwiftLibB.swift 3 | // SwiftLibB 4 | // 5 | // Created by ShannonChen on 2020/3/28. 6 | // Copyright © 2020 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | import ObjCLibB 11 | 12 | @objcMembers 13 | public class SwiftLibB: NSObject { 14 | 15 | public func sayHello(name: String) { 16 | ObjCLibB().sayHello() 17 | print("Hello, this is " + name + "!") 18 | print("-- Printed by SwiftLibB") 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64-apple-ios-simulator.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftdoc -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftinterface: -------------------------------------------------------------------------------- 1 | // swift-interface-format-version: 1.0 2 | // swift-compiler-version: Apple Swift version 5.1 (swiftlang-1100.0.270.13 clang-1100.0.33.7) 3 | // swift-module-flags: -target x86_64-apple-ios13.0-simulator -enable-objc-interop -enable-library-evolution -swift-version 5 -enforce-exclusivity=checked -Onone -module-name SwiftLibB 4 | import Foundation 5 | import ObjCLibB 6 | import Swift 7 | @objc @objcMembers public class SwiftLibB : ObjectiveC.NSObject { 8 | @objc public func sayHello(name: Swift.String) 9 | @objc override dynamic public init() 10 | @objc deinit 11 | } 12 | -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/Modules/SwiftLibB/SwiftLibB.swiftmodule/x86_64.swiftmodule -------------------------------------------------------------------------------- /Presentation/ObjC-Swift 混编在模块化:组件化项目中的实践/sample_projects/using_dependency_as_source_code/README.md: -------------------------------------------------------------------------------- 1 | # 示例代码 2 | 3 | 这个 sample project 演示的是通过源码(子工程)的方式依赖模块 SwiftLibB 和 ObjCLibB。 4 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/ConstrainingValues/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // ConstrainingValues 4 | // 5 | // Created by xianglongchen on 2019/11/13. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /// a value clamping property wrapper 12 | @propertyWrapper 13 | struct Clamping { 14 | var value: Value 15 | let range: ClosedRange 16 | 17 | init(wrappedValue value: Value, _ range: ClosedRange) { 18 | precondition(range.contains(value)) 19 | self.value = value 20 | self.range = range 21 | } 22 | 23 | var wrappedValue: Value { 24 | get { 25 | value 26 | } 27 | set { 28 | value = min(max(range.lowerBound, newValue), range.upperBound) 29 | } 30 | } 31 | } 32 | 33 | struct Solution { 34 | @Clamping(0...14) var pH: Double = 7.0 35 | } 36 | 37 | let carbonicAcid = Solution(pH: 4.68) // at 1 mM under standard conditions 38 | 39 | let superDuperAcid = Solution(pH: -1) 40 | print(superDuperAcid.pH) // 0 41 | 42 | 43 | //____________________________________________________________________________________________________________ 44 | 45 | /// a value clamping property wrapper 46 | @propertyWrapper 47 | struct UnitInterval { 48 | @Clamping(0...1) var wrappedValue: Value = .zero 49 | 50 | init(wrappedValue value: Value) { 51 | self.wrappedValue = value 52 | } 53 | } 54 | 55 | struct RGB { 56 | @UnitInterval var red: Double 57 | @UnitInterval var green: Double 58 | @UnitInterval var blue: Double 59 | } 60 | 61 | let cornflowerBlue = RGB(red: 0.392, green: 0.584, blue: 0.929) 62 | 63 | 64 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/Intro01/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Intro01 4 | // 5 | // Created by xianglongchen on 2019/11/13. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | var settings = ["swift": true, "latestVersion": true] 12 | struct Settings { 13 | var isSwift: Bool { 14 | get { 15 | return settings["swift"] ?? false 16 | } 17 | set { 18 | settings["swift"] = newValue 19 | } 20 | } 21 | 22 | var isLatestVersion: Bool { 23 | get { 24 | return settings["latestVersion"] ?? false 25 | } 26 | set { 27 | settings["latestVersion"] = newValue 28 | } 29 | } 30 | } 31 | 32 | var newSettings = Settings() 33 | print(newSettings.isSwift) 34 | print(newSettings.isLatestVersion) 35 | newSettings.isSwift = false 36 | newSettings.isLatestVersion = false 37 | print(newSettings.isSwift) 38 | print(newSettings.isLatestVersion) 39 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/Intro02/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Intro02 4 | // 5 | // Created by xianglongchen on 2019/11/13. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | var settings = ["swift": true, "latestVersion": true] 12 | // 1 13 | @propertyWrapper 14 | struct SettingsWrapper { 15 | let key: String 16 | let defaultValue: Bool 17 | 18 | // 2 19 | var wrappedValue: Bool { 20 | get { 21 | settings[key] ?? defaultValue 22 | } 23 | set { 24 | settings[key] = newValue 25 | } 26 | } 27 | } 28 | 29 | // 3 30 | struct Settings { 31 | @SettingsWrapper(key: "swift", defaultValue: false) var isSwift: Bool 32 | @SettingsWrapper(key: "latestVersion", defaultValue: false) var isLatestVersion: Bool 33 | } 34 | 35 | 36 | 37 | var newSettings = Settings() 38 | print(newSettings.isSwift) 39 | print(newSettings.isLatestVersion) 40 | newSettings.isSwift = false 41 | newSettings.isLatestVersion = false 42 | print(newSettings.isSwift) 43 | print(newSettings.isLatestVersion) 44 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/PropertyWrapper.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/README.md: -------------------------------------------------------------------------------- 1 | # Property Wrapper 2 | 3 | 4 | 5 | ### 四种使用场景: 6 | - Constraining Values 7 | - Transforming Values on Property Assignment 8 | - Changing Synthesized Equality and Comparison Semantics 9 | - Auditing Property Access 10 | 11 | ### 缺点 12 | - Properties Can’t Participate in Error Handling 13 | - Wrapped Properties Can’t Be Aliased 14 | - Property Wrappers Are Difficult To Compose 15 | - Property Wrappers Aren’t First-Class Dependent Types 16 | - Property Wrappers Are Difficult to Document 17 | - Property Wrappers Further Complicate Swift 18 | 19 | ### 参考: 20 | https://nshipster.com/propertywrapper/ 21 | https://github.com/apple/swift-evolution/blob/master/proposals/0258-property-wrappers.md 22 | https://medium.com/genetec-tech/property-wrappers-in-swift-5-1-the-missing-published-implementation-1a466ebcf660 23 | -------------------------------------------------------------------------------- /Presentation/PropertyWrapper/TransformingValues/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // TransformingValues 4 | // 5 | // Created by xianglongchen on 2019/11/13. 6 | // Copyright © 2019 ctrip. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /// A Property Wrapper that Trims Whitespace from String Values 12 | @propertyWrapper 13 | struct Trimmed { 14 | private(set) var value: String = "" 15 | 16 | var wrappedValue: String { 17 | get { value } 18 | set { value = newValue.trimmingCharacters(in: .whitespacesAndNewlines) } 19 | } 20 | 21 | init(wrappedValue value: String) { 22 | self.wrappedValue = value 23 | } 24 | } 25 | 26 | struct Post { 27 | @Trimmed var title: String 28 | @Trimmed var body: String 29 | 30 | 31 | // var title: String { 32 | // willSet { 33 | // title = newValue.trimmingCharacters(in: .whitespacesAndNewlines) 34 | // /* ⚠️ Attempting to store to property 'title' within its own willSet, 35 | // which is about to be overwritten by the new value */ 36 | // } 37 | // } 38 | 39 | // var title: String { 40 | // // 😓 Not called during initialization 41 | // didSet { 42 | // self.title = title.trimmingCharacters(in: .whitespacesAndNewlines) 43 | // } 44 | // } 45 | } 46 | 47 | var quine = Post(title: " Swift Property Wrappers ", body: "...") 48 | print(quine.title) // "Swift Property Wrappers" (no leading or trailing spaces!) 49 | 50 | quine.title = " @propertyWrapper " 51 | print(quine.title) // "@propertyWrapper" (still no leading or trailing spaces!) 52 | -------------------------------------------------------------------------------- /Presentation/SwiftProgramming.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/SwiftProgramming.key -------------------------------------------------------------------------------- /Presentation/SwiftProgramming.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/Presentation/SwiftProgramming.pdf -------------------------------------------------------------------------------- /Presentation/ValueTypes/EratosthenesSieve/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // EratosthenesSieve 4 | // 5 | // Created by ShannonChen on 2019/9/8. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | /** 埃拉托斯特尼筛选法:求不超过自然数N(N>1)的所有质数的一种算法。 12 | 13 | */ 14 | 15 | /// mutating 版本 16 | func primes(n: Int) -> [Int] { 17 | var numbers = [Int](2.. 0 { 21 | for multiple in stride(from: 2 * prime-2, to: n-2, by: prime) { 22 | numbers[multiple] = 0 23 | } 24 | } 25 | } 26 | return numbers.filter { $0 > 0 } 27 | } 28 | // 29 | //func foo() -> (a: Int, b: Int) { 30 | // return (5, 8) 31 | //} 32 | // 33 | //let (a: Int, b: Int) = foo() 34 | 35 | 36 | /// non-mutating 版本 37 | func sieve(numbers: [Int]) -> [Int] { 38 | if numbers.isEmpty { return [] } 39 | let p = numbers[0] 40 | return [p] + sieve(numbers: numbers[1.. 0 }) 41 | } 42 | 43 | 44 | print(primes(n: 20)) 45 | 46 | let numbers = [Int](2..<20) 47 | let result = sieve(numbers: numbers) 48 | print(result) 49 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/Immutability/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Immutability 4 | // 5 | // Created by ShannonChen on 2019/9/8. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | class Temperature { 12 | let celsius: Double 13 | var fahrenheit: Double { 14 | get { return celsius * 9 / 5 + 32} 15 | } 16 | 17 | init(celsius: Double) { 18 | self.celsius = celsius 19 | } 20 | init(fahrenheit: Double) { 21 | self.celsius = (fahrenheit - 32) * 5 / 9 22 | } 23 | 24 | } 25 | 26 | 27 | /// 空调 28 | class Thermostat { 29 | var temperature = Temperature(celsius: 0) 30 | 31 | func turnUp() { 32 | 33 | } 34 | func turnDown() { 35 | 36 | } 37 | } 38 | 39 | /// 烤箱 40 | class Oven { 41 | var temperature = Temperature(celsius: 0) 42 | 43 | func bake() { 44 | 45 | } 46 | } 47 | 48 | 49 | /// 房子 50 | class House { 51 | var thermostat = Thermostat() 52 | var oven = Oven() 53 | } 54 | 55 | let home = House() 56 | home.thermostat.temperature = Temperature(celsius: 10.0) 57 | //home.thermostat.temperature.celsius += 10.0 58 | let temp = home.thermostat.temperature 59 | home.thermostat.temperature = Temperature(celsius: temp.celsius + 10.0) 60 | // 其实如果严格按照 Immutablity 的要求的话,除了 Temperature 之外,其他的 class 的属性也都要改成 let 了,这样的话,修改状态将会变得非常麻烦 61 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueSemantics/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // ValueSemantics 4 | // 5 | // Created by ShannonChen on 2019/9/8. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | struct Temperature: Equatable { 12 | var celsius: Double = 0 13 | var fahrenheit: Double { 14 | get { return celsius * 9 / 5 + 32 } 15 | set { celsius = (newValue - 32) * 5 / 9 } 16 | } 17 | 18 | static func ==(lhs: Temperature, rhs: Temperature) -> Bool { 19 | return lhs.celsius == rhs.celsius 20 | } 21 | 22 | } 23 | 24 | /// 空调 25 | class Thermostat { 26 | var temperature = Temperature(celsius: 0) 27 | 28 | func turnUp() { 29 | 30 | } 31 | func turnDown() { 32 | 33 | } 34 | } 35 | 36 | /// 烤箱 37 | class Oven { 38 | var temperature = Temperature(celsius: 0) 39 | 40 | func bake() { 41 | 42 | } 43 | } 44 | 45 | 46 | /// 房子 47 | class House { 48 | var thermostat = Thermostat() 49 | var oven = Oven() 50 | } 51 | 52 | let home = House() 53 | var temp = Temperature(celsius: 0) 54 | temp.fahrenheit = 75 55 | home.thermostat.temperature = temp // copy on write 56 | 57 | temp.fahrenheit = 425 58 | home.oven.temperature = temp 59 | home.oven.bake() 60 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypes.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | @UIApplicationMain 12 | class AppDelegate: UIResponder, UIApplicationDelegate { 13 | 14 | 15 | 16 | func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { 17 | // Override point for customization after application launch. 18 | return true 19 | } 20 | 21 | // MARK: UISceneSession Lifecycle 22 | 23 | func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration { 24 | // Called when a new scene session is being created. 25 | // Use this method to select a configuration to create the new scene with. 26 | return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role) 27 | } 28 | 29 | func application(_ application: UIApplication, didDiscardSceneSessions sceneSessions: Set) { 30 | // Called when the user discards a scene session. 31 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 32 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 33 | } 34 | 35 | 36 | } 37 | 38 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/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 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/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 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/BezierPath.swift: -------------------------------------------------------------------------------- 1 | // 2 | // BezierPath.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | struct BezierPath: Drawable { 12 | private var _path = UIBezierPath() 13 | 14 | var pathForReading: UIBezierPath { 15 | return _path 16 | } 17 | 18 | var pathForWriting: UIBezierPath { 19 | mutating get { 20 | _path = _path.copy() as! UIBezierPath 21 | return _path 22 | } 23 | } 24 | 25 | init(path: UIBezierPath) { 26 | _path = path 27 | } 28 | 29 | func draw() { 30 | //... 31 | } 32 | 33 | } 34 | 35 | extension BezierPath { 36 | var isEmpty: Bool { 37 | return pathForReading.isEmpty 38 | } 39 | 40 | mutating func addLine(to point: CGPoint) { 41 | pathForWriting.addLine(to: point) 42 | } 43 | 44 | mutating func move(to point: CGPoint) { 45 | pathForWriting.move(to: point) 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/Circle.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Circle.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | 12 | struct Circle: Equatable { 13 | var center: CGPoint 14 | var radius: CGFloat 15 | init(center: CGPoint, radius: CGFloat) { 16 | self.center = center 17 | self.radius = radius 18 | } 19 | 20 | static func ==(lhs: Circle, rhs: Circle) -> Bool { 21 | return lhs.center == rhs.center && lhs.radius == rhs.radius 22 | } 23 | } 24 | 25 | extension Circle: Drawable { 26 | func draw() { 27 | let arc = CGMutablePath() 28 | arc.addArc(center: center, radius: radius, startAngle: 0, endAngle: 2 * CGFloat.pi, clockwise: true) 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/Diagram.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Diagram.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | struct Diagram: Drawable { 12 | var items: [Drawable] = [] 13 | 14 | mutating func addItem(item: Drawable) { 15 | items.append(item) 16 | } 17 | 18 | func draw() { 19 | for item in items { 20 | item.draw() 21 | } 22 | } 23 | 24 | } 25 | 26 | //extension Diagram: Equatable { 27 | // static func ==(lhs: Diagram, rhs: Diagram) -> Bool { 28 | // return lhs.items == rhs.items 29 | // } 30 | //} 31 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/Drawable.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Drawable.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | 12 | protocol Drawable { 13 | func draw() 14 | } 15 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/Polygon.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Polygon.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | 12 | struct Polygon: Equatable { 13 | var corners: [CGPoint] = [] 14 | 15 | static func ==(lhs: Polygon, rhs: Polygon) -> Bool { 16 | return lhs.corners == rhs.corners 17 | } 18 | } 19 | 20 | extension Polygon: Drawable { 21 | func draw() { 22 | let ctx = UIGraphicsGetCurrentContext() 23 | ctx?.move(to: corners.last!) 24 | for point in corners { 25 | ctx?.move(to: point) 26 | } 27 | ctx?.closePath() 28 | ctx?.strokePath() 29 | } 30 | 31 | } 32 | 33 | extension Polygon { 34 | var path: BezierPath { 35 | let result = UIBezierPath() 36 | result.move(to: corners.last!) 37 | for point in corners { 38 | result.addLine(to: point) 39 | } 40 | return BezierPath(path: result) 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /Presentation/ValueTypes/ValueTypesInPractice/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // ValueTypesInPractice 4 | // 5 | // Created by ShannonChen on 2019/9/13. 6 | // Copyright © 2019 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController { 12 | 13 | override func viewDidLoad() { 14 | super.viewDidLoad() 15 | 16 | var doc = Diagram() 17 | doc.addItem(item: Polygon()) 18 | doc.addItem(item: Circle(center: CGPoint(), radius: 10)) 19 | 20 | var doc2 = doc 21 | let points = [CGPoint(x: 0, y: 0), 22 | CGPoint(x: 10, y: 10), 23 | CGPoint(x: 14, y: 3)] 24 | doc2.items[1] = Polygon(corners: points) 25 | 26 | 27 | doc.addItem(item: Diagram()) 28 | } 29 | 30 | 31 | } 32 | 33 | -------------------------------------------------------------------------------- /RangeSliderExample/README.md: -------------------------------------------------------------------------------- 1 | # RangeSliderExample 2 | 3 | A example project to show how to make a cutom control in Swift. 4 | -------------------------------------------------------------------------------- /RangeSliderExample/RangeSliderExample.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /RangeSliderExample/RangeSliderExample/Assets.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 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /RangeSliderExample/RangeSliderExample/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 | 38 | 39 | -------------------------------------------------------------------------------- /RangeSliderExample/RangeSliderExample/RangeSliderThumbLayer.swift: -------------------------------------------------------------------------------- 1 | // 2 | // RangeSliderThumbLayer.swift 3 | // RangeSliderExample 4 | // 5 | // Created by ShannonChen on 2017/4/29. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class RangeSliderThumbLayer: CALayer { 12 | 13 | var highlighted: Bool = false { 14 | didSet { 15 | setNeedsDisplay() 16 | } 17 | } 18 | weak var rangeSlider: RangeSlider? 19 | 20 | 21 | override func draw(in ctx: CGContext) { 22 | 23 | if let slider = rangeSlider { 24 | 25 | let thumbFrame = bounds.insetBy(dx: 2.0, dy: 2.0) 26 | let cornerRadius = thumbFrame.height * slider.curvaceousness / 2.0 27 | let thumbPath = UIBezierPath.init(roundedRect: thumbFrame, cornerRadius: cornerRadius) 28 | 29 | // Fill - with a subtle shadow 30 | let shadowColor = UIColor.gray 31 | let shadowOffset = CGSize.init(width: 0.0, height: 1.0) 32 | ctx.setShadow(offset: shadowOffset, blur: 1.0, color: shadowColor.cgColor) 33 | ctx.setFillColor(slider.thumbTintColor.cgColor) 34 | ctx.addPath(thumbPath.cgPath) 35 | ctx.fillPath() 36 | 37 | // Outline 38 | ctx.setStrokeColor(shadowColor.cgColor) 39 | ctx.setLineWidth(0.5) 40 | ctx.addPath(thumbPath.cgPath) 41 | ctx.strokePath() 42 | 43 | if highlighted { 44 | ctx.setFillColor(slider.thumbHighlightTintColor.cgColor) 45 | ctx.addPath(thumbPath.cgPath) 46 | ctx.fillPath() 47 | } 48 | } 49 | } 50 | 51 | } 52 | -------------------------------------------------------------------------------- /RangeSliderExample/RangeSliderExample/RangeSliderTrackLayer.swift: -------------------------------------------------------------------------------- 1 | // 2 | // RangeSliderTrackLayer.swift 3 | // RangeSliderExample 4 | // 5 | // Created by ShannonChen on 2017/4/29. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class RangeSliderTrackLayer: CALayer { 12 | weak var rangeSlider: RangeSlider? 13 | 14 | // TODO: Why do we override is this method 15 | // TODO: Core Graphics 16 | override func draw(in ctx: CGContext) { 17 | 18 | if let slider = rangeSlider { 19 | 20 | // Clip 21 | let cornerRadius = bounds.height * 0.5 * slider.curvaceousness 22 | let path = UIBezierPath.init(roundedRect: bounds, cornerRadius: cornerRadius) 23 | ctx.addPath(path.cgPath) 24 | 25 | // Fill the track 26 | ctx.setFillColor(slider.trackTintColor.cgColor) 27 | ctx.addPath(path.cgPath) 28 | ctx.fillPath() 29 | 30 | 31 | // Fill the highlighted range 32 | ctx.setFillColor(slider.trackHighlightTintColor.cgColor) 33 | let lowerValuePosition = CGFloat(slider.positionForValue(value: slider.lowerValue)) 34 | let upperValuePosition = CGFloat(slider.positionForValue(value: slider.upperValue)) 35 | let rect = CGRect.init(x: lowerValuePosition, y: 0.0, width: upperValuePosition - lowerValuePosition, height: bounds.height) 36 | ctx.fill(rect) 37 | 38 | } 39 | 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // Landmarks 4 | // 5 | // Created by xianglongchen on 2019/7/24. 6 | // Copyright © 2019 xianglongchen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | @UIApplicationMain 12 | class AppDelegate: UIResponder, UIApplicationDelegate { 13 | 14 | 15 | 16 | func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { 17 | // Override point for customization after application launch. 18 | return true 19 | } 20 | 21 | // MARK: UISceneSession Lifecycle 22 | 23 | func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration { 24 | // Called when a new scene session is being created. 25 | // Use this method to select a configuration to create the new scene with. 26 | return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role) 27 | } 28 | 29 | func application(_ application: UIApplication, didDiscardSceneSessions sceneSessions: Set) { 30 | // Called when the user discards a scene session. 31 | // If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions. 32 | // Use this method to release any resources that were specific to the discarded scenes, as they will not return. 33 | } 34 | 35 | 36 | } 37 | 38 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Assets.xcassets/turtlerock.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "turtlerock.jpg", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x" 11 | }, 12 | { 13 | "idiom" : "universal", 14 | "scale" : "3x" 15 | } 16 | ], 17 | "info" : { 18 | "version" : 1, 19 | "author" : "xcode" 20 | } 21 | } -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Assets.xcassets/turtlerock.imageset/turtlerock.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Assets.xcassets/turtlerock.imageset/turtlerock.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/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 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/CircleImage.swift: -------------------------------------------------------------------------------- 1 | // 2 | // CircleImage.swift 3 | // Landmarks 4 | // 5 | // Created by xianglongchen on 2019/7/25. 6 | // Copyright © 2019 xianglongchen. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct CircleImage : View { 12 | var image: Image 13 | 14 | var body: some View { 15 | image 16 | .clipShape(Circle()) 17 | .overlay( 18 | Circle().stroke(Color.white, lineWidth: 4)) 19 | .shadow(radius: 10) 20 | } 21 | } 22 | 23 | #if DEBUG 24 | struct CircleImage_Previews : PreviewProvider { 25 | static var previews: some View { 26 | CircleImage(image: Image("turtlerock")) 27 | } 28 | } 29 | #endif 30 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/LandmarkList.swift: -------------------------------------------------------------------------------- 1 | // 2 | // LandmarkList.swift 3 | // Landmarks 4 | // 5 | // Created by ShannonChen on 2019/8/11. 6 | // Copyright © 2019 xianglongchen. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct LandmarkList : View { 12 | var body: some View { 13 | NavigationView { 14 | List(landmarkData) { landmark in 15 | NavigationLink(destination: LandmarkDetail(landmark: landmark)) { 16 | LandmarkRow(landmark: landmark) 17 | } 18 | } 19 | } 20 | .navigationBarTitle(Text("Landmarks").color(Color.blue)) 21 | } 22 | } 23 | 24 | #if DEBUG 25 | struct LandmarkList_Previews : PreviewProvider { 26 | static var previews: some View { 27 | LandmarkList() 28 | } 29 | } 30 | #endif 31 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/LandmarkRow.swift: -------------------------------------------------------------------------------- 1 | // 2 | // LandmarkRow.swift 3 | // Landmarks 4 | // 5 | // Created by ShannonChen on 2019/8/11. 6 | // Copyright © 2019 xianglongchen. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | 11 | struct LandmarkRow : View { 12 | var landmark: Landmark 13 | 14 | var body: some View { 15 | HStack { 16 | landmark.image 17 | .resizable() 18 | .frame(width: 50, height: 50) 19 | Text(landmark.name) 20 | Spacer() 21 | }.background(Color.red) 22 | } 23 | } 24 | 25 | #if DEBUG 26 | struct LandmarkRow_Previews : PreviewProvider { 27 | static var previews: some View { 28 | LandmarkRow(landmark: landmarkData[0]) 29 | } 30 | } 31 | #endif 32 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/MapView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MapView.swift 3 | // Landmarks 4 | // 5 | // Created by xianglongchen on 2019/7/25. 6 | // Copyright © 2019 xianglongchen. All rights reserved. 7 | // 8 | 9 | import SwiftUI 10 | import MapKit 11 | 12 | /* 13 | To use UIView subclasses from within SwiftUI, you wrap the other view in a SwiftUI view that conforms to the UIViewRepresentable protocol. 14 | 15 | The UIViewRepresentable protocol has two requirements you need to add: a `makeUIView(context:)` method that creates an MKMapView, and an `updateUIView(_:context:)` method that configures the view and responds to any changes. 16 | */ 17 | struct MapView : UIViewRepresentable { 18 | var coordinate: CLLocationCoordinate2D 19 | 20 | func makeUIView(context: UIViewRepresentableContext) -> MKMapView { 21 | MKMapView(frame: .zero) 22 | } 23 | 24 | func updateUIView(_ uiView: MKMapView, context: UIViewRepresentableContext) { 25 | 26 | let span = MKCoordinateSpan(latitudeDelta: 0.02, longitudeDelta: 0.02) 27 | let region = MKCoordinateRegion(center: coordinate, span: span) 28 | uiView.setRegion(region, animated: true) 29 | } 30 | } 31 | 32 | #if DEBUG 33 | struct MapView_Previews : PreviewProvider { 34 | static var previews: some View { 35 | MapView(coordinate: landmarkData[0].locationCoordinate) 36 | } 37 | } 38 | #endif 39 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Models/Landmark.swift: -------------------------------------------------------------------------------- 1 | /* 2 | See LICENSE folder for this sample’s licensing information. 3 | 4 | Abstract: 5 | The model for an individual landmark. 6 | */ 7 | 8 | import SwiftUI 9 | import CoreLocation 10 | 11 | 12 | /// a Landmark structure that stores all of the landmark information the app needs to display, and imports an array of landmark data from landmarkData.json. 13 | struct Landmark: Hashable, Codable, Identifiable { 14 | var id: Int 15 | var name: String 16 | fileprivate var imageName: String 17 | fileprivate var coordinates: Coordinates 18 | var state: String 19 | var park: String 20 | var category: Category 21 | 22 | var locationCoordinate: CLLocationCoordinate2D { 23 | CLLocationCoordinate2D( 24 | latitude: coordinates.latitude, 25 | longitude: coordinates.longitude) 26 | } 27 | 28 | enum Category: String, CaseIterable, Codable, Hashable { 29 | case featured = "Featured" 30 | case lakes = "Lakes" 31 | case rivers = "Rivers" 32 | } 33 | } 34 | 35 | extension Landmark { 36 | var image: Image { 37 | ImageStore.shared.image(name: imageName) 38 | } 39 | } 40 | 41 | struct Coordinates: Hashable, Codable { 42 | var latitude: Double 43 | var longitude: Double 44 | } 45 | -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Preview Content/Preview Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/chilkoottrail.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/chilkoottrail.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/chincoteague.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/chincoteague.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/hiddenlake.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/hiddenlake.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/icybay.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/icybay.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/lakemcdonald.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/lakemcdonald.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/rainbowlake.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/rainbowlake.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/silversalmoncreek.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/silversalmoncreek.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/stmarylake.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/stmarylake.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/turtlerock.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/turtlerock.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/twinlake.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/twinlake.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/umbagog.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/umbagog.jpg -------------------------------------------------------------------------------- /SwiftUI/Landmarks/Landmarks/Resources/yukon_charleyrivers.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/SwiftUI/Landmarks/Landmarks/Resources/yukon_charleyrivers.jpg -------------------------------------------------------------------------------- /TheSwiftProgrammingLanguage(Swift3.1).epub: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/TheSwiftProgrammingLanguage(Swift3.1).epub -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/VocalTextEdit/VocalTextEdit.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | VocalTextEdit.xcscheme 8 | 9 | orderHint 10 | 0 11 | 12 | 13 | SuppressBuildableAutocreation 14 | 15 | 583ED4F81E3C5A0700E29325 16 | 17 | primary 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // VocalTextEdit 4 | // 5 | // Created by ShannonChen on 2017/1/28. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Cocoa 10 | 11 | @NSApplicationMain 12 | class AppDelegate: NSObject, NSApplicationDelegate { 13 | 14 | 15 | 16 | func applicationDidFinishLaunching(_ aNotification: Notification) { 17 | // Insert code here to initialize your application 18 | } 19 | 20 | func applicationWillTerminate(_ aNotification: Notification) { 21 | // Insert code here to tear down your application 22 | } 23 | 24 | 25 | } 26 | 27 | -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "mac", 5 | "size" : "16x16", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "mac", 10 | "size" : "16x16", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "mac", 15 | "size" : "32x32", 16 | "scale" : "1x" 17 | }, 18 | { 19 | "idiom" : "mac", 20 | "size" : "32x32", 21 | "scale" : "2x" 22 | }, 23 | { 24 | "idiom" : "mac", 25 | "size" : "128x128", 26 | "scale" : "1x" 27 | }, 28 | { 29 | "idiom" : "mac", 30 | "size" : "128x128", 31 | "scale" : "2x" 32 | }, 33 | { 34 | "idiom" : "mac", 35 | "size" : "256x256", 36 | "scale" : "1x" 37 | }, 38 | { 39 | "idiom" : "mac", 40 | "size" : "256x256", 41 | "scale" : "2x" 42 | }, 43 | { 44 | "idiom" : "mac", 45 | "size" : "512x512", 46 | "scale" : "1x" 47 | }, 48 | { 49 | "idiom" : "mac", 50 | "size" : "512x512", 51 | "scale" : "2x" 52 | } 53 | ], 54 | "info" : { 55 | "version" : 1, 56 | "author" : "xcode" 57 | } 58 | } -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleDocumentTypes 8 | 9 | 10 | CFBundleTypeExtensions 11 | 12 | txt 13 | 14 | CFBundleTypeIconFile 15 | 16 | CFBundleTypeName 17 | DocumentType 18 | CFBundleTypeOSTypes 19 | 20 | ???? 21 | 22 | CFBundleTypeRole 23 | Editor 24 | NSDocumentClass 25 | $(PRODUCT_MODULE_NAME).Document 26 | 27 | 28 | CFBundleExecutable 29 | $(EXECUTABLE_NAME) 30 | CFBundleIconFile 31 | 32 | CFBundleIdentifier 33 | $(PRODUCT_BUNDLE_IDENTIFIER) 34 | CFBundleInfoDictionaryVersion 35 | 6.0 36 | CFBundleName 37 | $(PRODUCT_NAME) 38 | CFBundlePackageType 39 | APPL 40 | CFBundleShortVersionString 41 | 1.0 42 | CFBundleVersion 43 | 1 44 | LSMinimumSystemVersion 45 | $(MACOSX_DEPLOYMENT_TARGET) 46 | NSHumanReadableCopyright 47 | Copyright © 2017年 ShannonChen. All rights reserved. 48 | NSMainStoryboardFile 49 | Main 50 | NSPrincipalClass 51 | NSApplication 52 | 53 | 54 | -------------------------------------------------------------------------------- /VocalTextEdit/VocalTextEdit/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // VocalTextEdit 4 | // 5 | // Created by ShannonChen on 2017/1/28. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import Cocoa 10 | 11 | class ViewController: NSViewController { 12 | 13 | // MARK: Properties 14 | let speechSythesizer = NSSpeechSynthesizer() 15 | var contents: String? { 16 | get { 17 | return textView.string 18 | } 19 | set { 20 | textView.string = newValue 21 | } 22 | } 23 | 24 | 25 | @IBOutlet private var textView: NSTextView! 26 | 27 | 28 | // Button Actions 29 | @IBAction func speakButtonClicked(_ sender: NSButton) { 30 | if let contents = textView.string, !contents.isEmpty { 31 | speechSythesizer.startSpeaking(contents) 32 | } 33 | else { 34 | speechSythesizer.startSpeaking("The documents is empty") 35 | } 36 | } 37 | 38 | @IBAction func stopButtonClicked(_ sender: NSButton) { 39 | speechSythesizer.stopSpeaking() 40 | } 41 | 42 | 43 | } 44 | 45 | -------------------------------------------------------------------------------- /WorldTrotter/WorldTrotter.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /WorldTrotter/WorldTrotter/Assets.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 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /WorldTrotter/WorldTrotter/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 | -------------------------------------------------------------------------------- /WorldTrotter/WorldTrotter/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 | 38 | 39 | -------------------------------------------------------------------------------- /WorldTrotter/WorldTrotter/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // WorldTrotter 4 | // 5 | // Created by ShannonChen on 2017/2/5. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController { 12 | 13 | override func viewDidLoad() { 14 | super.viewDidLoad() 15 | 16 | let firstFrame = CGRect(x: 160, y: 240, width: 100, height: 150) 17 | let firstView = UIView.init(frame: firstFrame) 18 | firstView.backgroundColor = UIColor.blue 19 | view.addSubview(firstView) 20 | } 21 | 22 | 23 | 24 | } 25 | 26 | -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ShannonChenCHN/ASwiftTour/2a928dcecd095d9cbe320dafb3392bff4a41f6d0/iTahDoodle/iTahDoodle.xcodeproj/project.xcworkspace/xcuserdata/ShannonChen.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle.xcodeproj/xcuserdata/ShannonChen.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | iTahDoodle.xcscheme 8 | 9 | orderHint 10 | 0 11 | 12 | 13 | SuppressBuildableAutocreation 14 | 15 | 58F9457D1E3B873600D31A70 16 | 17 | primary 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle/Assets.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 | "info" : { 35 | "version" : 1, 36 | "author" : "xcode" 37 | } 38 | } -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle/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 | 38 | 39 | -------------------------------------------------------------------------------- /iTahDoodle/iTahDoodle/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // iTahDoodle 4 | // 5 | // Created by ShannonChen on 2017/1/27. 6 | // Copyright © 2017年 ShannonChen. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController, UITextFieldDelegate { 12 | 13 | // MARK: Properties 14 | @IBOutlet weak var itemTextField: UITextField! 15 | @IBOutlet weak var tableView: UITableView! 16 | @IBOutlet weak var addButton: UIButton! 17 | 18 | let todoList = TodoList() 19 | 20 | 21 | override func viewDidLoad() { 22 | super.viewDidLoad() 23 | 24 | tableView.dataSource = todoList 25 | tableView.delegate = todoList 26 | todoList.registerCell(for: tableView) 27 | 28 | itemTextField.delegate = self 29 | } 30 | 31 | func textFieldDidBeginEditing(_ textField: UITextField) { 32 | addButton.isEnabled = false 33 | } 34 | 35 | func textFieldShouldReturn(_ textField: UITextField) -> Bool { 36 | textField.resignFirstResponder() 37 | 38 | return true 39 | } 40 | 41 | func textFieldDidEndEditing(_ textField: UITextField) { 42 | 43 | 44 | addButton.isEnabled = !textField.text!.isEmpty 45 | } 46 | 47 | // MARK: Button Action 48 | @IBAction func addButtonPressed(_ sender: UIButton) { 49 | print("Add to-do item: \(itemTextField.text!)") 50 | 51 | guard let todo = itemTextField.text else { 52 | return 53 | } 54 | todoList.add(todo) 55 | 56 | tableView.reloadData() 57 | 58 | itemTextField.text = nil 59 | } 60 | 61 | } 62 | 63 | --------------------------------------------------------------------------------