├── Pod ├── Assets │ ├── .gitkeep │ ├── KZNAssets.xcassets │ │ ├── kzn_circle.imageset │ │ │ ├── circle.png │ │ │ ├── circle@2x.png │ │ │ └── Contents.json │ │ ├── kzn_circleFill.imageset │ │ │ ├── circleFill.png │ │ │ ├── circleFill@2x.png │ │ │ └── Contents.json │ │ ├── kzn_closeButton.imageset │ │ │ ├── closeButton.png │ │ │ ├── closeButton@2x.png │ │ │ └── Contents.json │ │ └── kzn_sliderHandler.imageset │ │ │ ├── sliderHandler.png │ │ │ ├── sliderHandler@2x.png │ │ │ └── Contents.json │ ├── KZNWorkspaceBlockCell.xib │ ├── KZNSocket_Input.xib │ ├── KZNSocket_Output.xib │ └── KZNNode.xib └── Classes │ ├── .gitkeep │ ├── Node │ ├── WithText │ │ ├── KZNNodeWithText.h │ │ └── KZNNodeWithText.m │ ├── WithSlider │ │ ├── KZNNodeWithSlider.h │ │ └── KZNNodeWithSlider.m │ └── KZNNode.h │ ├── Socket │ ├── KZNSocket+Internal.h │ ├── KZNSocket.h │ └── KZNSocket.m │ ├── Workspace │ ├── GridView │ │ └── KZNGridView.h │ └── KZNWorkspace.h │ └── NodeType │ ├── KZNNodeType.h │ └── KZNNodeType.m ├── Example ├── Pods │ ├── Target Support Files │ │ ├── Pods-KZNodes-dyci │ │ │ ├── Pods-KZNodes-dyci.xcconfig │ │ │ ├── Pods-KZNodes-dyci-prefix.pch │ │ │ ├── Pods-KZNodes-dyci-dummy.m │ │ │ └── Pods-KZNodes-dyci-Private.xcconfig │ │ ├── Pods-KZNodes-KZNodes │ │ │ ├── Pods-KZNodes-KZNodes.xcconfig │ │ │ ├── Pods-KZNodes-KZNodes-prefix.pch │ │ │ ├── Pods-KZNodes-KZNodes-dummy.m │ │ │ └── Pods-KZNodes-KZNodes-Private.xcconfig │ │ ├── Pods-KZNodes-KZPlayground │ │ │ ├── Pods-KZNodes-KZPlayground.xcconfig │ │ │ ├── Pods-KZNodes-KZPlayground-prefix.pch │ │ │ ├── Pods-KZNodes-KZPlayground-dummy.m │ │ │ └── Pods-KZNodes-KZPlayground-Private.xcconfig │ │ ├── Pods-KZNodes-NHBalancedFlowLayout │ │ │ ├── Pods-KZNodes-NHBalancedFlowLayout.xcconfig │ │ │ ├── Pods-KZNodes-NHBalancedFlowLayout-prefix.pch │ │ │ ├── Pods-KZNodes-NHBalancedFlowLayout-dummy.m │ │ │ └── Pods-KZNodes-NHBalancedFlowLayout-Private.xcconfig │ │ ├── Pods-KZNodes-RSSwizzle │ │ │ ├── Pods-KZNodes-RSSwizzle.xcconfig │ │ │ ├── Pods-KZNodes-RSSwizzle-prefix.pch │ │ │ ├── Pods-KZNodes-RSSwizzle-dummy.m │ │ │ └── Pods-KZNodes-RSSwizzle-Private.xcconfig │ │ └── Pods-KZNodes │ │ │ ├── Pods-KZNodes-dummy.m │ │ │ ├── Pods-KZNodes.debug.xcconfig │ │ │ ├── Pods-KZNodes.release.xcconfig │ │ │ ├── Pods-KZNodes-environment.h │ │ │ ├── Pods-KZNodes-resources.sh │ │ │ └── Pods-KZNodes-acknowledgements.markdown │ ├── Headers │ │ └── Public │ │ │ ├── KZNodes │ │ │ ├── KZNNode.h │ │ │ ├── KZNSocket.h │ │ │ ├── KZNNodeType.h │ │ │ ├── KZNWorkspace.h │ │ │ ├── KZNGridView.h │ │ │ ├── KZNNodeWithText.h │ │ │ ├── KZNSocket+Internal.h │ │ │ └── KZNNodeWithSlider.h │ │ │ ├── RSSwizzle │ │ │ └── RSSwizzle.h │ │ │ ├── KZPlayground │ │ │ ├── KZPComponent.h │ │ │ ├── KZPPlayground.h │ │ │ ├── KZPSnapshotView.h │ │ │ ├── KZPPlayground+Internal.h │ │ │ ├── KZPTimelineViewController.h │ │ │ ├── KZPActionComponent.h │ │ │ ├── KZPAnimatorComponent.h │ │ │ ├── KZPPresenterComponent.h │ │ │ ├── KZPPlaygroundViewController.h │ │ │ ├── KZPImagePickerComponent.h │ │ │ ├── KZPValueAdjustComponent.h │ │ │ ├── KZPPresenterInfoViewController.h │ │ │ ├── KZPSynchronizationComponent.h │ │ │ └── KZPImagePickerCollectionViewController.h │ │ │ ├── dyci │ │ │ ├── SFFileWatcher.h │ │ │ ├── NSSet+ClassesList.h │ │ │ ├── SFDynamicCodeInjection.h │ │ │ ├── NSObject+DyCInjection.h │ │ │ ├── SFFileWatcherDelegate.h │ │ │ ├── UINib+StoryBoardSupport.h │ │ │ ├── UIViewController+XIBSupport.h │ │ │ └── SFInjectionsNotificationsCenter.h │ │ │ └── NHBalancedFlowLayout │ │ │ ├── NHLinearPartition.h │ │ │ └── NHBalancedFlowLayout.h │ ├── KZPlayground │ │ ├── Pod │ │ │ ├── Classes │ │ │ │ ├── Components │ │ │ │ │ ├── KZPComponent.h │ │ │ │ │ ├── KZPSnapshotView.h │ │ │ │ │ ├── Presenter │ │ │ │ │ │ ├── KZPPresenterInfoViewController.h │ │ │ │ │ │ ├── KZPPresenterInfoViewController.m │ │ │ │ │ │ ├── KZPPresenterComponent.h │ │ │ │ │ │ └── KZPPresenterComponent.m │ │ │ │ │ ├── Controls │ │ │ │ │ │ ├── Action │ │ │ │ │ │ │ ├── KZPActionComponent.h │ │ │ │ │ │ │ └── KZPActionComponent.m │ │ │ │ │ │ └── ValueAdjust │ │ │ │ │ │ │ ├── KZPValueAdjustComponent.h │ │ │ │ │ │ │ └── KZPValueAdjustComponent.m │ │ │ │ │ ├── Images │ │ │ │ │ │ └── ImagePicker │ │ │ │ │ │ │ ├── AssetBrowser │ │ │ │ │ │ │ ├── KZPImagePickerCollectionViewController.h │ │ │ │ │ │ │ └── KZPImagePickerCollectionViewController.m │ │ │ │ │ │ │ ├── KZPImagePickerComponent.h │ │ │ │ │ │ │ └── KZPImagePickerComponent.m │ │ │ │ │ ├── Synchronization │ │ │ │ │ │ ├── KZPSynchronizationComponent.h │ │ │ │ │ │ └── KZPSynchronizationComponent.m │ │ │ │ │ └── Animation │ │ │ │ │ │ ├── KZPAnimatorComponent.h │ │ │ │ │ │ └── KZPAnimatorComponent.m │ │ │ │ ├── Playground │ │ │ │ │ ├── KZPPlayground+Internal.h │ │ │ │ │ ├── KZPPlaygroundViewController.h │ │ │ │ │ ├── KZPPlayground.h │ │ │ │ │ ├── KZPPlayground.m │ │ │ │ │ └── KZPPlaygroundViewController.m │ │ │ │ └── Timeline │ │ │ │ │ ├── KZPTimelineViewController.h │ │ │ │ │ └── KZPTimelineViewController.m │ │ │ └── Assets │ │ │ │ └── KZPPresenterInfoViewController.xib │ │ └── LICENSE │ ├── dyci │ │ ├── Dynamic Code Injection │ │ │ └── dyci │ │ │ │ └── Classes │ │ │ │ ├── SFDynamicCodeInjection.h │ │ │ │ ├── Categories │ │ │ │ ├── NSSet+ClassesList.h │ │ │ │ └── NSSet+ClassesList.m │ │ │ │ ├── Injections │ │ │ │ ├── UINib+StoryBoardSupport.h │ │ │ │ ├── UIViewController+XIBSupport.h │ │ │ │ ├── UINib+StoryBoardSupport.m │ │ │ │ ├── NSObject+DyCInjection.h │ │ │ │ ├── NSObject+DyCInjection.m │ │ │ │ └── UIViewController+XIBSupport.m │ │ │ │ ├── FileWatcher │ │ │ │ ├── SFFileWatcherDelegate.h │ │ │ │ ├── SFFileWatcher.h │ │ │ │ └── SFFileWatcher.m │ │ │ │ └── Notifications │ │ │ │ ├── SFInjectionsNotificationsCenter.h │ │ │ │ └── SFInjectionsNotificationsCenter.m │ │ ├── LICENSE.md │ │ └── README.md │ ├── Manifest.lock │ ├── NHBalancedFlowLayout │ │ ├── NHBalancedFlowLayout │ │ │ ├── NHLinearPartition.h │ │ │ ├── NHBalancedFlowLayout.h │ │ │ └── NHLinearPartition.m │ │ ├── LICENSE │ │ └── README.md │ ├── Local Podspecs │ │ └── KZNodes.podspec │ └── RSSwizzle │ │ ├── LICENSE │ │ └── README.md ├── KZNodes │ ├── en.lproj │ │ └── InfoPlist.strings │ ├── LocalAssets.xcassets │ │ ├── kzn_circle.imageset │ │ │ ├── circle.png │ │ │ ├── circle@2x.png │ │ │ └── Contents.json │ │ ├── kzn_circleFill.imageset │ │ │ ├── circleFill.png │ │ │ ├── circleFill@2x.png │ │ │ └── Contents.json │ │ ├── kzn_closeButton.imageset │ │ │ ├── closeButton.png │ │ │ ├── closeButton@2x.png │ │ │ └── Contents.json │ │ └── kzn_sliderHandler.imageset │ │ │ ├── sliderHandler.png │ │ │ ├── sliderHandler@2x.png │ │ │ └── Contents.json │ ├── KZPlaygroundExample.h │ ├── KZNAppDelegate.h │ ├── KZNodes-Prefix.pch │ ├── main.m │ ├── Images.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ └── LaunchImage.launchimage │ │ │ └── Contents.json │ ├── KZNodes-Info.plist │ └── KZNAppDelegate.m ├── avatar.jpg ├── Podfile ├── KZNodes.xcodeproj │ ├── project.xcworkspace │ │ └── contents.xcworkspacedata │ └── xcshareddata │ │ └── xcschemes │ │ └── KZNodes.xcscheme ├── KZNodes.xcworkspace │ └── contents.xcworkspacedata ├── .kick └── Podfile.lock ├── Screenshots ├── slider.png ├── coreimage.gif ├── textfield.png └── transforms.gif ├── .travis.yml ├── .gitignore ├── KZNodes.podspec ├── LICENSE └── README.md /Pod/Assets/.gitkeep: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Pod/Classes/.gitkeep: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-dyci/Pods-KZNodes-dyci.xcconfig: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNNode.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Node/KZNNode.h -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZNodes/Pods-KZNodes-KZNodes.xcconfig: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNSocket.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Socket/KZNSocket.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/RSSwizzle/RSSwizzle.h: -------------------------------------------------------------------------------- 1 | ../../../RSSwizzle/RSSwizzle/RSSwizzle.h -------------------------------------------------------------------------------- /Example/KZNodes/en.lproj/InfoPlist.strings: -------------------------------------------------------------------------------- 1 | /* Localized versions of Info.plist keys */ 2 | 3 | -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNNodeType.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/NodeType/KZNNodeType.h -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZPlayground/Pods-KZNodes-KZPlayground.xcconfig: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Example/avatar.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/avatar.jpg -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNWorkspace.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Workspace/KZNWorkspace.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNGridView.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Workspace/GridView/KZNGridView.h -------------------------------------------------------------------------------- /Screenshots/slider.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Screenshots/slider.png -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNNodeWithText.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Node/WithText/KZNNodeWithText.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNSocket+Internal.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Socket/KZNSocket+Internal.h -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-NHBalancedFlowLayout/Pods-KZNodes-NHBalancedFlowLayout.xcconfig: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Screenshots/coreimage.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Screenshots/coreimage.gif -------------------------------------------------------------------------------- /Screenshots/textfield.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Screenshots/textfield.png -------------------------------------------------------------------------------- /Screenshots/transforms.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Screenshots/transforms.gif -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZNodes/KZNNodeWithSlider.h: -------------------------------------------------------------------------------- 1 | ../../../../../Pod/Classes/Node/WithSlider/KZNNodeWithSlider.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/KZPComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPPlayground.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Playground/KZPPlayground.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPSnapshotView.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/KZPSnapshotView.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/SFFileWatcher.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/FileWatcher/SFFileWatcher.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/NSSet+ClassesList.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/Categories/NSSet+ClassesList.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/SFDynamicCodeInjection.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/SFDynamicCodeInjection.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPPlayground+Internal.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Playground/KZPPlayground+Internal.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPTimelineViewController.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Timeline/KZPTimelineViewController.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/NHBalancedFlowLayout/NHLinearPartition.h: -------------------------------------------------------------------------------- 1 | ../../../NHBalancedFlowLayout/NHBalancedFlowLayout/NHLinearPartition.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPActionComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Controls/Action/KZPActionComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPAnimatorComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Animation/KZPAnimatorComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPPresenterComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/NSObject+DyCInjection.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/Injections/NSObject+DyCInjection.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/SFFileWatcherDelegate.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/FileWatcher/SFFileWatcherDelegate.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPPlaygroundViewController.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Playground/KZPPlaygroundViewController.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/NHBalancedFlowLayout/NHBalancedFlowLayout.h: -------------------------------------------------------------------------------- 1 | ../../../NHBalancedFlowLayout/NHBalancedFlowLayout/NHBalancedFlowLayout.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/UINib+StoryBoardSupport.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/Injections/UINib+StoryBoardSupport.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/UIViewController+XIBSupport.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/Injections/UIViewController+XIBSupport.h -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-RSSwizzle/Pods-KZNodes-RSSwizzle.xcconfig: -------------------------------------------------------------------------------- 1 | PODS_KZNODES_RSSWIZZLE_OTHER_LDFLAGS = -framework "Foundation" -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPImagePickerComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Images/ImagePicker/KZPImagePickerComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPValueAdjustComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Controls/ValueAdjust/KZPValueAdjustComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPPresenterInfoViewController.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterInfoViewController.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPSynchronizationComponent.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Synchronization/KZPSynchronizationComponent.h -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/dyci/SFInjectionsNotificationsCenter.h: -------------------------------------------------------------------------------- 1 | ../../../dyci/Dynamic Code Injection/dyci/Classes/Notifications/SFInjectionsNotificationsCenter.h -------------------------------------------------------------------------------- /Example/Podfile: -------------------------------------------------------------------------------- 1 | source 'https://github.com/CocoaPods/Specs.git' 2 | 3 | target 'KZNodes', :exclusive => true do 4 | pod "KZNodes", :path => "../" 5 | pod "KZPlayground" 6 | end -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circle.imageset/circle.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_circle.imageset/circle.png -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circle.imageset/circle@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_circle.imageset/circle@2x.png -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZNodes/Pods-KZNodes-KZNodes-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #endif 4 | 5 | #import "Pods-KZNodes-environment.h" 6 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-dyci/Pods-KZNodes-dyci-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #endif 4 | 5 | #import "Pods-KZNodes-environment.h" 6 | 7 | -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circle.imageset/circle.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_circle.imageset/circle.png -------------------------------------------------------------------------------- /Example/Pods/Headers/Public/KZPlayground/KZPImagePickerCollectionViewController.h: -------------------------------------------------------------------------------- 1 | ../../../KZPlayground/Pod/Classes/Components/Images/ImagePicker/AssetBrowser/KZPImagePickerCollectionViewController.h -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-RSSwizzle/Pods-KZNodes-RSSwizzle-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #endif 4 | 5 | #import "Pods-KZNodes-environment.h" 6 | -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circleFill.imageset/circleFill.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_circleFill.imageset/circleFill.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circle.imageset/circle@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_circle.imageset/circle@2x.png -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZPlayground/Pods-KZNodes-KZPlayground-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #endif 4 | 5 | #import "Pods-KZNodes-environment.h" 6 | -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circleFill.imageset/circleFill@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_circleFill.imageset/circleFill@2x.png -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_closeButton.imageset/closeButton.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_closeButton.imageset/closeButton.png -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_closeButton.imageset/closeButton@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_closeButton.imageset/closeButton@2x.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circleFill.imageset/circleFill.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_circleFill.imageset/circleFill.png -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circleFill.imageset/circleFill@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_circleFill.imageset/circleFill@2x.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_closeButton.imageset/closeButton.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_closeButton.imageset/closeButton.png -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-NHBalancedFlowLayout/Pods-KZNodes-NHBalancedFlowLayout-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #endif 4 | 5 | #import "Pods-KZNodes-environment.h" 6 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes 5 | @end 6 | -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Pod/Assets/KZNAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler@2x.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_closeButton.imageset/closeButton@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_closeButton.imageset/closeButton@2x.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler.png -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/krzysztofzablocki/KZNodes/HEAD/Example/KZNodes/LocalAssets.xcassets/kzn_sliderHandler.imageset/sliderHandler@2x.png -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-dyci/Pods-KZNodes-dyci-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes_dyci : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes_dyci 5 | @end 6 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZNodes/Pods-KZNodes-KZNodes-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes_KZNodes : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes_KZNodes 5 | @end 6 | -------------------------------------------------------------------------------- /Example/KZNodes.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-RSSwizzle/Pods-KZNodes-RSSwizzle-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes_RSSwizzle : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes_RSSwizzle 5 | @end 6 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZPlayground/Pods-KZNodes-KZPlayground-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes_KZPlayground : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes_KZPlayground 5 | @end 6 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | # reference: http://www.objc.io/issue-6/travis-ci.html 2 | 3 | language: objective-c 4 | # before_install: cd Example && pod install && cd - 5 | script: 6 | - xctool test -workspace Example/KZNodes.xcworkspace -scheme KZNodes -sdk iphonesimulator ONLY_ACTIVE_ARCH=NO 7 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/KZPComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | 10 | @protocol KZPComponent 11 | @required 12 | + (void)reset; 13 | @end -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-NHBalancedFlowLayout/Pods-KZNodes-NHBalancedFlowLayout-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_KZNodes_NHBalancedFlowLayout : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_KZNodes_NHBalancedFlowLayout 5 | @end 6 | -------------------------------------------------------------------------------- /Example/KZNodes.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /Pod/Classes/Node/WithText/KZNNodeWithText.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZNNode.h" 12 | 13 | 14 | @interface KZNNodeWithText : KZNNode 15 | @property(nonatomic, weak) IBOutlet UITextField *textField; 16 | 17 | @end 18 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/KZPSnapshotView.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | 10 | @protocol KZPSnapshotView 11 | @required 12 | - (BOOL)hasExtraInformation; 13 | - (UIViewController*)extraInfoController; 14 | @end -------------------------------------------------------------------------------- /Pod/Classes/Node/WithSlider/KZNNodeWithSlider.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZNNode.h" 12 | 13 | 14 | @interface KZNNodeWithSlider : KZNNode 15 | @property(nonatomic, weak) IBOutlet UISlider *slider; 16 | - (void)forceLabelUpdate; 17 | @end 18 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Playground/KZPPlayground+Internal.h: -------------------------------------------------------------------------------- 1 | #import "KZPPlayground.h" 2 | 3 | @interface KZPPlayground (Internal) 4 | @property(nonatomic, weak, readwrite) UIView *worksheetView; 5 | @property(nonatomic, weak, readwrite) UIViewController *viewController; 6 | @property(nonatomic, weak, readwrite) KZPPlaygroundViewController *playgroundViewController; 7 | @end -------------------------------------------------------------------------------- /Example/KZNodes/KZPlaygroundExample.h: -------------------------------------------------------------------------------- 1 | // 2 | // KZPlaygroundExample.h 3 | // KZPPlaygroundHelper 4 | // 5 | // Created by Krzysztof Zabłocki on 19/10/2014. 6 | // Copyright (c) 2014 pixle. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "KZPPlayground.h" 11 | 12 | @interface KZPlaygroundExample : KZPPlayground 13 | @end 14 | 15 | -------------------------------------------------------------------------------- /Example/KZNodes/KZNAppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // KZNAppDelegate.h 3 | // KZNodes 4 | // 5 | // Created by CocoaPods on 10/30/2014. 6 | // Copyright (c) 2014 Krzysztof Zablocki. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface KZNAppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow *window; 14 | 15 | @end 16 | -------------------------------------------------------------------------------- /Pod/Classes/Socket/KZNSocket+Internal.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | 10 | #import "KZNSocket.h" 11 | 12 | @interface KZNSocket () 13 | @property(nonatomic, weak, readwrite) KZNNode *parent; 14 | @property(nonatomic, strong, readwrite) NSMutableSet *connections; 15 | @property(nonatomic) CGFloat extraSpace; 16 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Playground/KZPPlaygroundViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 19/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | @interface KZPPlaygroundViewController : UIViewController 12 | @property(nonatomic, assign) BOOL timelineHidden; 13 | 14 | + (instancetype)playgroundViewController; 15 | 16 | @end 17 | -------------------------------------------------------------------------------- /Example/KZNodes/KZNodes-Prefix.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Prefix header 3 | // 4 | // The contents of this file are implicitly included at the beginning of every source file. 5 | // 6 | 7 | #import 8 | 9 | #ifndef __IPHONE_5_0 10 | #warning "This project uses features only available in iOS SDK 5.0 and later." 11 | #endif 12 | 13 | #ifdef __OBJC__ 14 | #import 15 | #import 16 | #endif 17 | -------------------------------------------------------------------------------- /Example/KZNodes/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // KZNodes 4 | // 5 | // Created by Krzysztof Zablocki on 10/30/2014. 6 | // Copyright (c) 2014 Krzysztof Zablocki. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | #import "KZNAppDelegate.h" 12 | 13 | int main(int argc, char * argv[]) 14 | { 15 | @autoreleasepool { 16 | return UIApplicationMain(argc, argv, nil, NSStringFromClass([KZNAppDelegate class])); 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterInfoViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // KZPPresenterInfoViewController.h 3 | // Playground 4 | // 5 | // Created by Krzysztof Zabłocki on 21/10/2014. 6 | // Copyright (c) 2014 pixle. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface KZPPresenterInfoViewController : UIViewController 12 | - (void)setFromImage:(UIImage *)image title:(NSString *)title; 13 | @end 14 | -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circle.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "circle.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "circle@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circle.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "circle.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "circle@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/SFDynamicCodeInjection.h: -------------------------------------------------------------------------------- 1 | // 2 | // SFDynamicCodeInjection 3 | // Nemlig-iPad 4 | // 5 | // Created by Paul Taykalo on 10/7/12. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import 9 | 10 | @interface SFDynamicCodeInjection : NSObject 11 | 12 | /* 13 | Enables dynamic runtime 14 | */ 15 | + (void)enable; 16 | 17 | /* 18 | Disables dynamic runtime 19 | */ 20 | + (void)disable; 21 | 22 | 23 | @end -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_circleFill.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "circleFill.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "circleFill@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_closeButton.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "closeButton.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "closeButton@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_circleFill.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "circleFill.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "circleFill@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Controls/Action/KZPActionComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | 10 | #import "KZPComponent.h" 11 | 12 | extern void __attribute__((overloadable)) KZPAction(NSString *name, void (^block)(void)); 13 | 14 | @interface KZPActionComponent : NSObject 15 | + (void)addCallToActionWithName:(NSString *)name block:(void (^)())block; 16 | @end -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_closeButton.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "closeButton.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "closeButton@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Images/ImagePicker/AssetBrowser/KZPImagePickerCollectionViewController.h: -------------------------------------------------------------------------------- 1 | 2 | @import Foundation; 3 | @import UIKit; 4 | 5 | @interface KZPImagePickerCollectionViewCell : UICollectionViewCell 6 | @property(nonatomic, weak) UIImageView *imageView; 7 | @property(nonatomic, weak) UILabel *titleLabel; 8 | @end 9 | 10 | @interface KZPImagePickerCollectionViewController : UICollectionViewController 11 | @property(nonatomic, copy) void (^onSelectionBlock)(UIImage *); 12 | @end -------------------------------------------------------------------------------- /Pod/Assets/KZNAssets.xcassets/kzn_sliderHandler.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "sliderHandler.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "sliderHandler@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/KZNodes/LocalAssets.xcassets/kzn_sliderHandler.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "scale" : "1x", 6 | "filename" : "sliderHandler.png" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "scale" : "2x", 11 | "filename" : "sliderHandler@2x.png" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "scale" : "3x" 16 | } 17 | ], 18 | "info" : { 19 | "version" : 1, 20 | "author" : "xcode" 21 | } 22 | } -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-dyci/Pods-KZNodes-dyci-Private.xcconfig: -------------------------------------------------------------------------------- 1 | #include "Pods-KZNodes-dyci.xcconfig" 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Build" "${PODS_ROOT}/Headers/Build/dyci" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC 5 | PODS_ROOT = ${SRCROOT} -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZNodes/Pods-KZNodes-KZNodes-Private.xcconfig: -------------------------------------------------------------------------------- 1 | #include "Pods-KZNodes-KZNodes.xcconfig" 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Build" "${PODS_ROOT}/Headers/Build/KZNodes" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC 5 | PODS_ROOT = ${SRCROOT} -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Categories/NSSet+ClassesList.h: -------------------------------------------------------------------------------- 1 | // 2 | // NSSet+ClassesList(Classes) 3 | // Dynamic Code Injection 4 | // 5 | // Created by Paul Taykalo on 10/21/12. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import 9 | 10 | 11 | #if TARGET_IPHONE_SIMULATOR 12 | 13 | @interface NSSet (ClassesList) 14 | 15 | /* 16 | Returns set of currently registered classes, wrapped with NSValue 17 | */ 18 | + (NSMutableSet *)currentClassesSet; 19 | 20 | 21 | @end 22 | 23 | #endif -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-KZPlayground/Pods-KZNodes-KZPlayground-Private.xcconfig: -------------------------------------------------------------------------------- 1 | #include "Pods-KZNodes-KZPlayground.xcconfig" 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Build" "${PODS_ROOT}/Headers/Build/KZPlayground" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC 5 | PODS_ROOT = ${SRCROOT} -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-RSSwizzle/Pods-KZNodes-RSSwizzle-Private.xcconfig: -------------------------------------------------------------------------------- 1 | #include "Pods-KZNodes-RSSwizzle.xcconfig" 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Build" "${PODS_ROOT}/Headers/Build/RSSwizzle" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = ${PODS_KZNODES_RSSWIZZLE_OTHER_LDFLAGS} -ObjC 5 | PODS_ROOT = ${SRCROOT} -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes-NHBalancedFlowLayout/Pods-KZNodes-NHBalancedFlowLayout-Private.xcconfig: -------------------------------------------------------------------------------- 1 | #include "Pods-KZNodes-NHBalancedFlowLayout.xcconfig" 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Build" "${PODS_ROOT}/Headers/Build/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC 5 | PODS_ROOT = ${SRCROOT} -------------------------------------------------------------------------------- /Pod/Classes/Workspace/GridView/KZNGridView.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | @class KZNSocket; 11 | @class KZNNode; 12 | @class KZNWorkspace; 13 | 14 | @interface KZNGridView : UIView 15 | @property(nonatomic, assign) CGPoint offset; 16 | @property(nonatomic, weak) KZNWorkspace *workspace; 17 | 18 | - (void)updateConnections; 19 | 20 | - (void)prepareConnectionLayerForSocket:(KZNSocket *)socket; 21 | 22 | - (void)addNode:(KZNNode *)node; 23 | 24 | - (void)removeNode:(KZNNode *)node; 25 | 26 | - (void)clearConnectionLayerForSocket:(KZNSocket *)inputSocket; 27 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Synchronization/KZPSynchronizationComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 25/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZPComponent.h" 12 | 13 | void KZPWaitForEvaluation(id (^valueGetter)(), void (^completion)(id)); 14 | 15 | #define KZPWhenSet(value, completion) KZPWaitForEvaluation(^{return value;}, completion) 16 | 17 | @interface KZPSynchronizationComponent : NSObject 18 | + (void)addComponentWithGetter:(id (^)())valueGetter completion:(void (^)(id))completion; 19 | 20 | - (BOOL)evaluate; 21 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Timeline/KZPTimelineViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 19/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZPPlaygroundViewController.h" 12 | 13 | @interface KZPTimelineViewController : UIViewController 14 | + (KZPTimelineViewController *)sharedInstance; 15 | 16 | + (void)setSharedInstance:(KZPTimelineViewController *)sharedInstance; 17 | 18 | - (void)playgroundDidRun; 19 | - (void)playgroundSetupCompleted; 20 | 21 | - (CGFloat)maxWidthForSnapshotView; 22 | 23 | - (void)reset; 24 | 25 | - (void)addView:(UIView *)view; 26 | 27 | @end -------------------------------------------------------------------------------- /Example/.kick: -------------------------------------------------------------------------------- 1 | recipe :ruby 2 | Kicker::Recipes::Ruby.runner_bin = 'bacon -q' 3 | 4 | process do |potential_files| 5 | files = potential_files.take_and_map do |file| 6 | if file =~ %r{^.*\.(m|xib|strings)$} 7 | execute("/usr/bin/python #{File.expand_path("~/.dyci/scripts/dyci-recompile.py")} #{File.expand_path(file)}") 8 | puts "KZPlayground: Recompiled #{file}" 9 | file 10 | end 11 | end 12 | end 13 | 14 | process do |remaining_files| 15 | remaining_files.take_and_map do |file| 16 | puts "KZPlayground: Ignored #{file}" 17 | file 18 | end 19 | end 20 | 21 | startup do 22 | log "KZPlayground: Watching for file changes!" 23 | end 24 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Images/ImagePicker/KZPImagePickerComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | 10 | #import "KZPComponent.h" 11 | 12 | @class KZPPresenterComponent; 13 | 14 | extern void __attribute__((overloadable)) KZPAdjust(NSString *name, void (^block)(UIImage *)); 15 | #define KZPAdjustImage(name) __block UIImage *name = nil; KZPAdjust(@#name, ^(UIImage* value) { name = value; }) 16 | 17 | @interface KZPImagePickerComponent : NSObject 18 | + (void)addImagePickerWithName:(NSString *)name block:(void (^)(UIImage *))block; 19 | @end -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/UINib+StoryBoardSupport.h: -------------------------------------------------------------------------------- 1 | // 2 | // UINib(StoryBoardSupport) 3 | // dyci 4 | // 5 | // Created by Paul Taykalo on 5/27/13. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import 9 | #import 10 | 11 | 12 | #if TARGET_IPHONE_SIMULATOR 13 | 14 | /* 15 | It seems that storyboard passing some options, when instantiating the nibs 16 | So, we would save those, and reuse after injections 17 | */ 18 | @interface UINib (StoryBoardSupport) 19 | 20 | 21 | /* 22 | Returns options, saved for the owner 23 | */ 24 | + (NSDictionary *)optionsByOwner:(id)owner; 25 | 26 | @end 27 | 28 | #endif -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/FileWatcher/SFFileWatcherDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SFFileWatcherDelegate.h 3 | // Dynamic Code Injection 4 | // 5 | // Created by adenisov on 16.10.12. 6 | // Copyright (c) 2012 Stanfy. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | 12 | #if TARGET_IPHONE_SIMULATOR 13 | 14 | /* 15 | Object that get notified by SFFileWatcher, when some files are changed in the 16 | some directory 17 | */ 18 | @protocol SFFileWatcherDelegate 19 | 20 | @optional 21 | 22 | /* 23 | This method will be called each time, when something changes in watching directory 24 | */ 25 | - (void)newFileWasFoundAtPath:(NSString *)filePath; 26 | 27 | @end 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # OS X 2 | .DS_Store 3 | 4 | # Xcode 5 | build/ 6 | *.pbxuser 7 | !default.pbxuser 8 | *.mode1v3 9 | !default.mode1v3 10 | *.mode2v3 11 | !default.mode2v3 12 | *.perspectivev3 13 | !default.perspectivev3 14 | xcuserdata 15 | *.xccheckout 16 | profile 17 | *.moved-aside 18 | DerivedData 19 | *.hmap 20 | *.ipa 21 | 22 | # Bundler 23 | .bundle 24 | 25 | # We recommend against adding the Pods directory to your .gitignore. However 26 | # you should judge for yourself, the pros and cons are mentioned at: 27 | # http://guides.cocoapods.org/using/using-cocoapods.html#should-i-ignore-the-pods-directory-in-source-control 28 | # 29 | # Note: if you ignore the Pods directory, make sure to uncomment 30 | # `pod install` in .travis.yml 31 | # 32 | # Pods/ 33 | -------------------------------------------------------------------------------- /Pod/Classes/Workspace/KZNWorkspace.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | @class KZNNode; 11 | @class KZNSocket; 12 | 13 | @interface KZNWorkspace : UIView 14 | @property(nonatomic, weak, readonly) IBOutlet UIView *previewView; 15 | 16 | + (instancetype)workspaceWithBounds:(CGRect)bounds; 17 | 18 | - (void)addNode:(KZNNode *)node; 19 | 20 | - (void)removeNode:(KZNNode *)node; 21 | 22 | - (void)pressedSocket:(KZNSocket *)socket; 23 | 24 | - (void)breakConnectionFromSocket:(KZNSocket *)outputSocket toSocket:(KZNSocket *)inputSocket; 25 | 26 | - (void)evaluate; 27 | - (NSArray*)arrayWithNodesComposition; 28 | - (void)restoreNodesCompositionFrom:(NSArray*)serializedObjects removeNodesFromGrid:(BOOL)removeNodes; 29 | @end 30 | -------------------------------------------------------------------------------- /Example/Podfile.lock: -------------------------------------------------------------------------------- 1 | PODS: 2 | - dyci (0.1.5.6): 3 | - dyci/Injections 4 | - dyci/Injections (0.1.5.6) 5 | - KZNodes (0.1.0) 6 | - KZPlayground (0.3.2): 7 | - dyci (~> 0.1.5.6) 8 | - NHBalancedFlowLayout (~> 0.2) 9 | - RSSwizzle (~> 0.1.0) 10 | - NHBalancedFlowLayout (0.2) 11 | - RSSwizzle (0.1.0) 12 | 13 | DEPENDENCIES: 14 | - KZNodes (from `../`) 15 | - KZPlayground 16 | 17 | EXTERNAL SOURCES: 18 | KZNodes: 19 | :path: ../ 20 | 21 | SPEC CHECKSUMS: 22 | dyci: 86668b266b8a281cb6db02843150f6a210c34ee9 23 | KZNodes: 84017d4b2532b4cc46cf11b820452a80ff4af084 24 | KZPlayground: 06275e2fd015b4207b74df627ac2b725b2222338 25 | NHBalancedFlowLayout: be3c297b54f74c27607aaa04563270ecbd2d8e38 26 | RSSwizzle: ab39962b7ec56d19c2318ec1127e253797121363 27 | 28 | COCOAPODS: 0.34.4 29 | -------------------------------------------------------------------------------- /Example/Pods/Manifest.lock: -------------------------------------------------------------------------------- 1 | PODS: 2 | - dyci (0.1.5.6): 3 | - dyci/Injections 4 | - dyci/Injections (0.1.5.6) 5 | - KZNodes (0.1.0) 6 | - KZPlayground (0.3.2): 7 | - dyci (~> 0.1.5.6) 8 | - NHBalancedFlowLayout (~> 0.2) 9 | - RSSwizzle (~> 0.1.0) 10 | - NHBalancedFlowLayout (0.2) 11 | - RSSwizzle (0.1.0) 12 | 13 | DEPENDENCIES: 14 | - KZNodes (from `../`) 15 | - KZPlayground 16 | 17 | EXTERNAL SOURCES: 18 | KZNodes: 19 | :path: ../ 20 | 21 | SPEC CHECKSUMS: 22 | dyci: 86668b266b8a281cb6db02843150f6a210c34ee9 23 | KZNodes: 84017d4b2532b4cc46cf11b820452a80ff4af084 24 | KZPlayground: 06275e2fd015b4207b74df627ac2b725b2222338 25 | NHBalancedFlowLayout: be3c297b54f74c27607aaa04563270ecbd2d8e38 26 | RSSwizzle: ab39962b7ec56d19c2318ec1127e253797121363 27 | 28 | COCOAPODS: 0.34.4 29 | -------------------------------------------------------------------------------- /Example/Pods/NHBalancedFlowLayout/NHBalancedFlowLayout/NHLinearPartition.h: -------------------------------------------------------------------------------- 1 | // 2 | // LinearPartition.h 3 | // BalancedFlowLayout 4 | // 5 | // Created by Niels de Hoog on 08-10-13. 6 | // Copyright (c) 2013 Niels de Hoog. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | /** 12 | * Partitions a sequence of non-negative integers into the required number of partitions. 13 | * Based on implementation in Python by Óscar López: http://stackoverflow.com/a/7942946 14 | * Example: [LinearPartition linearPartitionForSequence:@[9,2,6,3,8,5,8,1,7,3,4] numberOfPartitions:3] => @[@[9,2,6,3],@[8,5,8],@[1,7,3,4]] 15 | */ 16 | @interface NHLinearPartition : NSObject 17 | 18 | + (NSArray *)linearPartitionForSequence:(NSArray *)sequence numberOfPartitions:(NSInteger)numberOfPartitions; 19 | 20 | @end 21 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes.debug.xcconfig: -------------------------------------------------------------------------------- 1 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 2 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 3 | OTHER_CFLAGS = $(inherited) -isystem "${PODS_ROOT}/Headers/Public" -isystem "${PODS_ROOT}/Headers/Public/KZNodes" -isystem "${PODS_ROOT}/Headers/Public/KZPlayground" -isystem "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" -isystem "${PODS_ROOT}/Headers/Public/RSSwizzle" -isystem "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC -l"Pods-KZNodes-KZNodes" -l"Pods-KZNodes-KZPlayground" -l"Pods-KZNodes-NHBalancedFlowLayout" -l"Pods-KZNodes-RSSwizzle" -l"Pods-KZNodes-dyci" -framework "Foundation" 5 | OTHER_LIBTOOLFLAGS = $(OTHER_LDFLAGS) 6 | PODS_ROOT = ${SRCROOT}/Pods -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes.release.xcconfig: -------------------------------------------------------------------------------- 1 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 2 | HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/KZNodes" "${PODS_ROOT}/Headers/Public/KZPlayground" "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" "${PODS_ROOT}/Headers/Public/RSSwizzle" "${PODS_ROOT}/Headers/Public/dyci" 3 | OTHER_CFLAGS = $(inherited) -isystem "${PODS_ROOT}/Headers/Public" -isystem "${PODS_ROOT}/Headers/Public/KZNodes" -isystem "${PODS_ROOT}/Headers/Public/KZPlayground" -isystem "${PODS_ROOT}/Headers/Public/NHBalancedFlowLayout" -isystem "${PODS_ROOT}/Headers/Public/RSSwizzle" -isystem "${PODS_ROOT}/Headers/Public/dyci" 4 | OTHER_LDFLAGS = -ObjC -l"Pods-KZNodes-KZNodes" -l"Pods-KZNodes-KZPlayground" -l"Pods-KZNodes-NHBalancedFlowLayout" -l"Pods-KZNodes-RSSwizzle" -l"Pods-KZNodes-dyci" -framework "Foundation" 5 | OTHER_LIBTOOLFLAGS = $(OTHER_LDFLAGS) 6 | PODS_ROOT = ${SRCROOT}/Pods -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/UIViewController+XIBSupport.h: -------------------------------------------------------------------------------- 1 | // 2 | // UIViewController+XIBSupport.h 3 | // Dynamic Code Ibjection 4 | // 5 | // Created by Paul Taykalo on 11/30/12. 6 | // Copyright (c) 2012 Stanfy. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | 12 | #if TARGET_IPHONE_SIMULATOR 13 | 14 | /* 15 | This category allows Xibs to be injected in runtime 16 | */ 17 | @interface UIViewController (XIBSupport) 18 | 19 | /* 20 | Overriden updateOnResource Injection 21 | this method will check, if injected path is same as our xib, 22 | And will reinitialize xib with new nib instance 23 | 24 | This functionality is experimental. So, in case if it isn't working, 25 | describe the steps, and setup and issue on the Github 26 | https://github.com/DyCI/dyci-main/issues?sort=updated&state=open 27 | */ 28 | - (void)updateOnResourceInjection:(NSString *)path; 29 | 30 | @end 31 | 32 | #endif 33 | -------------------------------------------------------------------------------- /KZNodes.podspec: -------------------------------------------------------------------------------- 1 | Pod::Spec.new do |s| 2 | s.name = "KZNodes" 3 | s.version = "0.1.2" 4 | s.summary = "Framework for building visual workflow editors eg. Origami." 5 | s.description = <<-DESC 6 | Have you ever wondered how you could create an editor like Origami? 7 | With KZNodes you can do that in a manner of minutes. 8 | DESC 9 | s.homepage = "https://github.com/krzysztofzablocki/KZNodes" 10 | s.license = 'MIT' 11 | s.author = { "Krzysztof Zablocki" => "krzysztof.zablocki@me.com" } 12 | s.source = { :git => "https://github.com/krzysztofzablocki/KZNodes.git", :tag => s.version.to_s } 13 | s.social_media_url = 'https://twitter.com/merowing_' 14 | 15 | s.platform = :ios, '7.0' 16 | s.requires_arc = true 17 | 18 | s.source_files = 'Pod/Classes/**/*.h', 'Pod/Classes/**/*.m' 19 | s.resources = ['Pod/Assets/*'] 20 | end 21 | -------------------------------------------------------------------------------- /Example/Pods/Local Podspecs/KZNodes.podspec: -------------------------------------------------------------------------------- 1 | Pod::Spec.new do |s| 2 | s.name = "KZNodes" 3 | s.version = "0.1.0" 4 | s.summary = "Framework for building visual workflow editors eg. Origami." 5 | s.description = <<-DESC 6 | Have you ever wondered how you could create an editor like Origami? 7 | With KZNodes you can do that in a manner of minutes. 8 | DESC 9 | s.homepage = "https://github.com/krzysztofzablocki/KZNodes" 10 | s.license = 'MIT' 11 | s.author = { "Krzysztof Zablocki" => "krzysztof.zablocki@me.com" } 12 | s.source = { :git => "https://github.com/krzysztofzablocki/KZNodes.git", :tag => s.version.to_s } 13 | s.social_media_url = 'https://twitter.com/merowing_' 14 | 15 | s.platform = :ios, '7.0' 16 | s.requires_arc = true 17 | 18 | s.source_files = 'Pod/Classes/**/*.h', 'Pod/Classes/**/*.m' 19 | s.resources = ['Pod/Assets/*'] 20 | end 21 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Controls/ValueAdjust/KZPValueAdjustComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | @class KZPValueAdjustComponent; 11 | 12 | //! only generates rounded values 13 | extern KZPValueAdjustComponent * __attribute__((overloadable)) KZPAdjust(NSString *name, int from, int to, void (^block)(int)); 14 | 15 | extern KZPValueAdjustComponent * __attribute__((overloadable)) KZPAdjust(NSString *name, float from, float to, void (^block)(float)); 16 | 17 | #define KZPAdjustValue(name, from, to) __block typeof(from) name = from; KZPAdjust(@#name, from, to, ^(typeof(from) value) { name = value; }) 18 | 19 | @interface KZPValueAdjustComponent : NSObject 20 | @property(nonatomic, copy, readonly) void (^defaultValue)(CGFloat); 21 | + (KZPValueAdjustComponent*)addValueAdjustWithName:(NSString *)name fromValue:(CGFloat)from toValue:(CGFloat)to withBlock:(CGFloat (^)(CGFloat))block; 22 | @end -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Categories/NSSet+ClassesList.m: -------------------------------------------------------------------------------- 1 | // 2 | // NSSet+ClassesList(Classes) 3 | // Dynamic Code Injection 4 | // 5 | // Created by Paul Taykalo on 10/21/12. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import 9 | #import "NSSet+ClassesList.h" 10 | 11 | 12 | #if TARGET_IPHONE_SIMULATOR 13 | 14 | @implementation NSSet (ClassesList) 15 | 16 | + (NSMutableSet *)currentClassesSet { 17 | NSMutableSet * classesSet = [NSMutableSet set]; 18 | 19 | int classesCount = objc_getClassList(NULL, 0); 20 | Class * classes = NULL; 21 | if (classesCount > 0) { 22 | classes = (Class *) malloc(sizeof(Class) * classesCount); 23 | classesCount = objc_getClassList(classes, classesCount); 24 | for (int i = 0; i < classesCount; ++i) { 25 | NSValue * wrappedClass = [NSValue value:&classes[i] withObjCType:@encode(Class)]; 26 | [classesSet addObject:wrappedClass]; 27 | } 28 | free(classes); 29 | } 30 | return classesSet; 31 | } 32 | 33 | @end 34 | 35 | #endif -------------------------------------------------------------------------------- /Pod/Classes/Node/KZNNode.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | @class KZNNodeType; 12 | 13 | @class KZNWorkspace; 14 | @class KZNSocket; 15 | 16 | @interface KZNNode : UIView 17 | @property(nonatomic, weak) IBOutlet UIView *containerView; 18 | @property(nonatomic, weak, readonly) KZNNodeType *type; 19 | @property(nonatomic, weak) KZNWorkspace *workspace; 20 | 21 | @property(nonatomic, strong, readonly) NSArray *inputSockets; 22 | @property(nonatomic, strong, readonly) NSArray *outputSockets; 23 | 24 | + (instancetype)nodeWithType:(KZNNodeType *)type inputSockets:(NSArray *)inputSockets outputSockets:(NSArray *)outputSockets; 25 | 26 | - (void)setupWithType:(KZNNodeType *)type inputSockets:(NSArray *)inputSockets outputSockets:(NSArray *)outputSockets NS_REQUIRES_SUPER; 27 | 28 | - (KZNSocket *)socketForTouchPoint:(CGPoint)point; 29 | 30 | - (BOOL)canDragWithPoint:(CGPoint)point; 31 | 32 | - (NSDictionary *)evaluateWithTick:(NSUInteger)tick withForwardPropagation:(BOOL)forwardPropagation; 33 | @end -------------------------------------------------------------------------------- /Example/KZNodes/Images.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "29x29", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "40x40", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "60x60", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "ipad", 20 | "size" : "29x29", 21 | "scale" : "1x" 22 | }, 23 | { 24 | "idiom" : "ipad", 25 | "size" : "29x29", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "ipad", 30 | "size" : "40x40", 31 | "scale" : "1x" 32 | }, 33 | { 34 | "idiom" : "ipad", 35 | "size" : "40x40", 36 | "scale" : "2x" 37 | }, 38 | { 39 | "idiom" : "ipad", 40 | "size" : "76x76", 41 | "scale" : "1x" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "size" : "76x76", 46 | "scale" : "2x" 47 | } 48 | ], 49 | "info" : { 50 | "version" : 1, 51 | "author" : "xcode" 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/FileWatcher/SFFileWatcher.h: -------------------------------------------------------------------------------- 1 | // 2 | // SFFileWatcher.h 3 | // Dynamic Code Injection 4 | // 5 | // Created by adenisov on 16.10.12. 6 | // Copyright (c) 2012 Stanfy. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "SFFileWatcherDelegate.h" 11 | 12 | #if TARGET_IPHONE_SIMULATOR 13 | 14 | /* 15 | File watcher object. 16 | Watching for changes on the specified path 17 | */ 18 | @interface SFFileWatcher : NSObject 19 | 20 | /* 21 | Path on which current watcher is watching 22 | */ 23 | @property(nonatomic, readonly) NSString * watchingPath; 24 | 25 | /* 26 | Delegate that will be notified each time, as something changed 27 | */ 28 | @property(nonatomic, assign) id delegate; 29 | 30 | /* 31 | Designated initializer 32 | Starts watching on specified path and with specified delegate 33 | */ 34 | - (id)initWithFilePath:(NSString *)watchingFilePath delegate:(id)delegate; 35 | + (id)fileWatcherWithPath:(NSString *)watchingFilePath delegate:(id)delegate; 36 | 37 | 38 | @end 39 | 40 | #endif -------------------------------------------------------------------------------- /Example/Pods/RSSwizzle/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2013 Yan Rabovik 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is furnished 8 | to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in all 11 | copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 15 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 16 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 17 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 18 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 19 | THE SOFTWARE. 20 | 21 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2014 Krzysztof Zablocki 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is 8 | furnished to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 15 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 16 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 17 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 18 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 19 | THE SOFTWARE. 20 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Animation/KZPAnimatorComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZPComponent.h" 12 | 13 | // from - to - from - to 14 | 15 | extern void __attribute__((overloadable)) KZPAnimate(CGFloat from, CGFloat to, void (^block)(CGFloat)); 16 | 17 | extern void __attribute__((overloadable)) KZPAnimate(void (^block)(void)); 18 | 19 | #define KZPAnimateValue(name, from, to) __block CGFloat name = from; KZPAnimate(from, to, ^(CGFloat f) { name = f; }); 20 | #define KZPAnimateValueAR(name, from, to) __block CGFloat name = from; KZPAnimate(0, M_PI, ^(CGFloat f) { name = sinf(f) * (to - from) + from; }); 21 | 22 | #define KZPWhenChanged(value, completion) __block typeof(value) kzp_previous__##value = value; KZPAnimate(^{ if (kzp_previous__##value != value) { kzp_previous__##value = value; completion(value); }}) 23 | 24 | @interface KZPAnimatorComponent : NSObject 25 | + (void)addAnimatorFromValue:(CGFloat)from toValue:(CGFloat)to withBlock:(void (^)(CGFloat))block; 26 | @end -------------------------------------------------------------------------------- /Example/Pods/dyci/LICENSE.md: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2014 Stanfy LLC 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. -------------------------------------------------------------------------------- /Example/Pods/NHBalancedFlowLayout/LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2013 Niels de Hoog 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/UINib+StoryBoardSupport.m: -------------------------------------------------------------------------------- 1 | // 2 | // UINib(StoryBoardSupport) 3 | // dyci 4 | // 5 | // Created by Paul Taykalo on 5/27/13. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import "UINib+StoryBoardSupport.h" 9 | 10 | #if TARGET_IPHONE_SIMULATOR 11 | 12 | 13 | @implementation UINib (StoryBoardSupport) 14 | 15 | static NSMutableDictionary * cachedOptions; 16 | 17 | - (NSArray *)_swizzledInstantiateWithOwner:(id)owner options:(NSDictionary *)options { 18 | 19 | // 20 | if (!cachedOptions) { 21 | cachedOptions = [[NSMutableDictionary alloc] init]; 22 | } 23 | 24 | // Saving options per owner (View Controller address) 25 | if ( owner && options) { 26 | [cachedOptions setObject:options forKey:[NSString stringWithFormat:@"%0x", owner]]; 27 | } 28 | 29 | NSArray *items = [self _swizzledInstantiateWithOwner:owner options:options]; 30 | return items; 31 | } 32 | 33 | 34 | + (NSDictionary *)optionsByOwner:(id)owner { 35 | NSString * optionsKey = [NSString stringWithFormat:@"%0x", owner]; 36 | return cachedOptions[optionsKey]; 37 | } 38 | 39 | 40 | @end 41 | 42 | #endif -------------------------------------------------------------------------------- /Pod/Classes/Node/WithText/KZNNodeWithText.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import "KZNNodeWithText.h" 9 | #import "KZNWorkspace.h" 10 | #import "KZNNodeType.h" 11 | 12 | 13 | @interface KZNNodeWithText () 14 | @end 15 | 16 | @implementation KZNNodeWithText : KZNNode 17 | - (void)setupWithType:(KZNNodeType *)type inputSockets:(NSArray *)inputSockets outputSockets:(NSArray *)outputSockets 18 | { 19 | [super setupWithType:type inputSockets:inputSockets outputSockets:outputSockets]; 20 | [self.textField addTarget:self action:@selector(textChanged) forControlEvents:UIControlEventEditingChanged]; 21 | 22 | self.textField.layer.borderColor = [UIColor colorWithRed:0.462 green:0.517 blue:0.552 alpha:1].CGColor; 23 | self.textField.layer.borderWidth = 1.0f; 24 | self.textField.attributedPlaceholder = [[NSAttributedString alloc] initWithString:@"XXX VALUE" attributes:@{ 25 | NSFontAttributeName : [UIFont fontWithName:@"AvenirNext-Regular" size:12], 26 | NSForegroundColorAttributeName : [UIColor colorWithRed:0.462 green:0.517 blue:0.552 alpha:1] 27 | }]; 28 | self.textField.layer.sublayerTransform = CATransform3DMakeTranslation(5, 0, 0); 29 | } 30 | 31 | - (void)textChanged 32 | { 33 | [self.workspace evaluate]; 34 | } 35 | 36 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2014 Krzysztof Zablocki 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is 8 | furnished to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | 13 | Redistribution in binary form is not permitted without specific prior written 14 | permission from the copyright holders. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /Pod/Classes/Node/WithSlider/KZNNodeWithSlider.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import "KZNNodeWithSlider.h" 9 | #import "KZNWorkspace.h" 10 | #import "KZNNodeType.h" 11 | 12 | 13 | @interface KZNNodeWithSlider () 14 | @property(weak, nonatomic) IBOutlet UILabel *valueLabel; 15 | @end 16 | 17 | @implementation KZNNodeWithSlider : KZNNode 18 | - (void)setupWithType:(KZNNodeType *)type inputSockets:(NSArray *)inputSockets outputSockets:(NSArray *)outputSockets 19 | { 20 | [super setupWithType:type inputSockets:inputSockets outputSockets:outputSockets]; 21 | [self.slider setThumbImage:[UIImage imageNamed:@"sliderHandler"] forState:UIControlStateNormal]; 22 | [self.slider setThumbImage:[UIImage imageNamed:@"sliderHandler"] forState:UIControlStateHighlighted]; 23 | [self.slider addTarget:self action:@selector(valueChanged:) forControlEvents:UIControlEventValueChanged]; 24 | [self valueChanged:self.slider]; 25 | } 26 | 27 | - (void)valueChanged:(UISlider *)slider 28 | { 29 | self.valueLabel.text = [NSString stringWithFormat:@"%.2f", slider.value]; 30 | [self.valueLabel sizeToFit]; 31 | [self.workspace evaluate]; 32 | } 33 | 34 | - (void)forceLabelUpdate 35 | { 36 | self.valueLabel.text = [NSString stringWithFormat:@"%.2f", _slider.value]; 37 | } 38 | 39 | @end 40 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterInfoViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // KZPPresenterInfoViewController.m 3 | // Playground 4 | // 5 | // Created by Krzysztof Zabłocki on 21/10/2014. 6 | // Copyright (c) 2014 pixle. All rights reserved. 7 | // 8 | 9 | #import "KZPPresenterInfoViewController.h" 10 | 11 | @interface KZPPresenterInfoViewController () 12 | @property(weak, nonatomic) IBOutlet UILabel *titleLabel; 13 | @property(weak, nonatomic) IBOutlet UIImageView *imageView; 14 | 15 | @property(nonatomic, strong) UIImage *image; 16 | 17 | @end 18 | 19 | @implementation KZPPresenterInfoViewController 20 | 21 | - (void)setFromImage:(UIImage *)image title:(NSString *)title 22 | { 23 | self.image = image; 24 | self.title = title; 25 | } 26 | 27 | - (void)viewDidLoad 28 | { 29 | [super viewDidLoad]; 30 | self.imageView.image = self.image; 31 | self.titleLabel.text = self.title; 32 | [self.view setNeedsLayout]; 33 | } 34 | 35 | - (CGSize)preferredContentSize 36 | { 37 | static const NSInteger padding = 10; 38 | CGSize labelSize = [self.titleLabel sizeThatFits:CGSizeMake(1024, CGRectGetHeight(self.titleLabel.bounds))]; 39 | return CGSizeMake(MAX(self.image.size.width, labelSize.width) + padding * 2, self.image.size.height + CGRectGetHeight(self.titleLabel.bounds) + padding); 40 | } 41 | @end 42 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterComponent.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | @import QuartzCore; 11 | 12 | #import "KZPComponent.h" 13 | 14 | extern void __attribute__((overloadable)) KZPShow(CALayer *layer); 15 | 16 | extern void __attribute__((overloadable)) KZPShow(UIView *view); 17 | 18 | extern void __attribute__((overloadable)) KZPShow(UIBezierPath *path); 19 | 20 | extern void __attribute__((overloadable)) KZPShow(CGPathRef path); 21 | 22 | extern void __attribute__((overloadable)) KZPShow(CGImageRef image); 23 | 24 | extern void __attribute__((overloadable)) KZPShow(UIImage *image); 25 | 26 | extern void __attribute__((overloadable)) KZPShow(NSString *format, ...); 27 | 28 | extern void __attribute__((overloadable)) KZPShow(id obj); 29 | 30 | @protocol KZPPresenterDebugProtocol 31 | //! preffered 32 | - (UIImage *)kzp_debugImage; 33 | 34 | //! will use if object provides any of [CALayer, UIView, UIBezierPath, UIImage, NSString] 35 | @optional 36 | - (id)debugQuickLookObject; 37 | @end 38 | 39 | @interface KZPPresenterComponent : UIView 40 | @property(nonatomic, strong) UIImage *image; 41 | 42 | - (instancetype)initWithImage:(UIImage *)image type:(NSString *)type; 43 | @end -------------------------------------------------------------------------------- /Example/KZNodes/Images.xcassets/LaunchImage.launchimage/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "orientation" : "portrait", 5 | "idiom" : "iphone", 6 | "extent" : "full-screen", 7 | "minimum-system-version" : "7.0", 8 | "scale" : "2x" 9 | }, 10 | { 11 | "orientation" : "portrait", 12 | "idiom" : "iphone", 13 | "subtype" : "retina4", 14 | "extent" : "full-screen", 15 | "minimum-system-version" : "7.0", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "orientation" : "portrait", 20 | "idiom" : "ipad", 21 | "extent" : "full-screen", 22 | "minimum-system-version" : "7.0", 23 | "scale" : "1x" 24 | }, 25 | { 26 | "orientation" : "landscape", 27 | "idiom" : "ipad", 28 | "extent" : "full-screen", 29 | "minimum-system-version" : "7.0", 30 | "scale" : "1x" 31 | }, 32 | { 33 | "orientation" : "portrait", 34 | "idiom" : "ipad", 35 | "extent" : "full-screen", 36 | "minimum-system-version" : "7.0", 37 | "scale" : "2x" 38 | }, 39 | { 40 | "orientation" : "landscape", 41 | "idiom" : "ipad", 42 | "extent" : "full-screen", 43 | "minimum-system-version" : "7.0", 44 | "scale" : "2x" 45 | } 46 | ], 47 | "info" : { 48 | "version" : 1, 49 | "author" : "xcode" 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Playground/KZPPlayground.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 22/10/14. 3 | // 4 | // 5 | // 6 | 7 | #import "KZPAnimatorComponent.h" 8 | #import "KZPPresenterComponent.h" 9 | #import "KZPValueAdjustComponent.h" 10 | #import "KZPActionComponent.h" 11 | #import "KZPSynchronizationComponent.h" 12 | #import "KZPImagePickerComponent.h" 13 | #import "KZPPlaygroundViewController.h" 14 | 15 | @import Foundation; 16 | @import UIKit;@class KZPPlaygroundViewController; 17 | 18 | extern NSString *const KZPPlaygroundDidChangeImplementationNotification; 19 | 20 | //! adapt KZPActivePlayground in a KZPPlayground class that you want to use as active playground 21 | @protocol KZPActivePlayground 22 | @end 23 | 24 | @interface KZPPlayground : NSObject 25 | @property(nonatomic, weak, readonly) UIView *worksheetView; 26 | @property(nonatomic, weak, readonly) UIViewController *viewController; 27 | @property(nonatomic, weak, readonly) KZPPlaygroundViewController *playgroundViewController; 28 | 29 | //! objects store that will be re-created with recompilation, use eg. instead of instance variables 30 | @property(nonatomic, strong, readonly) NSMutableDictionary *transientObjects; 31 | 32 | - (instancetype)init NS_REQUIRES_SUPER NS_DESIGNATED_INITIALIZER; 33 | 34 | //! called only once 35 | - (void)setup; 36 | 37 | //! called on each code change 38 | - (void)run; 39 | @end -------------------------------------------------------------------------------- /Pod/Classes/Socket/KZNSocket.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | @class KZNNode; 12 | 13 | 14 | typedef NS_ENUM(NSUInteger, KZNNodeSocketType) { 15 | KZNNodeSocketTypeInput = 0, 16 | KZNNodeSocketTypeOutput = 1 17 | }; 18 | 19 | 20 | @interface KZNSocket : UIView 21 | @property(nonatomic, weak) IBOutlet UIView *containerView; 22 | @property(nonatomic, copy, readonly) NSString *name; 23 | @property(nonatomic, weak, readonly) Class type; 24 | @property(nonatomic, assign, readonly) KZNNodeSocketType socketType; 25 | @property(nonatomic, strong, readonly) UIColor *color; 26 | @property(nonatomic, weak, readonly) CAShapeLayer *shapeLayer; 27 | @property(nonatomic, weak, readonly) KZNNode *parent; 28 | @property(nonatomic, strong, readonly) NSSet *connections; 29 | @property(nonatomic, strong) KZNSocket *sourceSocket; 30 | 31 | + (instancetype)socketWithName:(NSString *)name socketType:(KZNNodeSocketType)socketType dataType:(Class)type; 32 | 33 | - (void)setupWithName:(NSString *)name socketType:(KZNNodeSocketType)socketType dataType:(Class)type; 34 | 35 | - (void)addConnectionToSocket:(KZNSocket *)inputSocket; 36 | 37 | - (void)removeConnectionToSocket:(KZNSocket *)inputSocket; 38 | 39 | - (CGPoint)socketCenter; 40 | 41 | - (BOOL)canConnectToSocket:(KZNSocket *)other; 42 | 43 | - (void)setCompatible:(BOOL)isCompatible; 44 | @end -------------------------------------------------------------------------------- /Pod/Classes/NodeType/KZNNodeType.h: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | @import Foundation; 9 | @import UIKit; 10 | 11 | #import "KZNSocket.h" 12 | 13 | typedef NS_ENUM(NSUInteger, KZNEvaluationMode) { 14 | KZNEvaluationModeOnChange = 0, 15 | KZNEvaluationModeContinuous 16 | }; 17 | 18 | @interface KZNNodeType : NSObject 19 | @property(nonatomic, assign, readonly) NSString *name; 20 | @property(nonatomic, copy) void (^processingBlock)(id node, NSDictionary *inputs, NSMutableDictionary *outputs); 21 | @property(nonatomic, weak) Class baseNodeClass; 22 | @property(nonatomic, assign) KZNEvaluationMode evaluationMode; 23 | @property(nonatomic, copy) void (^nodeSetup)(id); 24 | 25 | + (NSMutableDictionary *)nodeTypes; 26 | 27 | + (KZNNodeType *)registerType:(NSString *)typeName inputs:(NSDictionary *)inputs outputs:(NSDictionary *)outputs processingBlock:(void (^)(id node, NSDictionary *inputs, NSMutableDictionary *outputs))processingBlock __attribute__((nonnull(1, 4))); 28 | + (KZNNodeType *)registerType:(NSString *)typeName withClass:(Class)nodeClass inputs:(NSDictionary *)inputs outputs:(NSDictionary *)outputs processingBlock:(void (^)(id node, NSDictionary *inputs, NSMutableDictionary *outputs))processingBlock __attribute__((nonnull(1, 2, 5))); 29 | + (KZNNodeType *)registerType:(NSString *)typeName withBuilder:(void (^)(KZNNodeType *))builderBlock __attribute__((nonnull)); 30 | 31 | - (void)addSocket:(KZNNodeSocketType)type name:(NSString *)name type:(Class)class; 32 | 33 | - (KZNNode *)createNode; 34 | @end -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/NSObject+DyCInjection.h: -------------------------------------------------------------------------------- 1 | // 2 | // NSObject+DyCInjection(DCInjection) 3 | // Dynamic Code Injection 4 | // 5 | // Created by Paul Taykalo on 10/21/12. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | #import 9 | 10 | #if TARGET_IPHONE_SIMULATOR 11 | 12 | /* 13 | Methods that will be called on object, that are waiting for injection 14 | */ 15 | @interface NSObject (DyCInjection) 16 | 17 | 18 | + (void)allowInjectionSubscriptionOnInitMethod; 19 | 20 | /* 21 | This method will be called in order to determine, 22 | do we need to subscribe to Injection notifications, or not 23 | 24 | By default all objects that have prefixes: 25 | _ 26 | NS 27 | CF 28 | Web 29 | UI 30 | DOM 31 | SFInj 32 | OS_ 33 | 34 | are skipped 35 | 36 | This behaviour can be changed in next releases 37 | */ 38 | + (BOOL)shouldPerformRuntimeCodeInjectionOnObject:(id)instance; 39 | 40 | 41 | 42 | /* 43 | Will be called, when some class (X) will be injected in application runtime 44 | On All instances of class X, and instances of subclasses of X, this method will be called 45 | */ 46 | - (void)updateOnClassInjection; 47 | 48 | /* 49 | This method will be called for all classes, that are waiting for resources changes. 50 | Before this method is called, Image cache is flushed, so you don't have to call memory warnings 51 | Resource that was injected is passed with parameter. But in general, you don't need to care 52 | 53 | */ 54 | - (void)updateOnResourceInjection:(NSString *)resourcePath; 55 | 56 | 57 | @end 58 | 59 | #endif -------------------------------------------------------------------------------- /Example/KZNodes/KZNodes-Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | en 7 | CFBundleDisplayName 8 | ${PRODUCT_NAME} 9 | CFBundleExecutable 10 | ${EXECUTABLE_NAME} 11 | CFBundleIdentifier 12 | org.cocoapods.demo.${PRODUCT_NAME:rfc1034identifier} 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | ${PRODUCT_NAME} 17 | CFBundlePackageType 18 | APPL 19 | CFBundleShortVersionString 20 | 1.0 21 | CFBundleSignature 22 | ???? 23 | CFBundleVersion 24 | 1.0 25 | LSRequiresIPhoneOS 26 | 27 | UIRequiredDeviceCapabilities 28 | 29 | armv7 30 | 31 | UISupportedInterfaceOrientations 32 | 33 | UIInterfaceOrientationPortrait 34 | UIInterfaceOrientationLandscapeLeft 35 | UIInterfaceOrientationLandscapeRight 36 | 37 | UIStatusBarHidden 38 | 39 | UIViewControllerBasedStatusBarAppearance 40 | 41 | UISupportedInterfaceOrientations~ipad 42 | 43 | UIInterfaceOrientationLandscapeLeft 44 | UIInterfaceOrientationLandscapeRight 45 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Controls/Action/KZPActionComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import 9 | #import "KZPActionComponent.h" 10 | #import "KZPTimelineViewController.h" 11 | 12 | static const void *kActionBlockKey = &kActionBlockKey; 13 | 14 | void __attribute__((overloadable)) KZPAction(NSString *name, void (^block)(void)) { 15 | [KZPActionComponent addCallToActionWithName:name block:block]; 16 | } 17 | 18 | @implementation KZPActionComponent 19 | + (void)addCallToActionWithName:(NSString *)name block:(void (^)())block 20 | { 21 | KZPTimelineViewController *timelineViewController = [KZPTimelineViewController sharedInstance]; 22 | 23 | UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom]; 24 | [button setTitle:name forState:UIControlStateNormal]; 25 | [button setTitleColor:UIColor.brownColor forState:UIControlStateNormal]; 26 | button.titleLabel.adjustsFontSizeToFitWidth = YES; 27 | CGSize size = [button sizeThatFits:CGSizeMake(timelineViewController.maxWidthForSnapshotView, CGFLOAT_MAX)]; 28 | button.frame = CGRectMake(0, 0, size.width, size.height); 29 | objc_setAssociatedObject(button, kActionBlockKey, block, OBJC_ASSOCIATION_COPY_NONATOMIC); 30 | [button addTarget:self action:@selector(actionWithButton:) forControlEvents:UIControlEventTouchUpInside]; 31 | [timelineViewController addView:button]; 32 | } 33 | 34 | + (void)actionWithButton:(UIButton *)button 35 | { 36 | void(^block)(void) = objc_getAssociatedObject(button, kActionBlockKey); 37 | block(); 38 | } 39 | 40 | + (void)reset 41 | { 42 | 43 | } 44 | 45 | @end -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes-environment.h: -------------------------------------------------------------------------------- 1 | 2 | // To check if a library is compiled with CocoaPods you 3 | // can use the `COCOAPODS` macro definition which is 4 | // defined in the xcconfigs so it is available in 5 | // headers also when they are imported in the client 6 | // project. 7 | 8 | 9 | // KZNodes 10 | #define COCOAPODS_POD_AVAILABLE_KZNodes 11 | #define COCOAPODS_VERSION_MAJOR_KZNodes 0 12 | #define COCOAPODS_VERSION_MINOR_KZNodes 1 13 | #define COCOAPODS_VERSION_PATCH_KZNodes 0 14 | 15 | // KZPlayground 16 | #define COCOAPODS_POD_AVAILABLE_KZPlayground 17 | #define COCOAPODS_VERSION_MAJOR_KZPlayground 0 18 | #define COCOAPODS_VERSION_MINOR_KZPlayground 3 19 | #define COCOAPODS_VERSION_PATCH_KZPlayground 2 20 | 21 | // NHBalancedFlowLayout 22 | #define COCOAPODS_POD_AVAILABLE_NHBalancedFlowLayout 23 | #define COCOAPODS_VERSION_MAJOR_NHBalancedFlowLayout 0 24 | #define COCOAPODS_VERSION_MINOR_NHBalancedFlowLayout 2 25 | #define COCOAPODS_VERSION_PATCH_NHBalancedFlowLayout 0 26 | 27 | // RSSwizzle 28 | #define COCOAPODS_POD_AVAILABLE_RSSwizzle 29 | #define COCOAPODS_VERSION_MAJOR_RSSwizzle 0 30 | #define COCOAPODS_VERSION_MINOR_RSSwizzle 1 31 | #define COCOAPODS_VERSION_PATCH_RSSwizzle 0 32 | 33 | // dyci 34 | #define COCOAPODS_POD_AVAILABLE_dyci 35 | // This library does not follow semantic-versioning, 36 | // so we were not able to define version macros. 37 | // Please contact the author. 38 | // Version: 0.1.5.6. 39 | 40 | // dyci/Injections 41 | #define COCOAPODS_POD_AVAILABLE_dyci_Injections 42 | // This library does not follow semantic-versioning, 43 | // so we were not able to define version macros. 44 | // Please contact the author. 45 | // Version: 0.1.5.6. 46 | 47 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Notifications/SFInjectionsNotificationsCenter.h: -------------------------------------------------------------------------------- 1 | // 2 | // SFInjectionsNotificationsCenter.h 3 | // dyci-framework 4 | // 5 | // Created by Paul Taykalo on 6/1/13. 6 | // Copyright (c) 2013 Stanfy. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | #if TARGET_IPHONE_SIMULATOR 12 | 13 | @protocol SFInjectionObserver 14 | 15 | /* 16 | Will be called, when some class (X) will be injected in application runtime 17 | On All instances of class X, and instances of subclasses of X, this method will be called 18 | */ 19 | - (void)updateOnClassInjection; 20 | 21 | /* 22 | This method will be called for all classes, that are waiting for resources changes. 23 | Before this method is called, Image cache is flushed, so you don't have to call memory warnings 24 | Resource that was injected is passed with parameter. But in general, you don't need to care 25 | */ 26 | - (void)updateOnResourceInjection:(NSString *)resourcePath; 27 | 28 | @end 29 | 30 | 31 | /* 32 | This notification center will notify classes about new infection code available 33 | Live classes about new code 34 | This one was made because it seems sometimes classes doesn't remove themself as observers from 35 | Notification Center. And we'll try to understand why it's so 36 | 37 | Also it'll try to understand which classes should be filtered from observing 38 | */ 39 | @interface SFInjectionsNotificationsCenter : NSObject 40 | 41 | /* 42 | Returns notification center instance 43 | */ 44 | + (instancetype)sharedInstance; 45 | 46 | - (void)addObserver:(id)observer; 47 | - (void)removeObserver:(id)observer; 48 | 49 | /* 50 | This will notify about class injection 51 | */ 52 | - (void)notifyOnClassInjection:(Class)class; 53 | 54 | /* 55 | This will notiy all registered classes about that some resource was injected 56 | */ 57 | - (void)notifyOnResourceInjection:(NSString *)resourceInjection; 58 | 59 | @end 60 | 61 | #endif -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Animation/KZPAnimatorComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | #import "KZPAnimatorComponent.h" 8 | 9 | 10 | void __attribute__((overloadable)) KZPAnimate(CGFloat from, CGFloat to, void (^block)(CGFloat)) { 11 | [KZPAnimatorComponent addAnimatorFromValue:from toValue:to withBlock:block]; 12 | } 13 | 14 | void __attribute__((overloadable)) KZPAnimate(void (^block)(void)) { 15 | [KZPAnimatorComponent addAnimatorFromValue:0 toValue:60 withBlock:^(CGFloat v) { 16 | block(); 17 | }]; 18 | } 19 | 20 | NSMutableArray *displayLinks = nil; 21 | 22 | @interface KZPAnimatorComponent () 23 | @property(nonatomic, copy) void (^animationBlock)(CGFloat); 24 | @property(nonatomic, assign) CGFloat from; 25 | @property(nonatomic, assign) CGFloat to; 26 | 27 | @property(nonatomic, assign) CGFloat accumulator; 28 | @end 29 | 30 | @implementation KZPAnimatorComponent 31 | 32 | + (void)addAnimatorFromValue:(CGFloat)from toValue:(CGFloat)to withBlock:(void (^)(CGFloat))block 33 | { 34 | KZPAnimatorComponent *animation = [KZPAnimatorComponent new]; 35 | animation.animationBlock = block; 36 | animation.from = from; 37 | animation.to = to; 38 | 39 | CADisplayLink *displayLink = [CADisplayLink displayLinkWithTarget:animation selector:@selector(animate:)]; 40 | [displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode]; 41 | 42 | if (!displayLinks) { 43 | displayLinks = [NSMutableArray new]; 44 | } 45 | [displayLinks addObject:displayLink]; 46 | } 47 | 48 | + (void)reset 49 | { 50 | [displayLinks enumerateObjectsUsingBlock:^(CADisplayLink *obj, NSUInteger idx, BOOL *stop) { 51 | [obj invalidate]; 52 | }]; 53 | [displayLinks removeAllObjects]; 54 | } 55 | 56 | - (void)animate:(CADisplayLink *)displayLink 57 | { 58 | self.accumulator += displayLink.duration * fabs(self.from - self.to) * 0.6; 59 | if (self.accumulator >= self.to) { 60 | self.accumulator = self.from; 61 | } 62 | self.animationBlock(self.accumulator); 63 | } 64 | 65 | - (void)setFrom:(CGFloat)from 66 | { 67 | _from = from; 68 | self.accumulator = _from; 69 | } 70 | 71 | 72 | @end 73 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Playground/KZPPlayground.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 22/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import 9 | #import "KZPPlayground.h" 10 | #import "RSSwizzle.h" 11 | #import "SFDynamicCodeInjection.h" 12 | #import "KZPPlaygroundViewController.h" 13 | 14 | NSString *const KZPPlaygroundDidChangeImplementationNotification = @"KZPPlaygroundDidChangeImplementationNotification"; 15 | 16 | @interface NSObject (KZPOverride) 17 | @end 18 | 19 | @implementation NSObject (KZPOverride) 20 | #pragma clang diagnostic push 21 | #pragma clang diagnostic ignored "-Wundeclared-selector" 22 | #pragma ide diagnostic ignored "UnresolvedMessage" 23 | + (void)load 24 | { 25 | SEL selectorToSwizzle = @selector(performInjectionWithClass:); 26 | RSSwizzleInstanceMethod(SFDynamicCodeInjection.class, 27 | selectorToSwizzle, 28 | RSSWReturnType(void), 29 | RSSWArguments(Class aClass), 30 | RSSWReplacement({ 31 | RSSWCallOriginal(aClass); 32 | [[NSNotificationCenter defaultCenter] postNotificationName:KZPPlaygroundDidChangeImplementationNotification object:nil]; 33 | }), 0, NULL); 34 | 35 | } 36 | #pragma clang diagnostic pop 37 | 38 | @end 39 | 40 | @interface KZPPlayground () 41 | @property(nonatomic, weak, readwrite) UIView *worksheetView; 42 | @property(nonatomic, weak, readwrite) UIViewController *viewController; 43 | @property(nonatomic, weak, readwrite) KZPPlaygroundViewController *playgroundViewController; 44 | @end 45 | 46 | @implementation KZPPlayground 47 | @synthesize transientObjects = _transientObjects; 48 | 49 | - (instancetype)init 50 | { 51 | self = [super init]; 52 | if (self) { 53 | [self setup]; 54 | } 55 | 56 | return self; 57 | } 58 | 59 | - (NSMutableDictionary *)transientObjects 60 | { 61 | return (_transientObjects = _transientObjects ?: [NSMutableDictionary new]); 62 | } 63 | 64 | - (void)setup 65 | { 66 | 67 | } 68 | 69 | - (void)run 70 | { 71 | 72 | } 73 | 74 | - (void)updateOnClassInjection 75 | { 76 | 77 | } 78 | 79 | - (void)updateOnResourceInjection:(NSString *)path { 80 | [[NSNotificationCenter defaultCenter] postNotificationName:KZPPlaygroundDidChangeImplementationNotification object:nil]; 81 | } 82 | 83 | @end -------------------------------------------------------------------------------- /Example/Pods/NHBalancedFlowLayout/NHBalancedFlowLayout/NHBalancedFlowLayout.h: -------------------------------------------------------------------------------- 1 | // 2 | // BalancedFlowLayout.h 3 | // BalancedFlowLayout 4 | // 5 | // Created by Niels de Hoog on 31/10/13. 6 | // Copyright (c) 2013 Niels de Hoog. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | /** 12 | * The BalancedFlowLayout class is designed to display items of different sizes and aspect ratios in a grid, without wasting any visual space. 13 | * It takes the preferred sizes for the displayed items and a preferred row height as input to determine the optimal layout. 14 | * 15 | * In order to use this layout, the delegate for the collection view must implement the required methods in the BalancedFlowLayoutDelegate protocol. 16 | * Currently this class does not support supplementary or decoration views. 17 | * 18 | */ 19 | @interface NHBalancedFlowLayout : UICollectionViewLayout 20 | 21 | // The preferred size for each row measured in the scroll direction 22 | @property (nonatomic) CGFloat preferredRowSize; 23 | 24 | // The size of each section's header. This maybe dynamically adjusted 25 | // per section via the protocol method referenceSizeForHeaderInSection. 26 | @property (nonatomic) CGSize headerReferenceSize; 27 | 28 | // The size of each section's header. This maybe dynamically adjusted 29 | // per section via the protocol method referenceSizeForFooterInSection. 30 | @property (nonatomic) CGSize footerReferenceSize; 31 | 32 | // The margins used to lay out content in a section. 33 | @property (nonatomic) UIEdgeInsets sectionInset; 34 | 35 | // The minimum spacing to use between lines of items in the grid. 36 | @property (nonatomic) CGFloat minimumLineSpacing; 37 | 38 | // The minimum spacing to use between items in the same row. 39 | @property (nonatomic) CGFloat minimumInteritemSpacing; 40 | 41 | // The scroll direction of the grid. 42 | @property (nonatomic) UICollectionViewScrollDirection scrollDirection; 43 | 44 | @end 45 | 46 | 47 | @protocol NHBalancedFlowLayoutDelegate 48 | 49 | @required 50 | - (CGSize)collectionView:(UICollectionView *)collectionView layout:(NHBalancedFlowLayout *)collectionViewLayout preferredSizeForItemAtIndexPath:(NSIndexPath *)indexPath; 51 | 52 | @end -------------------------------------------------------------------------------- /Example/KZNodes/KZNAppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // KZNAppDelegate.m 3 | // KZNodes 4 | // 5 | // Created by CocoaPods on 10/30/2014. 6 | // Copyright (c) 2014 Krzysztof Zablocki. All rights reserved. 7 | // 8 | 9 | #import "KZNAppDelegate.h" 10 | #import "KZPPlaygroundViewController.h" 11 | @implementation KZNAppDelegate 12 | 13 | - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions 14 | { 15 | self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].applicationFrame]; 16 | 17 | self.window.rootViewController = [KZPPlaygroundViewController playgroundViewController]; 18 | [self.window makeKeyAndVisible]; 19 | return YES; 20 | } 21 | 22 | - (void)applicationWillResignActive:(UIApplication *)application 23 | { 24 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 25 | // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game. 26 | } 27 | 28 | - (void)applicationDidEnterBackground:(UIApplication *)application 29 | { 30 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 31 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 32 | } 33 | 34 | - (void)applicationWillEnterForeground:(UIApplication *)application 35 | { 36 | // Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background. 37 | } 38 | 39 | - (void)applicationDidBecomeActive:(UIApplication *)application 40 | { 41 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 42 | } 43 | 44 | - (void)applicationWillTerminate:(UIApplication *)application 45 | { 46 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 47 | } 48 | 49 | @end 50 | -------------------------------------------------------------------------------- /Pod/Assets/KZNWorkspaceBlockCell.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | -------------------------------------------------------------------------------- /Example/Pods/NHBalancedFlowLayout/README.md: -------------------------------------------------------------------------------- 1 | NHBalancedFlowLayout 2 | ================== 3 | 4 | UICollectionViewLayout subclass for displaying items of different sizes in a grid without wasting any visual space. Inspired by: http://www.crispymtn.com/stories/the-algorithm-for-a-perfectly-balanced-photo-gallery 5 | 6 | ## Notes 7 | * Tested with iOS 7, but should be compatible with iOS6 as well 8 | * Works with iPhone and iPad 9 | * All interface orientations are supported 10 | 11 | ## Screenshots 12 | 13 | 14 | 15 | 16 | ## Installation 17 | 18 | The easiest way is to use CocoaPods. If you don't already, here's a [guide](http://guides.cocoapods.org/using/getting-started.html). 19 | 20 | pod 'NHBalancedFlowLayout', '~> 0.1.2' 21 | 22 | If you don't use CocoaPods, you'll need to copy the following files into your project: 23 | 24 | * NHBalancedFlowLayout.h 25 | * NHBalancedFlowLayout.m 26 | * NHLinearPartition.h 27 | * NHLinearPartition.m 28 | 29 | ## Credits 30 | 31 | Attributions for the photos in the same order as they appear in the demo: 32 | 33 | * http://www.flickr.com/photos/adriensifre/7162196453/ 34 | * http://www.flickr.com/photos/ucumari/2949701552/ 35 | * http://www.flickr.com/photos/ucumari/388370102/ 36 | * http://www.flickr.com/photos/38659937@N06/3567549164/ 37 | * http://www.flickr.com/photos/vinothchandar/5139245960/ 38 | * http://www.flickr.com/photos/expressmonorail/3581442376/ 39 | * http://www.flickr.com/photos/keithmwilliams/4465380932/ 40 | * http://en.wikipedia.org/wiki/File:Bobcat-Texas-9110.jpg 41 | * http://www.flickr.com/photos/thecaucas/2390806406/ 42 | * http://www.flickr.com/photos/ucumari/2342703987/ 43 | * http://www.flickr.com/photos/ucumari/2317386162/ 44 | * http://www.flickr.com/photos/ucumari/448815607/ 45 | * http://www.flickr.com/photos/kshathriya/331847679/ 46 | * http://www.flickr.com/photos/ucumari/367041320/ 47 | * http://www.flickr.com/photos/da100fotos/465868860/ 48 | * http://www.flickr.com/photos/hhoyer/3758550410/ 49 | * http://www.flickr.com/photos/tambako/9314344697/ 50 | * http://www.flickr.com/photos/sergiu_bacioiu/4485931477/ 51 | * http://www.flickr.com/photos/matthileo/4077650329/ 52 | * http://www.flickr.com/photos/markop/491027707/ 53 | * http://www.flickr.com/photos/stevedave/3566325269/ 54 | * http://www.flickr.com/photos/genista/127048347/ 55 | * http://www.flickr.com/photos/wagner-machado-carlos-lemes/5540332691/ 56 | * http://www.flickr.com/photos/29487767@N02/3438177701/ 57 | -------------------------------------------------------------------------------- /Example/Pods/dyci/README.md: -------------------------------------------------------------------------------- 1 | # WARNING 2 | **Please, Read this.** 3 | Uninstall dyci before updating Xcode. 4 | In other case, you'll need to reinstall it :( 5 | We're currenlty working on [this issue](https://github.com/DyCI/dyci-main/issues/8)... 6 | If you've already expirienced this issue - remove and reinstall Xcode. 7 | 8 | # dyci 9 | Dynamic code injection tool. 10 | Allows you to inject your code into running iOS application, whithout restarting it. 11 | 12 | ## Installation 13 | If you already know, what this tool is about, you can move to [Installation page](https://github.com/DyCI/dyci-main/wiki/Installation) 14 | 15 | ## Adding to your project 16 | After installation, you need to add dyci library to your project 17 | If you are using [CocoaPods](https://github.com/CocoaPods/CocoaPods), then, just add this line to your PodFile 18 | 19 | `pod 'dyci', :git => 'https://github.com/DyCI/dyci-main.git'` 20 | 21 | If not, then, you can add dyci in [other ways](https://github.com/DyCI/dyci-main/wiki/Using-dyci) 22 | 23 | ## Reasons, why do you need this tool 24 | * It's good for applying small logic changes 25 | * It's good for quick small fixes on big projects. 26 | * It's good for debugging purposes. Remember, you can inject any code at runtime. Logging is the code also. 27 | 28 | ## Differences from other tools 29 | * You need minimum moves to enable dyci 30 | * You aren't writing some kind of script, you are writing your code! 31 | * You don't need to prepare/modify/lock your code for dyci 32 | * Your changes are always saved (They will not be discarded on next run) 33 | 34 | ## How it works 35 | If you curious about How [how it works](https://github.com/DyCI/dyci-main/wiki/How-it-Works), you can read about it in [wiki](https://github.com/DyCI/dyci-main/wiki/How-it-Works). 36 | 37 | ##Example 38 | There's one example in sources 39 | There's video about Tic-Tac-Toe game creation without project restart 40 | [Video at Youtube](https://www.youtube.com/watch?v=8nyEpAqUug4) 41 | 42 | 43 | ##Some points of view 44 | 1. Dyci is not about loading new code in application. 45 | 2. Dyci is about speeding up development. 46 | 3. Each time, you are using dyci, it saves your time. 47 | 48 | 49 | ##WARNING 50 | Please, do not use this tool in your real applications, that you about to publish in App Store. Dyci won't work on devices by default. It was made for purpose. Dynamic code injection is good for development, but it will leave huge security hole if you put it in your application. Please, do not :) I warned you. 51 | 52 | #FAQ 53 | If you have some questions, before asking them , make sure that they aren't listed [here](https://github.com/DyCI/dyci-main/wiki/FAQ) 54 | 55 | 56 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/FileWatcher/SFFileWatcher.m: -------------------------------------------------------------------------------- 1 | // 2 | // SFFileWatcher.m 3 | // Dynamic Code Injection 4 | // 5 | // Created by adenisov on 16.10.12. 6 | // Copyright (c) 2012 Stanfy. All rights reserved. 7 | // 8 | 9 | #import "SFFileWatcher.h" 10 | 11 | #if TARGET_IPHONE_SIMULATOR 12 | 13 | @implementation SFFileWatcher { 14 | 15 | /* 16 | Date on what last changes was loaded 17 | */ 18 | NSDate *_lastLoadDate; 19 | 20 | /* 21 | Dispatching queue in which file watching operations will be performed 22 | */ 23 | dispatch_queue_t _queue; 24 | 25 | /* 26 | Dispatch source of file changes notifications 27 | */ 28 | dispatch_source_t _source; 29 | } 30 | 31 | 32 | + (id)fileWatcherWithPath:(NSString *)watchDirectory delegate:(id)delegate { 33 | return [[SFFileWatcher alloc] initWithFilePath:watchDirectory delegate:delegate]; 34 | } 35 | 36 | 37 | - (id)initWithFilePath:(NSString *)watchingFilePath delegate:(id)delegate { 38 | self = [super init]; 39 | if (self) { 40 | _watchingPath = watchingFilePath; 41 | _delegate = delegate; 42 | _lastLoadDate = [NSDate date]; 43 | 44 | [self setupHandlerOnFileChange:_watchingPath]; 45 | 46 | } 47 | 48 | return self; 49 | 50 | } 51 | 52 | 53 | - (void)setupHandlerOnFileChange:(NSString *)filePath { 54 | 55 | // Resolving file descriptor 56 | uintptr_t fd = (uintptr_t) open([filePath cStringUsingEncoding:NSUTF8StringEncoding], O_EVTONLY); 57 | 58 | // Setting up queued and source of dispatch events 59 | _queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0); 60 | _source = dispatch_source_create(DISPATCH_SOURCE_TYPE_VNODE, 61 | (uintptr_t) fd, 62 | DISPATCH_VNODE_WRITE, 63 | _queue); 64 | 65 | __block id weakSelf = self; 66 | dispatch_source_set_event_handler(_source, ^{ 67 | dispatch_async(dispatch_get_main_queue(), ^{ 68 | [weakSelf checkForFileCreationDate]; 69 | }); 70 | }); 71 | 72 | dispatch_source_set_cancel_handler(_source, ^{ 73 | close(fd); 74 | }); 75 | 76 | dispatch_resume(_source); 77 | } 78 | 79 | 80 | - (void)checkForFileCreationDate { 81 | NSFileManager * fm = [NSFileManager defaultManager]; 82 | 83 | NSArray * files = [fm contentsOfDirectoryAtPath:_watchingPath error:nil]; 84 | 85 | // Using the most recent file, but date should be >> _lastLoadData 86 | 87 | for (NSString * file in files) { 88 | NSString * filePath = [_watchingPath stringByAppendingPathComponent:file]; 89 | NSDictionary * fileAttributes = [[NSFileManager defaultManager] attributesOfItemAtPath:filePath error:nil]; 90 | NSDate * fileCreationDate = [fileAttributes fileCreationDate]; 91 | 92 | // If new file has bigger creation date, then, let's notify our delegate about it 93 | NSTimeInterval diff = [_lastLoadDate timeIntervalSinceDate:fileCreationDate]; 94 | if (diff < 0) { 95 | [self.delegate newFileWasFoundAtPath:filePath]; 96 | _lastLoadDate = fileCreationDate; 97 | } 98 | } 99 | } 100 | 101 | 102 | @end 103 | 104 | #endif -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Synchronization/KZPSynchronizationComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | #import 8 | #import "KZPSynchronizationComponent.h" 9 | 10 | void KZPWaitForEvaluation(id (^valueGetter)(), void (^completion)(id)) { 11 | [KZPSynchronizationComponent addComponentWithGetter:valueGetter completion:completion]; 12 | } 13 | 14 | static const void *kComponentsKey = &kComponentsKey; 15 | static const void *kIsFinishedKey = &kIsFinishedKey; 16 | 17 | @interface KZPSynchronizationComponent () 18 | @property(nonatomic, copy) id (^valueGetter)(void); 19 | @property(nonatomic, copy) void (^completion)(id); 20 | @end 21 | 22 | @implementation KZPSynchronizationComponent 23 | 24 | + (void)addComponentWithGetter:(id (^)())valueGetter completion:(void (^)(id))completion 25 | { 26 | KZPSynchronizationComponent *component = [KZPSynchronizationComponent new]; 27 | component.valueGetter = valueGetter; 28 | component.completion = completion; 29 | [self addComponent:component]; 30 | } 31 | 32 | + (void)addComponent:(KZPSynchronizationComponent *)component 33 | { 34 | @synchronized (self) { 35 | [self.components addObject:component]; 36 | } 37 | } 38 | 39 | + (NSMutableArray *)components 40 | { 41 | NSMutableArray *components = objc_getAssociatedObject(self, kComponentsKey); 42 | if (!components) { 43 | components = [NSMutableArray new]; 44 | objc_setAssociatedObject(self, kComponentsKey, components, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 45 | } 46 | return components; 47 | } 48 | 49 | + (void)load 50 | { 51 | [self performSelectorInBackground:@selector(backgroundProcessing) withObject:nil]; 52 | } 53 | 54 | + (BOOL)isResetting 55 | { 56 | return [objc_getAssociatedObject(self, kIsFinishedKey) boolValue]; 57 | } 58 | 59 | + (void)setFinished:(BOOL)finished 60 | { 61 | objc_setAssociatedObject(self, kIsFinishedKey, @(finished), OBJC_ASSOCIATION_RETAIN_NONATOMIC); 62 | } 63 | 64 | + (void)backgroundProcessing 65 | { 66 | @autoreleasepool { 67 | #pragma clang diagnostic push 68 | #pragma clang diagnostic ignored "-Wmissing-noreturn" 69 | while (YES) { 70 | NSArray *components = nil; 71 | @synchronized (self) { 72 | components = [self.components copy]; 73 | } 74 | 75 | NSMutableArray *componentsToRemove = [NSMutableArray new]; 76 | 77 | [components enumerateObjectsUsingBlock:^(KZPSynchronizationComponent *component, NSUInteger idx, BOOL *stop) { 78 | *stop = [self isResetting]; 79 | 80 | BOOL finished = [component evaluate]; 81 | if (finished) { 82 | [componentsToRemove addObject:component]; 83 | } 84 | }]; 85 | 86 | @synchronized (self) { 87 | if ([self isResetting]) { 88 | [self.components removeObjectsInArray:componentsToRemove]; 89 | } 90 | } 91 | 92 | [NSThread sleepForTimeInterval:0.1]; 93 | } 94 | #pragma clang diagnostic pop 95 | } 96 | } 97 | 98 | - (BOOL)evaluate 99 | { 100 | __block BOOL finished = NO; 101 | dispatch_sync(dispatch_get_main_queue(), ^{ 102 | id value = self.valueGetter(); 103 | if (value) { 104 | self.completion(value); 105 | finished = YES; 106 | } 107 | }); 108 | 109 | return finished; 110 | } 111 | 112 | + (void)reset 113 | { 114 | @synchronized (self) { 115 | self.finished = YES; 116 | [[self components] removeAllObjects]; 117 | } 118 | } 119 | 120 | 121 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Assets/KZPPresenterInfoViewController.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /Example/KZNodes.xcodeproj/xcshareddata/xcschemes/KZNodes.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 33 | 39 | 40 | 41 | 42 | 43 | 49 | 50 | 51 | 52 | 61 | 62 | 68 | 69 | 70 | 71 | 72 | 73 | 79 | 80 | 86 | 87 | 88 | 89 | 91 | 92 | 95 | 96 | 97 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Notifications/SFInjectionsNotificationsCenter.m: -------------------------------------------------------------------------------- 1 | // 2 | // SFInjectionsNotificationsCenter.m 3 | // dyci-framework 4 | // 5 | // Created by Paul Taykalo on 6/1/13. 6 | // Copyright (c) 2013 Stanfy. All rights reserved. 7 | // 8 | 9 | #import "SFInjectionsNotificationsCenter.h" 10 | 11 | #if TARGET_IPHONE_SIMULATOR 12 | 13 | @implementation SFInjectionsNotificationsCenter { 14 | NSMutableDictionary * _observers; 15 | } 16 | 17 | 18 | + (instancetype)sharedInstance { 19 | static SFInjectionsNotificationsCenter * _instance = nil; 20 | if (!_instance) { 21 | _instance = [[self alloc] init]; 22 | _instance->_observers = [NSMutableDictionary dictionary]; 23 | } 24 | return _instance; 25 | } 26 | 27 | 28 | - (void)addObserver:(id)observer { 29 | [self addObserver:observer forClass:[observer class]]; 30 | } 31 | 32 | 33 | - (void)removeObserver:(id)observer { 34 | [self removeObserver:observer ofClass:[observer class]]; 35 | } 36 | 37 | 38 | - (void)removeObserver:(id)observer ofClass:(Class)class { 39 | @synchronized (_observers) { 40 | NSMutableSet * observersPerClass = [_observers objectForKey:class]; 41 | if (observersPerClass) { 42 | @synchronized (observersPerClass) { 43 | [observersPerClass removeObject:observer]; 44 | } 45 | } 46 | } 47 | } 48 | 49 | 50 | - (void)addObserver:(id)observer forClass:(Class)class { 51 | if (!class) { 52 | return; 53 | } 54 | @synchronized (_observers) { 55 | NSMutableSet * observersPerClass = [_observers objectForKey:class]; 56 | if (!observersPerClass) { 57 | observersPerClass = (__bridge_transfer NSMutableSet *) CFSetCreateMutable(nil, 0, nil); 58 | [_observers setObject:observersPerClass forKey:class]; 59 | } 60 | @synchronized (observersPerClass) { 61 | [observersPerClass addObject:observer]; 62 | } 63 | } 64 | } 65 | 66 | 67 | /* 68 | This will notify about class injection 69 | */ 70 | - (void)notifyOnClassInjection:(Class)injectedClass { 71 | int idx = 0; 72 | @synchronized (_observers) { 73 | for (NSMutableSet * observersPerClass in [_observers allValues]) { 74 | @synchronized (observersPerClass) { 75 | id anyObject = [observersPerClass anyObject]; 76 | int localIdx = 0; 77 | if ([anyObject isKindOfClass:injectedClass]) { 78 | for (id observer in observersPerClass) { 79 | [observer updateOnClassInjection]; 80 | idx++; 81 | localIdx++; 82 | } 83 | NSLog(@"%d (%@) class instanses were notified on Class Injection : ", localIdx, NSStringFromClass([anyObject class])); 84 | } 85 | } 86 | } 87 | } 88 | 89 | NSLog(@"%d instanses were notified on Class Injection by injecting class: (%@)", idx, NSStringFromClass(injectedClass)); 90 | } 91 | 92 | 93 | /* 94 | This will notiy all registered classes about that some resource was injected 95 | */ 96 | - (void)notifyOnResourceInjection:(NSString *)resourceInjection { 97 | int idx = 0; 98 | @synchronized (_observers) { 99 | for (NSMutableSet * observersPerClass in [_observers allValues]) { 100 | @synchronized (observersPerClass) { 101 | for (id observer in observersPerClass) { 102 | [observer updateOnResourceInjection:resourceInjection]; 103 | idx++; 104 | } 105 | } 106 | } 107 | } 108 | NSLog(@"%d classes instanses were notified on REsource Injection", idx); 109 | } 110 | 111 | 112 | @end 113 | 114 | 115 | #endif -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # KZNodes - editors like Origami made easy. 2 | 3 | [![Version](https://img.shields.io/cocoapods/v/KZNodes.svg?style=flat)](http://cocoadocs.org/docsets/KZNodes) 4 | [![License](https://img.shields.io/cocoapods/l/KZNodes.svg?style=flat)](http://cocoadocs.org/docsets/KZNodes) 5 | [![Platform](https://img.shields.io/cocoapods/p/KZNodes.svg?style=flat)](http://cocoadocs.org/docsets/KZNodes) 6 | 7 | [Watch demo](https://vimeo.com/110467626) 8 | 9 | [![](/Screenshots/transforms.gif?raw=true)](https://vimeo.com/110467626) 10 | [![](/Screenshots/coreimage.gif?raw=true)](https://vimeo.com/110467626) 11 | 12 | Have you ever wondered how you could create an editor like Origami? 13 | How about creating a subset of Origami in less than 100 lines of code? 14 | 15 | Joining nodes is like functional programming, only visual. 16 | 17 | Features: 18 | - Domain agnostic, can be used to create editors for: 19 | - Animations 20 | - 3D Graphics 21 | - Image processing 22 | - Data Processing 23 | - Artificial Inteligence 24 | - Anything that you can express as a data / function pipeline? 25 | - Sockets have data types, you specify what classes are supported, that way you never get unsupported connections. 26 | - Fully native with 0 dependencies 27 | - Slick looking out of the box 28 | - Ultra simple to create new node classes, want to add class that can be used to apply sqrtf to it's input? 3 lines of code. 29 | 30 | 31 | 32 | ## NodeType creation 33 | Think of NodeTypes like objc classes, they define common behaviour for all instances. 34 | You can create a new node class as follows: 35 | 36 | ```objc 37 | [KZNNodeType registerType:@"sqrtf" inputs:@{ @"Input" : NSNumber.class } outputs:@{ @"Output" : NSNumber.class } processingBlock:^(KZNNode *node, NSDictionary *inputs, NSMutableDictionary *outputs) { 38 | outputs[@"Output"] = @(sqrtf([inputs[@"Input"] floatValue])); 39 | }]; 40 | ``` 41 | 42 | - sqrtf is the name 43 | - it has input socket "Input" that accepts NSNumbers 44 | - it has output socket "Output" that generates NSNumbers 45 | - `Output = sqrtf(input)` 46 | 47 | There are also 2 more advanced creator functions: 48 | 49 | 1. KZNNodeType withClass allows you to change base class used for a node, eg. use node with slider. 50 | 2. KZNNodeType withBuilder allows you to use builder pattern instead of simplified syntax. 51 | 52 | ### Setup block 53 | You can also add setup block which will allow you to further configure new instances of your NodeType, eg. disable continuous slider. 54 | 55 | ## Node evaluation mode 56 | Nodes are lazy evaluated by default, they will only evaluate when there is a change on their sockets or connected nodes. 57 | Changes propagate to connections, so if you modify a node in the beginning of a graph it will propagate to all connected nodes. 58 | 59 | If you mark node type to use continuous evaluation, it will evaluate 60 times per second if possible, eg. time node in sample app. 60 | 61 | ## Built-in node classes 62 | ### KZNNodeWithSlider 63 | ![](/Screenshots/slider.png?raw=true) 64 | 65 | ### KZNNodeWithText 66 | ![](/Screenshots/textfield.png?raw=true) 67 | 68 | ## Adding new node classes 69 | 70 | It's simple: 71 | 72 | 1. Create a subclass of KZNNode 73 | 2. Do whatever you want with it 74 | 3. when you register Node type you can specify your class as baseClass, and reference it in processingBlock. 75 | 76 | 77 | 78 | # Installation and setup 79 | KZNodes is distributed as a [CocoaPod](http://cocoapods.org): 80 | `pod 'KZNodes'` 81 | so you can either add it to your existing project or clone this repository and play with it. 82 | 83 | ## Roadmap & Contributing 84 | 85 | - Serialization of workspaces. 86 | - Idiot-proofing. 87 | - Lazy evaluation of sockets. 88 | 89 | Pull-requests are welcomed. 90 | 91 | It took me around 18h to get from idea to release so the code is likely to change before 1.0 release. 92 | 93 | If you'd like to get specific features [I'm available for iOS consulting](http://www.merowing.info/about/). 94 | 95 | ## Changelog 96 | 97 | ### 0.1.1 98 | - much nicer bezier curves, based on [the-graph](https://github.com/the-grid/the-graph/) 99 | 100 | ### 0.1.0 101 | - initial release 102 | 103 | ## License 104 | 105 | KZNodes is available under the MIT license. See the LICENSE file for more info. 106 | 107 | ## Author 108 | 109 | Krzysztof Zablocki, krzysztof.zablocki@pixle.pl 110 | 111 | [Follow me on twitter.](http://twitter.com/merowing_) 112 | 113 | [Check-out my blog](http://merowing.info) or [GitHub profile](https://github.com/krzysztofzablocki) for more cool stuff. 114 | -------------------------------------------------------------------------------- /Pod/Assets/KZNSocket_Input.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 30 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes-resources.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | mkdir -p "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 5 | 6 | RESOURCES_TO_COPY=${PODS_ROOT}/resources-to-copy-${TARGETNAME}.txt 7 | > "$RESOURCES_TO_COPY" 8 | 9 | install_resource() 10 | { 11 | case $1 in 12 | *.storyboard) 13 | echo "ibtool --reference-external-strings-file --errors --warnings --notices --output-format human-readable-text --compile ${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$1\" .storyboard`.storyboardc ${PODS_ROOT}/$1 --sdk ${SDKROOT}" 14 | ibtool --reference-external-strings-file --errors --warnings --notices --output-format human-readable-text --compile "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$1\" .storyboard`.storyboardc" "${PODS_ROOT}/$1" --sdk "${SDKROOT}" 15 | ;; 16 | *.xib) 17 | echo "ibtool --reference-external-strings-file --errors --warnings --notices --output-format human-readable-text --compile ${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$1\" .xib`.nib ${PODS_ROOT}/$1 --sdk ${SDKROOT}" 18 | ibtool --reference-external-strings-file --errors --warnings --notices --output-format human-readable-text --compile "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$1\" .xib`.nib" "${PODS_ROOT}/$1" --sdk "${SDKROOT}" 19 | ;; 20 | *.framework) 21 | echo "mkdir -p ${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 22 | mkdir -p "${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 23 | echo "rsync -av ${PODS_ROOT}/$1 ${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 24 | rsync -av "${PODS_ROOT}/$1" "${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 25 | ;; 26 | *.xcdatamodel) 27 | echo "xcrun momc \"${PODS_ROOT}/$1\" \"${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$1"`.mom\"" 28 | xcrun momc "${PODS_ROOT}/$1" "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$1" .xcdatamodel`.mom" 29 | ;; 30 | *.xcdatamodeld) 31 | echo "xcrun momc \"${PODS_ROOT}/$1\" \"${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$1" .xcdatamodeld`.momd\"" 32 | xcrun momc "${PODS_ROOT}/$1" "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$1" .xcdatamodeld`.momd" 33 | ;; 34 | *.xcassets) 35 | ;; 36 | /*) 37 | echo "$1" 38 | echo "$1" >> "$RESOURCES_TO_COPY" 39 | ;; 40 | *) 41 | echo "${PODS_ROOT}/$1" 42 | echo "${PODS_ROOT}/$1" >> "$RESOURCES_TO_COPY" 43 | ;; 44 | esac 45 | } 46 | install_resource "../../Pod/Assets/KZNNode.xib" 47 | install_resource "../../Pod/Assets/KZNNodeWithSlider.xib" 48 | install_resource "../../Pod/Assets/KZNNodeWithText.xib" 49 | install_resource "../../Pod/Assets/KZNSocket_Input.xib" 50 | install_resource "../../Pod/Assets/KZNSocket_Output.xib" 51 | install_resource "../../Pod/Assets/KZNWorkspace.xib" 52 | install_resource "../../Pod/Assets/KZNWorkspaceBlockCell.xib" 53 | install_resource "../../Pod/Assets/KZNAssets.xcassets" 54 | install_resource "KZPlayground/Pod/Assets/KZPPresenterInfoViewController.xib" 55 | install_resource "KZPlayground/Pod/Assets/Main.storyboard" 56 | 57 | rsync -avr --copy-links --no-relative --exclude '*/.svn/*' --files-from="$RESOURCES_TO_COPY" / "${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 58 | if [[ "${ACTION}" == "install" ]]; then 59 | rsync -avr --copy-links --no-relative --exclude '*/.svn/*' --files-from="$RESOURCES_TO_COPY" / "${INSTALL_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 60 | fi 61 | rm -f "$RESOURCES_TO_COPY" 62 | 63 | if [[ -n "${WRAPPER_EXTENSION}" ]] && [ "`xcrun --find actool`" ] && [ `find . -name '*.xcassets' | wc -l` -ne 0 ] 64 | then 65 | case "${TARGETED_DEVICE_FAMILY}" in 66 | 1,2) 67 | TARGET_DEVICE_ARGS="--target-device ipad --target-device iphone" 68 | ;; 69 | 1) 70 | TARGET_DEVICE_ARGS="--target-device iphone" 71 | ;; 72 | 2) 73 | TARGET_DEVICE_ARGS="--target-device ipad" 74 | ;; 75 | *) 76 | TARGET_DEVICE_ARGS="--target-device mac" 77 | ;; 78 | esac 79 | find "${PWD}" -name "*.xcassets" -print0 | xargs -0 actool --output-format human-readable-text --notices --warnings --platform "${PLATFORM_NAME}" --minimum-deployment-target "${IPHONEOS_DEPLOYMENT_TARGET}" ${TARGET_DEVICE_ARGS} --compress-pngs --compile "${BUILT_PRODUCTS_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 80 | fi 81 | -------------------------------------------------------------------------------- /Pod/Classes/NodeType/KZNNodeType.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | @import ObjectiveC.runtime; 8 | 9 | #import 10 | #import "KZNNodeType.h" 11 | #import "KZNNode.h" 12 | 13 | static void const *kNodeTypesKey = &kNodeTypesKey; 14 | 15 | @interface KZNNodeType () 16 | @property(nonatomic, strong, readonly) NSMutableArray *inputSocketsBuilders; 17 | @property(nonatomic, strong, readonly) NSMutableArray *outputSocketsBuilders; 18 | @property(nonatomic, assign, readwrite) NSString *name; 19 | @end 20 | 21 | @implementation KZNNodeType 22 | 23 | + (KZNNodeType *)registerType:(NSString *)typeName inputs:(NSDictionary *)inputs outputs:(NSDictionary *)outputs processingBlock:(void (^)(id, NSDictionary *, NSMutableDictionary *))processingBlock 24 | { 25 | return [self registerType:typeName withClass:KZNNode.class inputs:inputs outputs:outputs processingBlock:processingBlock]; 26 | } 27 | 28 | + (KZNNodeType *)registerType:(NSString *)typeName withClass:(Class)nodeClass inputs:(NSDictionary *)inputs outputs:(NSDictionary *)outputs processingBlock:(void (^)(id node, NSDictionary *inputs, NSMutableDictionary *outputs))processingBlock 29 | { 30 | return [self registerType:typeName withBuilder:^(KZNNodeType *type) { 31 | type.baseNodeClass = nodeClass; 32 | [inputs enumerateKeysAndObjectsUsingBlock:(void (^)(id, id, BOOL *))^(NSString *name, Class dataType, BOOL *stop) { 33 | [type addSocket:KZNNodeSocketTypeInput name:name type:dataType]; 34 | }]; 35 | 36 | [outputs enumerateKeysAndObjectsUsingBlock:(void (^)(id, id, BOOL *))^(NSString *name, Class dataType, BOOL *stop) { 37 | [type addSocket:KZNNodeSocketTypeOutput name:name type:dataType]; 38 | }]; 39 | 40 | type.processingBlock = processingBlock; 41 | }]; 42 | } 43 | 44 | + (KZNNodeType *)registerType:(NSString *)typeName withBuilder:(void (^)(KZNNodeType *))builderBlock 45 | { 46 | id __unused existingType = self.nodeTypes[typeName]; 47 | // NSAssert(existingType, @"Can't register node for type %@, already exist", typeName); 48 | 49 | KZNNodeType *type = [KZNNodeType new]; 50 | type.name = typeName; 51 | builderBlock(type); 52 | BOOL isValid = [type validate]; 53 | if (!isValid) { 54 | NSLog(@"Ignoring node type %@, because it's invalid", typeName); 55 | return nil; 56 | } 57 | self.nodeTypes[typeName] = type; 58 | return type; 59 | } 60 | 61 | - (instancetype)init 62 | { 63 | self = [super init]; 64 | if (!self) { 65 | return nil; 66 | } 67 | _inputSocketsBuilders = [NSMutableArray new]; 68 | _outputSocketsBuilders = [NSMutableArray new]; 69 | _baseNodeClass = KZNNode.class; 70 | return self; 71 | } 72 | 73 | 74 | - (void)addSocket:(KZNNodeSocketType)type name:(NSString *)name type:(Class)dataType 75 | { 76 | KZNSocket *(^socketCreationBlock)() = ^() { 77 | return [KZNSocket socketWithName:name socketType:type dataType:dataType]; 78 | }; 79 | 80 | if (type == KZNNodeSocketTypeInput) { 81 | [self.inputSocketsBuilders addObject:socketCreationBlock]; 82 | } else { 83 | [self.outputSocketsBuilders addObject:socketCreationBlock]; 84 | } 85 | } 86 | 87 | - (BOOL)validate 88 | { 89 | if (!self.processingBlock) { 90 | NSLog(@"Missing processing block"); 91 | return NO; 92 | } 93 | 94 | if (!self.inputSocketsBuilders.count && !self.outputSocketsBuilders.count) { 95 | NSLog(@"Either input or output sockets are required"); 96 | return NO; 97 | } 98 | 99 | if (!self.baseNodeClass) { 100 | NSLog(@"invalid node class %@", NSStringFromClass(self.baseNodeClass)); 101 | return NO; 102 | } 103 | 104 | return YES; 105 | } 106 | 107 | #pragma mark - Helpers 108 | 109 | + (NSMutableDictionary *)nodeTypes 110 | { 111 | NSMutableDictionary *nodeTypes = objc_getAssociatedObject(self, kNodeTypesKey); 112 | if (!nodeTypes) { 113 | nodeTypes = [NSMutableDictionary new]; 114 | } 115 | objc_setAssociatedObject(self, kNodeTypesKey, nodeTypes, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 116 | return nodeTypes; 117 | } 118 | 119 | - (KZNNode *)createNode 120 | { 121 | NSMutableArray *inSockets = [NSMutableArray new]; 122 | NSMutableArray *outSockets = [NSMutableArray new]; 123 | for (KZNSocket *(^builder)() 124 | in self.inputSocketsBuilders) { 125 | [inSockets addObject:builder()]; 126 | } 127 | 128 | for (KZNSocket *(^builder)() 129 | in self.outputSocketsBuilders) { 130 | [outSockets addObject:builder()]; 131 | } 132 | 133 | KZNNode *node = [self.baseNodeClass nodeWithType:self inputSockets:inSockets outputSockets:outSockets]; 134 | if (self.nodeSetup) { 135 | self.nodeSetup(node); 136 | } 137 | return node; 138 | } 139 | 140 | @end 141 | -------------------------------------------------------------------------------- /Example/Pods/NHBalancedFlowLayout/NHBalancedFlowLayout/NHLinearPartition.m: -------------------------------------------------------------------------------- 1 | // 2 | // LinearPartition.m 3 | // BalancedFlowLayout 4 | // 5 | // Created by Niels de Hoog on 08-10-13. 6 | // Copyright (c) 2013 Niels de Hoog. All rights reserved. 7 | // 8 | 9 | #import "NHLinearPartition.h" 10 | 11 | 12 | #define NH_LP_TABLE_LOOKUP(table, i, j, rowsize) (table)[(i) * (rowsize) + (j)] 13 | 14 | 15 | @implementation NHLinearPartition 16 | 17 | /** 18 | * Returns a solution integer array for the linear partition problem 19 | * 20 | * @param sequence An array of NSNumber's 21 | * @param numPartitions The number of partitions wanted 22 | * 23 | * @return A C-style solution table 24 | */ 25 | + (NSInteger *)linearPartitionTable:(NSArray *)sequence numPartitions:(NSInteger)numPartitions 26 | { 27 | NSInteger k = numPartitions; 28 | NSInteger n = [sequence count]; 29 | 30 | // allocate a table buffer of n * k integers 31 | NSInteger tableSize = sizeof(NSInteger) * n * k; 32 | NSInteger *tmpTable = (NSInteger *)malloc(tableSize); 33 | memset(tmpTable, 0, tableSize); 34 | 35 | // allocate a solution buffer of (n - 1) * (k - 1) integers 36 | NSInteger solutionSize = sizeof(NSInteger) * (n - 1) * (k - 1); 37 | NSInteger *solution = (NSInteger *)malloc(solutionSize); 38 | memset(solution, 0, solutionSize); 39 | 40 | // fill table with initial values 41 | for (NSInteger i = 0; i < n; i++) { 42 | NSInteger offset = i? NH_LP_TABLE_LOOKUP(tmpTable, i - 1, 0, k) : 0; 43 | NH_LP_TABLE_LOOKUP(tmpTable, i, 0, k) = [sequence[i] integerValue] + offset; 44 | } 45 | 46 | for (NSInteger j = 0; j < k; j++) { 47 | NH_LP_TABLE_LOOKUP(tmpTable, 0, j, k) = [sequence[0] integerValue]; 48 | } 49 | 50 | // calculate the costs and fill the solution buffer 51 | for (NSInteger i = 1; i < n; i++) { 52 | for (NSInteger j = 1; j < k; j++) { 53 | NSInteger currentMin = 0; 54 | NSInteger minX = NSIntegerMax; 55 | 56 | for (NSInteger x = 0; x < i; x++) { 57 | NSInteger c1 = NH_LP_TABLE_LOOKUP(tmpTable, x, j - 1, k); 58 | NSInteger c2 = NH_LP_TABLE_LOOKUP(tmpTable, i, 0, k) - NH_LP_TABLE_LOOKUP(tmpTable, x, 0, k); 59 | NSInteger cost = MAX(c1, c2); 60 | 61 | if (!x || cost < currentMin) { 62 | currentMin = cost; 63 | minX = x; 64 | } 65 | } 66 | 67 | NH_LP_TABLE_LOOKUP(tmpTable, i, j, k) = currentMin; 68 | NH_LP_TABLE_LOOKUP(solution, i - 1, j - 1, k - 1) = minX; 69 | } 70 | } 71 | 72 | // free the tmp table, we don't need it anymore 73 | free(tmpTable); 74 | 75 | return solution; 76 | } 77 | 78 | + (NSArray *)linearPartitionForSequence:(NSArray *)sequence numberOfPartitions:(NSInteger)numberOfPartitions 79 | { 80 | NSInteger n = [sequence count]; 81 | NSInteger k = numberOfPartitions; 82 | 83 | if (k <= 0) return @[]; 84 | 85 | if (k >= n) { 86 | NSMutableArray *partition = [[NSMutableArray alloc] init]; 87 | [sequence enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) { 88 | [partition addObject:@[obj]]; 89 | }]; 90 | return [partition copy]; 91 | } 92 | 93 | if (n == 1) { 94 | return @[sequence]; 95 | } 96 | 97 | // get the solution table 98 | NSInteger *solution = [self linearPartitionTable:sequence numPartitions:numberOfPartitions]; 99 | NSInteger solutionRowSize = numberOfPartitions - 1; 100 | 101 | k = k - 2; 102 | n = n - 1; 103 | NSMutableArray *answer = [NSMutableArray array]; 104 | 105 | while (k >= 0) { 106 | if (n < 1) { 107 | [answer insertObject:@[] atIndex:0]; 108 | } else { 109 | NSMutableArray *currentAnswer = [NSMutableArray array]; 110 | for (NSInteger i = NH_LP_TABLE_LOOKUP(solution, n - 1, k, solutionRowSize) + 1, range = n + 1; i < range; i++) { 111 | [currentAnswer addObject:sequence[i]]; 112 | } 113 | [answer insertObject:currentAnswer atIndex:0]; 114 | 115 | n = NH_LP_TABLE_LOOKUP(solution, n - 1, k, solutionRowSize); 116 | } 117 | 118 | k = k - 1; 119 | } 120 | 121 | // free the solution table because we don't need it anymore 122 | free(solution); 123 | 124 | NSMutableArray *currentAnswer = [NSMutableArray array]; 125 | for (NSInteger i = 0, range = n + 1; i < range; i++) { 126 | [currentAnswer addObject:sequence[i]]; 127 | } 128 | 129 | [answer insertObject:currentAnswer atIndex:0]; 130 | 131 | return [answer copy]; 132 | } 133 | 134 | @end 135 | 136 | 137 | 138 | -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/NSObject+DyCInjection.m: -------------------------------------------------------------------------------- 1 | // 2 | // NSObject+DyCInjection(DCInjection) 3 | // Dynamic Code Injection 4 | // 5 | // Created by Paul Taykalo on 10/21/12. 6 | // Copyright (c) 2012 Stanfy LLC. All rights reserved. 7 | // 8 | 9 | #if TARGET_IPHONE_SIMULATOR 10 | 11 | #import 12 | #import "NSObject+DyCInjection.h" 13 | //#import "SFDynamicCodeInjection.h" 14 | #import "SFInjectionsNotificationsCenter.h" 15 | 16 | 17 | void swizzle(Class c, SEL orig, SEL new) { 18 | Method origMethod = class_getInstanceMethod(c, orig); 19 | Method newMethod = class_getInstanceMethod(c, new); 20 | if (class_addMethod(c, orig, method_getImplementation(newMethod), method_getTypeEncoding(newMethod))) { 21 | class_replaceMethod(c, new, method_getImplementation(origMethod), method_getTypeEncoding(origMethod)); 22 | } else { 23 | method_exchangeImplementations(origMethod, newMethod); 24 | } 25 | } 26 | 27 | 28 | @interface NSObject (DyCInjectionObserver) 29 | 30 | @end 31 | 32 | 33 | @implementation NSObject (DyCInjection) 34 | 35 | #pragma mark - Swizzling 36 | 37 | + (void)allowInjectionSubscriptionOnInitMethod { 38 | swizzle([NSObject class], @selector(init), @selector(_swizzledInit)); 39 | swizzle([NSObject class], NSSelectorFromString(@"dealloc"), @selector(_swizzledDealloc)); 40 | 41 | // Storyboard support 42 | swizzle(NSClassFromString(@"UINib"), @selector(instantiateWithOwner:options:), @selector(_swizzledInstantiateWithOwner:options:)); 43 | } 44 | 45 | 46 | #pragma mark - Subscription check 47 | 48 | + (BOOL)shouldPerformRuntimeCodeInjectionOnObject:(__unsafe_unretained id)instance { 49 | if (!instance) { 50 | return NO; 51 | } 52 | 53 | #warning We should skip more than just NS, CF, and private classes 54 | char const * className = object_getClassName(instance); 55 | 56 | switch (className[0]) { 57 | case '_': 58 | return NO; 59 | case 'N': 60 | if (className[1] == 'S') { 61 | return NO; 62 | } 63 | break; 64 | case 'C': 65 | if (className[1] == 'A' || 66 | className[1] == 'F' ) { 67 | return NO; 68 | } 69 | break; 70 | case 'U': 71 | if (className[1] == 'I') { 72 | // Allowing to inject UIViewControllers 73 | if (strcmp(className, "UIViewController") == 0) { 74 | return YES; 75 | } 76 | if (strcmp(className, "UITableViewController") == 0) { 77 | return YES; 78 | } 79 | return NO; 80 | } 81 | break; 82 | case 'W': 83 | if (className[1] == 'e' && className[2] == 'b') { 84 | return NO; 85 | } 86 | break; 87 | case 'D': 88 | if (className[1] == 'O' && className[2] == 'M') { 89 | return NO; 90 | } 91 | break; 92 | case 'S': 93 | if (className[1] == 'F' && className[2] == 'I' && className[3] == 'n' && className[4] == 'j') { 94 | return NO; 95 | } 96 | break; 97 | case 'O': 98 | if (className[1] == 'S' && className[2] == '_') { 99 | return NO; 100 | } 101 | break; 102 | 103 | default: 104 | break; 105 | } 106 | 107 | // Disable injection on NSManagedObject object classes 108 | // They have slightly different lifecycle... 109 | Class clz = NSClassFromString(@"NSManagedObject"); 110 | if (clz && [instance isKindOfClass:clz]) { 111 | return NO; 112 | } 113 | 114 | return YES; 115 | } 116 | 117 | #pragma mark - On Injection methods 118 | 119 | - (void)updateOnClassInjection { 120 | 121 | } 122 | 123 | 124 | - (void)updateOnResourceInjection:(NSString *)resourcePath { 125 | 126 | } 127 | 128 | 129 | #pragma mark - Swizzled methods 130 | 131 | - (id)_swizzledInit { 132 | 133 | // Calling previous init 134 | 135 | id result = self; 136 | result = [result _swizzledInit]; 137 | 138 | if (result) { 139 | 140 | // In case, if we are in need to inject 141 | if ([NSObject shouldPerformRuntimeCodeInjectionOnObject:result]) { 142 | SFInjectionsNotificationsCenter * notificationCenter = [SFInjectionsNotificationsCenter sharedInstance]; 143 | [notificationCenter addObserver:result]; 144 | } 145 | 146 | } 147 | return result; 148 | } 149 | 150 | - (void)_swizzledDealloc { 151 | 152 | if ([NSObject shouldPerformRuntimeCodeInjectionOnObject:self]) { 153 | [[SFInjectionsNotificationsCenter sharedInstance] removeObserver:self]; 154 | } 155 | 156 | // Swizzled methods are fun 157 | // Calling previous dealloc implementation 158 | [self _swizzledDealloc]; 159 | 160 | } 161 | 162 | @end 163 | 164 | #endif 165 | -------------------------------------------------------------------------------- /Pod/Classes/Socket/KZNSocket.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by merowing on 29/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import "KZNSocket.h" 9 | #import "KZNSocket+Internal.h" 10 | #import "KZNNode.h" 11 | #import "KZNWorkspace.h" 12 | 13 | @interface KZNSocket () 14 | @property(weak, nonatomic) IBOutlet UIButton *socketButton; 15 | @property(weak, nonatomic) IBOutlet UILabel *label; 16 | @end 17 | 18 | @implementation KZNSocket 19 | + (UINib *)matchingNibForSocketType:(KZNNodeSocketType)type 20 | { 21 | NSString *nibName = [NSString stringWithFormat:@"%@_%@", NSStringFromClass(self.class), type == KZNNodeSocketTypeInput ? @"Input" : @"Output"]; 22 | 23 | if ([[NSBundle mainBundle] pathForResource:nibName ofType:@"nib"]) { 24 | return [UINib nibWithNibName:nibName bundle:[NSBundle mainBundle]]; 25 | } 26 | 27 | nibName = [NSString stringWithFormat:@"%@_%@", NSStringFromClass(KZNSocket.class), type == KZNNodeSocketTypeInput ? @"Input" : @"Output"]; 28 | return [UINib nibWithNibName:nibName bundle:[NSBundle bundleForClass:self.class]]; 29 | } 30 | 31 | + (instancetype)socketWithName:(NSString *)name socketType:(KZNNodeSocketType)socketType dataType:(Class)type 32 | { 33 | UINib *nib = [self matchingNibForSocketType:socketType]; 34 | 35 | KZNSocket *socket = [self new]; 36 | UIView *containerView = [[nib instantiateWithOwner:socket options:nil] firstObject]; 37 | socket.bounds = containerView.bounds; 38 | [socket addSubview:containerView]; 39 | if (!socket) { 40 | return nil; 41 | } 42 | 43 | [socket setupWithName:name socketType:socketType dataType:type]; 44 | return socket; 45 | } 46 | 47 | - (void)setupWithName:(NSString *)name socketType:(KZNNodeSocketType)socketType dataType:(Class)type 48 | { 49 | _name = [name copy]; 50 | _socketType = socketType; 51 | _type = type; 52 | _connections = [NSMutableSet new]; 53 | 54 | self.extraSpace = CGRectGetWidth(self.bounds) - CGRectGetWidth(self.label.bounds); 55 | 56 | self.label.text = [_name uppercaseString]; 57 | self.socketButton.adjustsImageWhenDisabled = NO; 58 | self.socketButton.adjustsImageWhenHighlighted = NO; 59 | self.socketButton.enabled = NO; 60 | 61 | [self sizeToFit]; 62 | } 63 | 64 | - (void)addConnectionToSocket:(KZNSocket *)inputSocket 65 | { 66 | NSParameterAssert(inputSocket.socketType == KZNNodeSocketTypeInput); 67 | NSParameterAssert(self.socketType == KZNNodeSocketTypeOutput); 68 | 69 | if (inputSocket.socketType == KZNNodeSocketTypeInput) { 70 | [(NSMutableSet *)self.connections addObject:inputSocket]; 71 | inputSocket.sourceSocket = self; 72 | } 73 | } 74 | 75 | - (void)removeConnectionToSocket:(KZNSocket *)inputSocket 76 | { 77 | NSParameterAssert(inputSocket.socketType == KZNNodeSocketTypeInput); 78 | [(NSMutableSet *)self.connections removeObject:inputSocket]; 79 | inputSocket.sourceSocket = nil; 80 | } 81 | 82 | 83 | - (void)setSourceSocket:(KZNSocket *)sourceSocket 84 | { 85 | NSParameterAssert(self.socketType == KZNNodeSocketTypeInput); 86 | NSParameterAssert(!sourceSocket || sourceSocket.socketType == KZNNodeSocketTypeOutput); 87 | 88 | [(NSMutableSet *)self.connections removeAllObjects]; 89 | if (sourceSocket) { 90 | [(NSMutableSet *)self.connections addObject:sourceSocket]; 91 | } 92 | 93 | [UIView transitionWithView:self.socketButton.imageView duration:0.25 options:UIViewAnimationOptionTransitionCrossDissolve animations:^{ 94 | BOOL connected = sourceSocket != nil; 95 | self.socketButton.selected = connected; 96 | self.socketButton.enabled = connected; 97 | } completion:nil]; 98 | } 99 | 100 | - (IBAction)pressedSocket:(id)sender 101 | { 102 | [self.parent.workspace pressedSocket:self]; 103 | } 104 | 105 | - (KZNSocket *)sourceSocket 106 | { 107 | NSParameterAssert(self.socketType == KZNNodeSocketTypeInput); 108 | NSParameterAssert([self.connections count] <= 1); 109 | return [self.connections anyObject]; 110 | } 111 | 112 | - (CGPoint)socketCenter 113 | { 114 | return self.socketButton.center; 115 | } 116 | 117 | - (BOOL)canConnectToSocket:(KZNSocket *)other 118 | { 119 | if (self.socketType != KZNNodeSocketTypeOutput || other.socketType != KZNNodeSocketTypeInput) { 120 | return NO; 121 | } 122 | 123 | Class curClass = self.type; 124 | while (curClass) { 125 | if (curClass == other.type) { 126 | return YES; 127 | } 128 | curClass = curClass.superclass; 129 | } 130 | 131 | return NO; 132 | } 133 | 134 | - (void)setCompatible:(BOOL)isCompatible 135 | { 136 | [UIView transitionWithView:self.socketButton.imageView duration:0.3 options:UIViewAnimationOptionTransitionCrossDissolve animations:^{ 137 | self.socketButton.imageView.alpha = isCompatible ? 1.0f : 0.1f; 138 | } completion:nil]; 139 | } 140 | 141 | - (CGSize)sizeThatFits:(CGSize)size 142 | { 143 | CGSize labelSize = [self.label sizeThatFits:size]; 144 | labelSize.width += self.extraSpace; 145 | CGSize s = [super sizeThatFits:size]; 146 | s.width = labelSize.width; 147 | return s; 148 | } 149 | 150 | @end 151 | -------------------------------------------------------------------------------- /Pod/Assets/KZNSocket_Output.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 33 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Controls/ValueAdjust/KZPValueAdjustComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import "KZPValueAdjustComponent.h" 9 | #import "KZPTimelineViewController.h" 10 | 11 | @import ObjectiveC.runtime; 12 | 13 | #import 14 | 15 | static const void *kLastValuesKey = &kLastValuesKey; 16 | static const void *kAdjusterLifetimeKey = &kAdjusterLifetimeKey; 17 | 18 | extern KZPValueAdjustComponent *__attribute__((overloadable)) KZPAdjust(NSString *name, int from, int to, void (^block)(int)) { 19 | return [KZPValueAdjustComponent addValueAdjustWithName:name fromValue:from toValue:to withBlock:^(CGFloat d) { 20 | int rounded = (int)roundf(d); 21 | block(rounded); 22 | return (CGFloat)rounded; 23 | }]; 24 | } 25 | 26 | extern KZPValueAdjustComponent *__attribute__((overloadable)) KZPAdjust(NSString *name, float from, float to, void (^block)(float)) { 27 | return [KZPValueAdjustComponent addValueAdjustWithName:name fromValue:(CGFloat)from toValue:(CGFloat)to withBlock:^CGFloat(CGFloat d) { 28 | block((float)d); 29 | return d; 30 | }]; 31 | } 32 | 33 | 34 | @interface KZPValueAdjustComponent () 35 | @property(nonatomic, weak) UISlider *valueSlider; 36 | @property(nonatomic, weak) UILabel *nameLabel; 37 | @property(nonatomic, copy) NSString *name; 38 | @property(nonatomic, copy) CGFloat (^changeBlock)(CGFloat); 39 | @end 40 | 41 | @implementation KZPValueAdjustComponent 42 | 43 | + (KZPValueAdjustComponent *)addValueAdjustWithName:(NSString *)name fromValue:(CGFloat)from toValue:(CGFloat)to withBlock:(CGFloat (^)(CGFloat))block 44 | { 45 | return [[KZPValueAdjustComponent alloc] initWithName:name fromValue:from toValue:to changeBlock:block]; 46 | } 47 | 48 | - (instancetype)initWithName:(NSString *)name fromValue:(CGFloat)fromValue toValue:(CGFloat)toValue changeBlock:(CGFloat (^)(CGFloat))changeBlock 49 | { 50 | self = [super init]; 51 | if (!self) { 52 | return nil; 53 | } 54 | 55 | KZPTimelineViewController *timelineViewController = [KZPTimelineViewController sharedInstance]; 56 | CGFloat controlWidth = timelineViewController.maxWidthForSnapshotView; 57 | 58 | UISlider *slider = [self createSliderWithWidth:controlWidth minValue:fromValue maxValue:toValue]; 59 | UILabel *nameLabel = [self createNameLabelWithWidth:controlWidth]; 60 | 61 | self.name = name; 62 | self.valueSlider = slider; 63 | self.nameLabel = nameLabel; 64 | self.changeBlock = changeBlock; 65 | 66 | [slider addTarget:self action:@selector(sliderChanged:) forControlEvents:UIControlEventValueChanged]; 67 | 68 | [timelineViewController addView:nameLabel]; 69 | [timelineViewController addView:slider]; 70 | 71 | //! bind adjuster lifetime to the slider itself 72 | objc_setAssociatedObject(slider, kAdjusterLifetimeKey, self, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 73 | 74 | NSNumber *previousValue = self.class.lastValues[name]; 75 | float value = previousValue ? previousValue.floatValue : fromValue; 76 | [self setCurrentValueWithoutPersistence:value]; 77 | 78 | return self; 79 | } 80 | 81 | - (void (^)(CGFloat))defaultValue 82 | { 83 | __weak typeof(self) weakSelf = self; 84 | return ^(CGFloat value) { 85 | __strong typeof(weakSelf) strongSelf = weakSelf; 86 | BOOL isInitializing = ![strongSelf.class lastValues][strongSelf.name]; 87 | if (isInitializing) { 88 | [strongSelf setCurrentValueWithoutPersistence:value]; 89 | } 90 | }; 91 | 92 | } 93 | 94 | - (UISlider *)createSliderWithWidth:(CGFloat)sliderWidth minValue:(CGFloat)minValue maxValue:(CGFloat)maxValue 95 | { 96 | UISlider *slider = [[UISlider alloc] initWithFrame:CGRectMake(0, 0, sliderWidth, 44)]; 97 | slider.minimumValue = minValue; 98 | slider.maximumValue = maxValue; 99 | [slider sizeToFit]; 100 | return slider; 101 | } 102 | 103 | - (UILabel *)createNameLabelWithWidth:(CGFloat)width 104 | { 105 | UILabel *nameLabel = [UILabel new]; 106 | nameLabel.textColor = [UIColor blackColor]; 107 | nameLabel.textAlignment = NSTextAlignmentCenter; 108 | nameLabel.text = @"Sizing"; 109 | [nameLabel sizeToFit]; 110 | nameLabel.frame = CGRectMake(0, 0, width, CGRectGetHeight(nameLabel.bounds)); 111 | return nameLabel; 112 | } 113 | 114 | - (void)setCurrentValueWithoutPersistence:(CGFloat)value 115 | { 116 | CGFloat adjustedValue = self.changeBlock(value); 117 | [self.valueSlider setValue:adjustedValue]; 118 | self.nameLabel.text = [NSString stringWithFormat:@"%@ %.2f", self.name, adjustedValue]; 119 | } 120 | 121 | - (void)sliderChanged:(UISlider *)sliderChanged 122 | { 123 | CGFloat adjustedValue = self.changeBlock(sliderChanged.value); 124 | self.nameLabel.text = [NSString stringWithFormat:@"%@ %.2f", self.name, adjustedValue]; 125 | self.class.lastValues[self.name] = @(adjustedValue); 126 | } 127 | 128 | #pragma mark - Helpers 129 | 130 | + (NSMutableDictionary *)lastValues 131 | { 132 | NSMutableDictionary *lastValues = objc_getAssociatedObject(self, kLastValuesKey); 133 | if (!lastValues) { 134 | lastValues = [NSMutableDictionary new]; 135 | objc_setAssociatedObject(self, kLastValuesKey, lastValues, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 136 | } 137 | return lastValues; 138 | } 139 | 140 | + (void)reset 141 | { 142 | } 143 | 144 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Images/ImagePicker/AssetBrowser/KZPImagePickerCollectionViewController.m: -------------------------------------------------------------------------------- 1 | #import "KZPImagePickerCollectionViewController.h" 2 | #import "NHBalancedFlowLayout.h" 3 | 4 | @interface CUICommonAssetStorage : NSObject 5 | 6 | - (NSArray *)allAssetKeys; 7 | 8 | - (NSArray *)allRenditionNames; 9 | 10 | - (id)initWithPath:(NSString *)p; 11 | 12 | - (NSString *)versionString; 13 | 14 | @end 15 | 16 | @interface CUINamedImage : NSObject 17 | 18 | - (CGImageRef)image; 19 | 20 | @end 21 | 22 | @interface CUIRenditionKey : NSObject 23 | @end 24 | 25 | @interface CUIThemeFacet : NSObject 26 | 27 | + (unsigned long long)themeWithContentsOfURL:(NSURL *)u error:(NSError **)e; 28 | 29 | @end 30 | 31 | @interface CUICatalog : NSObject 32 | 33 | - (id)initWithName:(NSString *)n fromBundle:(NSBundle *)b; 34 | 35 | - (id)allKeys; 36 | 37 | - (NSArray *)allImageNames; 38 | 39 | - (CUINamedImage *)imageWithName:(NSString *)n scaleFactor:(CGFloat)s; 40 | 41 | - (CUINamedImage *)imageWithName:(NSString *)n scaleFactor:(CGFloat)s deviceIdiom:(int)idiom; 42 | 43 | @end 44 | 45 | 46 | @implementation KZPImagePickerCollectionViewCell 47 | 48 | - (instancetype)initWithFrame:(CGRect)frame 49 | { 50 | self = [super initWithFrame:frame]; 51 | if (self) { 52 | [self setupViews]; 53 | } 54 | 55 | return self; 56 | } 57 | 58 | - (void)prepareForReuse 59 | { 60 | self.imageView.image = nil; 61 | self.titleLabel.text = nil; 62 | } 63 | 64 | - (void)setupViews 65 | { 66 | UIImageView *imageView = [[UIImageView alloc] initWithFrame:self.contentView.bounds]; 67 | imageView.contentMode = UIViewContentModeScaleAspectFit; 68 | self.imageView = imageView; 69 | [self.contentView addSubview:self.imageView]; 70 | 71 | UILabel *label = [UILabel new]; 72 | label.textColor = UIColor.whiteColor; 73 | label.textAlignment = NSTextAlignmentCenter; 74 | self.titleLabel = label; 75 | [self.contentView addSubview:label]; 76 | } 77 | 78 | - (void)layoutSubviews 79 | { 80 | [super layoutSubviews]; 81 | const NSUInteger labelHeight = 44; 82 | 83 | CGRect bounds = self.contentView.bounds; 84 | bounds.size.height -= labelHeight; 85 | self.imageView.frame = bounds; 86 | self.titleLabel.frame = CGRectMake(0, CGRectGetHeight(bounds), CGRectGetWidth(bounds), labelHeight); 87 | } 88 | @end 89 | 90 | @interface KZPImagePickerCollectionViewController () 91 | 92 | @property(nonatomic, copy) NSArray *imageNames; 93 | @property(nonatomic, copy) NSArray *images; 94 | @end 95 | 96 | @implementation KZPImagePickerCollectionViewController 97 | 98 | - (void)viewWillAppear:(BOOL)animated 99 | { 100 | [super viewWillAppear:animated]; 101 | [self.collectionView registerClass:KZPImagePickerCollectionViewCell.class forCellWithReuseIdentifier:@"ImageCell"]; 102 | [self loadImages]; 103 | } 104 | 105 | - (void)loadImages 106 | { 107 | NSString *carPath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:@"Assets.car"]; 108 | CUICatalog *catalog = [[NSClassFromString(@"CUICatalog") alloc] init]; 109 | NSError *error = nil; 110 | Class facetClass = NSClassFromString(@"CUIThemeFacet"); 111 | NSURL *url = [NSURL fileURLWithPath:carPath]; 112 | unsigned long long facet = [facetClass themeWithContentsOfURL:url error:&error]; 113 | /* Override CUICatalog to point to a file rather than a bundle */ 114 | [catalog setValue:@(facet) forKey:@"_storageRef"]; 115 | 116 | self.imageNames = [catalog allImageNames]; 117 | } 118 | 119 | - (void)setImageNames:(NSArray *)imageNames 120 | { 121 | NSMutableArray *images = [[NSMutableArray alloc] init]; 122 | for (int i = 0; i < imageNames.count; i++) { 123 | [images addObject:[UIImage imageNamed:imageNames[i]]]; 124 | } 125 | self.images = images; 126 | _imageNames = [imageNames copy]; 127 | [self.collectionView reloadData]; 128 | } 129 | 130 | #pragma mark - UICollectionViewFlowLayoutDelegate 131 | 132 | - (CGSize)collectionView:(UICollectionView *)collectionView layout:(NHBalancedFlowLayout *)collectionViewLayout preferredSizeForItemAtIndexPath:(NSIndexPath *)indexPath 133 | { 134 | CGSize size = [self.images[(NSUInteger)indexPath.item] size]; 135 | return size; 136 | } 137 | 138 | #pragma mark - UICollectionView data source 139 | 140 | - (NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView 141 | { 142 | return 1; 143 | } 144 | 145 | - (NSInteger)collectionView:(UICollectionView *)view numberOfItemsInSection:(NSInteger)section; 146 | { 147 | return [self.images count]; 148 | } 149 | 150 | - (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath; 151 | { 152 | KZPImagePickerCollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"ImageCell" forIndexPath:indexPath]; 153 | 154 | NSUInteger index = (NSUInteger)indexPath.item; 155 | //! TODO: add image decompression to avoid the decompression lag on first draw 156 | cell.imageView.image = self.images[index]; 157 | cell.titleLabel.text = self.imageNames[index]; 158 | return cell; 159 | } 160 | 161 | - (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath 162 | { 163 | if (self.onSelectionBlock) { 164 | self.onSelectionBlock(self.images[(NSUInteger)indexPath.item]); 165 | } 166 | [self dismissViewControllerAnimated:YES completion:nil]; 167 | } 168 | 169 | - (IBAction)cancel:(id)sender { 170 | [self dismissViewControllerAnimated:YES completion:nil]; 171 | } 172 | 173 | @end -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Playground/KZPPlaygroundViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 19/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import 9 | #import 10 | #import "KZPTimelineViewController.h" 11 | #import "KZPPlayground+Internal.h" 12 | 13 | @interface KZPPlaygroundViewController () 14 | @property(weak, nonatomic) IBOutlet UIView *timelineContainerView; 15 | @property(weak, nonatomic) IBOutlet UIView *worksheetContainerView; 16 | @property(strong, nonatomic) KZPPlayground *currentPlayground; 17 | @property(unsafe_unretained, nonatomic) IBOutlet NSLayoutConstraint *leadingTimelineConstraint; 18 | @end 19 | 20 | @implementation KZPPlaygroundViewController 21 | 22 | + (KZPPlaygroundViewController *)playgroundViewController 23 | { 24 | return [[UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle bundleForClass:self]] instantiateInitialViewController]; 25 | } 26 | 27 | - (void)setTimelineHidden:(BOOL)hidden 28 | { 29 | _timelineHidden = hidden; 30 | 31 | if ([self isViewLoaded]) { 32 | if (hidden) { 33 | self.leadingTimelineConstraint.constant = -CGRectGetWidth(self.timelineContainerView.bounds); 34 | } else { 35 | self.leadingTimelineConstraint.constant = 0; 36 | } 37 | [self.view layoutIfNeeded]; 38 | } 39 | } 40 | 41 | 42 | - (void)dealloc 43 | { 44 | [[NSNotificationCenter defaultCenter] removeObserver:self name:KZPPlaygroundDidChangeImplementationNotification object:nil]; 45 | } 46 | 47 | - (void)awakeFromNib 48 | { 49 | [super awakeFromNib]; 50 | [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(playgroundImplementationChanged) name:KZPPlaygroundDidChangeImplementationNotification object:nil]; 51 | } 52 | 53 | - (void)viewDidAppear:(BOOL)animated 54 | { 55 | [super viewDidAppear:animated]; 56 | 57 | static dispatch_once_t onceToken; 58 | dispatch_once(&onceToken, ^{ 59 | [KZPTimelineViewController setSharedInstance:self.timelineViewController]; 60 | self.timelineHidden = self.timelineHidden; 61 | self.currentPlayground = [self createActivePlayground]; 62 | [self.timelineViewController playgroundSetupCompleted]; 63 | [self executePlayground]; 64 | }); 65 | } 66 | 67 | - (KZPPlayground *)createActivePlayground 68 | { 69 | NSArray *playgrounds = [self findClassesConformingToProtocol:@protocol(KZPActivePlayground)]; 70 | NSAssert(playgrounds.count == 1, @"One KZPPlayground subclass needs to conform to KZPActivePlayground, it will be the active playground for the current run."); 71 | KZPPlayground *playground = (KZPPlayground *)[playgrounds.firstObject new]; 72 | NSAssert([playground isKindOfClass:KZPPlayground.class], @"Class conforming to KZPActivePlayground has to be a subclass of KZPPlayground."); 73 | return playground; 74 | } 75 | 76 | - (void)reset 77 | { 78 | self.currentPlayground.worksheetView = [self cleanWorksheet]; 79 | self.currentPlayground.viewController = self; 80 | self.currentPlayground.playgroundViewController = self; 81 | [self.currentPlayground.transientObjects removeAllObjects]; 82 | [self dismissViewControllerAnimated:NO completion:nil]; 83 | 84 | [self.timelineViewController reset]; 85 | [[self findClassesConformingToProtocol:@protocol(KZPComponent)] enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) { 86 | [obj reset]; 87 | }]; 88 | } 89 | 90 | - (UIView *)cleanWorksheet 91 | { 92 | [self.worksheetContainerView.subviews makeObjectsPerformSelector:@selector(removeFromSuperview)]; 93 | UIView *worksheetView = [[UIView alloc] initWithFrame:self.worksheetContainerView.bounds]; 94 | worksheetView.clipsToBounds = YES; 95 | worksheetView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; 96 | worksheetView.backgroundColor = UIColor.lightGrayColor; 97 | [self.worksheetContainerView addSubview:worksheetView]; 98 | return worksheetView; 99 | } 100 | 101 | - (void)executePlayground 102 | { 103 | [self reset]; 104 | [self.currentPlayground run]; 105 | [self playgroundDidRun]; 106 | } 107 | 108 | - (void)playgroundDidRun 109 | { 110 | [self.timelineViewController playgroundDidRun]; 111 | } 112 | 113 | - (void)playgroundImplementationChanged 114 | { 115 | [self setNeedsExecutePlayground]; 116 | } 117 | 118 | - (void)setNeedsExecutePlayground 119 | { 120 | [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(executePlayground) object:nil]; 121 | [self performSelector:@selector(executePlayground) withObject:nil afterDelay:0]; 122 | } 123 | 124 | #pragma mark - Helpers 125 | 126 | - (NSArray *)findClassesConformingToProtocol:(Protocol *)protocol 127 | { 128 | int numberOfClasses = objc_getClassList(NULL, 0); 129 | Class *classes; 130 | 131 | classes = (Class *)malloc(sizeof(Class) * numberOfClasses); 132 | objc_getClassList(classes, numberOfClasses); 133 | 134 | NSMutableArray *conformingClasses = [NSMutableArray array]; 135 | for (NSInteger i = 0; i < numberOfClasses; i++) { 136 | Class lClass = classes[i]; 137 | if (class_conformsToProtocol(lClass, protocol)) { 138 | [conformingClasses addObject:classes[i]]; 139 | } 140 | } 141 | 142 | free(classes); 143 | return [conformingClasses copy]; 144 | } 145 | 146 | - (KZPTimelineViewController *)timelineViewController 147 | { 148 | return [self controllerOfClass:KZPTimelineViewController.class]; 149 | } 150 | 151 | - (id)controllerOfClass:(Class)aClass 152 | { 153 | for (UIViewController *controller in self.childViewControllers) { 154 | if ([controller isKindOfClass:aClass]) { 155 | return controller; 156 | } 157 | } 158 | 159 | return nil; 160 | } 161 | @end 162 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Timeline/KZPTimelineViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 19/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import "KZPTimelineViewController.h" 9 | #import "KZPSnapshotView.h" 10 | #import "KZPPlayground.h" 11 | 12 | @import ObjectiveC.runtime; 13 | 14 | #import 15 | 16 | static const NSInteger kVerticalMargin = 10; 17 | static const NSInteger kHorizontalMargin = 10; 18 | static const NSInteger kInfoButtonMargin = 10; 19 | 20 | static const void *kSnapshotViewKey = &kSnapshotViewKey; 21 | 22 | static KZPTimelineViewController *_singleton = nil; 23 | 24 | @interface KZPTimelineViewController () 25 | @property(weak, nonatomic) IBOutlet UILabel *tickLabel; 26 | @property(nonatomic, weak) IBOutlet UIScrollView *scrollView; 27 | @property(nonatomic, strong) NSMutableArray *snapshotViews; 28 | @property(nonatomic, copy) NSArray *persistedSnapshotViews; 29 | @property(nonatomic, strong) UIPopoverController *currentPopoverController; 30 | @end 31 | 32 | @implementation KZPTimelineViewController 33 | 34 | + (KZPTimelineViewController *)sharedInstance 35 | { 36 | NSAssert(_singleton, @"KZPTimelineViewController has to be set before it's instance is referenced."); 37 | return _singleton; 38 | } 39 | 40 | + (void)setSharedInstance:(KZPTimelineViewController *)sharedInstance 41 | { 42 | _singleton = sharedInstance; 43 | } 44 | 45 | - (void)awakeFromNib 46 | { 47 | [super awakeFromNib]; 48 | self.snapshotViews = [NSMutableArray new]; 49 | self.persistedSnapshotViews = [NSArray new]; 50 | } 51 | 52 | - (void)addView:(UIView *)view 53 | { 54 | if (!view) { 55 | KZPShow(@"nil argument"); 56 | return; 57 | } 58 | 59 | //! TODO: layouting will be in separate pass inside run when I add dynamic-resizing timeline 60 | UIView *lastView = [self.snapshotViews lastObject]; 61 | CGFloat maxY = CGRectGetMaxY(lastView.frame); 62 | CGFloat width = CGRectGetWidth(view.bounds); 63 | if (width < 1) { 64 | KZPShow(@"View size %@", NSStringFromCGSize(view.bounds.size)); 65 | return; 66 | } 67 | 68 | CGFloat height = CGRectGetHeight(view.bounds); 69 | CGFloat limitedWidth = MIN(width, [self maxWidthForSnapshotView]); 70 | CGFloat aspectAdjustment = limitedWidth / width; 71 | height *= aspectAdjustment; 72 | CGRect frame = CGRectMake(self.widthForSnapshotColumn * 0.5f - limitedWidth * 0.5f, maxY + kVerticalMargin, limitedWidth, height); 73 | view.frame = CGRectIntegral(frame); 74 | 75 | if ([view conformsToProtocol:@protocol(KZPSnapshotView)]) { 76 | UIView *snapshot = (UIView *)view; 77 | if (snapshot.hasExtraInformation) { 78 | UIButton *infoButton = [self extraInfoButtonForSnapshotView:snapshot]; 79 | [self.scrollView addSubview:infoButton]; 80 | [self.snapshotViews addObject:infoButton]; 81 | } 82 | } 83 | 84 | [self.scrollView addSubview:view]; 85 | [self.snapshotViews addObject:view]; 86 | } 87 | 88 | - (UIButton *)extraInfoButtonForSnapshotView:(UIView *)snapshot 89 | { 90 | UIButton *infoButton = [UIButton buttonWithType:UIButtonTypeInfoLight]; 91 | objc_setAssociatedObject(infoButton, kSnapshotViewKey, snapshot, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 92 | CGFloat buttonHeight = CGRectGetHeight(infoButton.bounds); 93 | CGFloat buttonWidth = CGRectGetWidth(infoButton.bounds); 94 | infoButton.frame = CGRectIntegral(CGRectMake(CGRectGetWidth(self.scrollView.bounds) - buttonWidth - kInfoButtonMargin, CGRectGetMidY(snapshot.frame) - buttonHeight * 0.5f, buttonWidth, buttonHeight)); 95 | [infoButton addTarget:self action:@selector(showExtraInfoFromButton:) forControlEvents:UIControlEventTouchUpInside]; 96 | return infoButton; 97 | } 98 | 99 | 100 | - (void)showExtraInfoFromButton:(UIButton *)button 101 | { 102 | UIView *snapshot = objc_getAssociatedObject(button, kSnapshotViewKey); 103 | 104 | self.currentPopoverController = [[UIPopoverController alloc] initWithContentViewController:snapshot.extraInfoController]; 105 | CGRect buttonRect = [self.view convertRect:button.frame fromView:button.superview]; 106 | [self.currentPopoverController presentPopoverFromRect:buttonRect inView:self.view permittedArrowDirections:UIPopoverArrowDirectionLeft animated:YES]; 107 | } 108 | 109 | - (void)reset 110 | { 111 | [self updateTicker]; 112 | [self.currentPopoverController dismissPopoverAnimated:NO]; 113 | [self resetSnapshotViews]; 114 | } 115 | 116 | - (void)resetSnapshotViews 117 | { 118 | NSMutableSet *snapshotsToRemove = [NSMutableSet setWithArray:self.snapshotViews]; 119 | [snapshotsToRemove minusSet:[NSSet setWithArray:self.persistedSnapshotViews]]; 120 | self.snapshotViews = [self.persistedSnapshotViews mutableCopy]; 121 | [snapshotsToRemove makeObjectsPerformSelector:@selector(removeFromSuperview)]; 122 | } 123 | 124 | - (void)updateTicker 125 | { 126 | static NSInteger tick = -1; 127 | tick++; 128 | self.tickLabel.text = [NSString stringWithFormat:@"KZPlayground Tick %@", @(tick)]; 129 | } 130 | 131 | - (void)playgroundDidRun 132 | { 133 | UIView *lastView = [self.snapshotViews lastObject]; 134 | CGFloat y = CGRectGetMaxY(lastView.frame); 135 | self.scrollView.contentSize = CGSizeMake(0, y); 136 | } 137 | 138 | - (void)playgroundSetupCompleted 139 | { 140 | //! after playground has completed we have our initial snapshot views that should be persisted 141 | self.persistedSnapshotViews = self.snapshotViews; 142 | } 143 | 144 | #pragma mark - Helpers 145 | 146 | - (CGFloat)maxWidthForSnapshotView 147 | { 148 | return [self widthForSnapshotColumn] - kHorizontalMargin * 2; 149 | } 150 | 151 | - (CGFloat)widthForSnapshotColumn 152 | { 153 | static const int infoButtonSize = 22; 154 | return CGRectGetWidth(self.view.bounds) - (infoButtonSize + kInfoButtonMargin * 2); 155 | } 156 | 157 | @end -------------------------------------------------------------------------------- /Example/Pods/dyci/Dynamic Code Injection/dyci/Classes/Injections/UIViewController+XIBSupport.m: -------------------------------------------------------------------------------- 1 | // 2 | // UIViewController+XIBSupport.m 3 | // Dynamic Code Ibjection 4 | // 5 | // Created by Paul Taykalo on 11/30/12. 6 | // Copyright (c) 2012 Stanfy. All rights reserved. 7 | // 8 | 9 | #import "UIViewController+XIBSupport.h" 10 | #import "SFDynamicCodeInjection.h" 11 | #import "UINib+StoryBoardSupport.h" 12 | 13 | 14 | #if TARGET_IPHONE_SIMULATOR 15 | 16 | @interface SFDynamicCodeInjection (Private) 17 | 18 | + (id)sharedInstance; 19 | - (void)flushBundleCache:(NSBundle *)bundle; 20 | 21 | @end 22 | 23 | 24 | @implementation UIViewController (XIBSupport) 25 | 26 | - (void)updateOnResourceInjection:(NSString *)path { 27 | NSString * extension = [path pathExtension]; 28 | if ([extension isEqualToString:@"nib"] || 29 | [extension isEqualToString:@"xib"]) { 30 | [self updateOnXIBInjectionWithPath:path]; 31 | } 32 | 33 | if ([extension isEqualToString:@"storyboardc"]) { 34 | [self updateOnStoryboardInjectionWithPath:path]; 35 | } 36 | 37 | } 38 | 39 | 40 | - (void)updateOnXIBInjectionWithPath:(NSString *)path { 41 | NSString * resourceName = [[path lastPathComponent] stringByDeletingPathExtension]; 42 | NSString * nibName = [self nibName]; 43 | 44 | // Checking if it is our nib was ibjected 45 | if ([nibName isEqualToString:resourceName]) { 46 | 47 | // If so... let's check if we loaded our view already 48 | 49 | if ([self isViewLoaded]) { 50 | 51 | // Saving view "state" 52 | CGRect oldFrame = self.view.frame; 53 | UIView * superview = self.view.superview; 54 | NSUInteger index = [[superview subviews] indexOfObject:self.view]; 55 | 56 | // Removing it from the superview 57 | [[self view] removeFromSuperview]; 58 | 59 | // Reinitializing controller with new nib 60 | [[NSBundle mainBundle] loadNibNamed:nibName owner:self options:nil]; 61 | 62 | // Resouring view state 63 | [superview insertSubview:self.view atIndex:index]; 64 | self.view.frame = oldFrame; 65 | 66 | } else { 67 | 68 | // If view wasn't loaded yet, then simply reinializing contoller with new xib 69 | [[NSBundle mainBundle] loadNibNamed:nibName owner:self options:nil]; 70 | 71 | } 72 | } 73 | } 74 | 75 | 76 | - (void)updateOnStoryboardInjectionWithPath:(NSString *)path { 77 | NSString * name = [[path lastPathComponent] stringByDeletingPathExtension]; 78 | NSLog(@"Loading injected storyboard"); 79 | UIStoryboard * injectedStoryBoard = [UIStoryboard storyboardWithName:name bundle:nil]; 80 | NSLog(@"Injected storyboard : %@", injectedStoryBoard); 81 | if (self.storyboard && injectedStoryBoard) { 82 | // Keys 83 | NSString * kBundle = @"bundle"; 84 | NSString * kStoryboardFileName = @"storyboardFileName"; 85 | NSString * kDesignatedEntryPointIdentifier = @"designatedEntryPointIdentifier"; 86 | NSString * kIdentifierToNibNameMap = @"identifierToNibNameMap"; 87 | NSString * kIdentifierToUINibMap = @"identifierToUINibMap"; 88 | 89 | // Flushing keys 90 | NSBundle * storyboardBundle = [self.storyboard valueForKey:kBundle]; 91 | [[SFDynamicCodeInjection sharedInstance] flushBundleCache:storyboardBundle]; 92 | 93 | NSString * injectedFileName = [injectedStoryBoard valueForKey:kStoryboardFileName]; 94 | NSString * originalFileName = [self.storyboard valueForKey:kStoryboardFileName]; 95 | 96 | if ([injectedFileName isEqualToString:originalFileName]) { 97 | 98 | // Let's use KVO in inappropriate way 99 | for (NSString * key in @[ kDesignatedEntryPointIdentifier, kIdentifierToNibNameMap, kIdentifierToUINibMap ]) { 100 | id value = [injectedStoryBoard valueForKey:key]; 101 | [[self storyboard] setValue:value forKey:key]; 102 | } 103 | } 104 | 105 | 106 | // Nibname for sotryboard will be like 107 | // XXXX.storyboarc/YYYY 108 | // XXXX - Storyboard name 109 | // YYYY - nib name (This one is really tricky) 110 | 111 | NSString * nibName = [NSString stringWithFormat:@"%@.storyboardc/%@", name, self.nibName]; 112 | NSBundle * bundle = [self nibBundle] ? : [NSBundle mainBundle]; 113 | 114 | NSDictionary * options = [UINib optionsByOwner:self]; 115 | UINib * nib = [UINib nibWithNibName:nibName bundle:bundle]; 116 | NSLog(@"Injecting view Controller for nibName : %@. bundle : %@", nibName, bundle); 117 | 118 | if ([self isViewLoaded]) { 119 | 120 | // Saving view "state" 121 | CGRect oldFrame = self.view.frame; 122 | UIView * superview = self.view.superview; 123 | NSUInteger index = [[superview subviews] indexOfObject:self.view]; 124 | 125 | [self viewWillDisappear:NO]; 126 | // Removing it from the superview 127 | [[self view] removeFromSuperview]; 128 | [self viewDidDisappear:NO]; 129 | 130 | // Reinitializing controller with new nib 131 | [nib instantiateWithOwner:self options:options]; 132 | 133 | self.view.frame = oldFrame; 134 | [[self view] setNeedsLayout]; 135 | [[self view] layoutIfNeeded]; 136 | 137 | [self viewWillAppear:NO]; 138 | // Restoring view state 139 | 140 | [superview insertSubview:self.view atIndex:index]; 141 | [self viewDidAppear:NO]; 142 | 143 | } else { 144 | 145 | // If view wasn't loaded yet, then simply reinitializing controller with new xib 146 | [nib instantiateWithOwner:self options:options]; 147 | 148 | } 149 | 150 | } 151 | 152 | } 153 | 154 | @end 155 | 156 | #endif -------------------------------------------------------------------------------- /Example/Pods/Target Support Files/Pods-KZNodes/Pods-KZNodes-acknowledgements.markdown: -------------------------------------------------------------------------------- 1 | # Acknowledgements 2 | This application makes use of the following third party libraries: 3 | 4 | ## KZNodes 5 | 6 | Copyright (c) 2014 Krzysztof Zablocki 7 | 8 | Permission is hereby granted, free of charge, to any person obtaining a copy 9 | of this software and associated documentation files (the "Software"), to deal 10 | in the Software without restriction, including without limitation the rights 11 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 12 | copies of the Software, and to permit persons to whom the Software is 13 | furnished to do so, subject to the following conditions: 14 | 15 | The above copyright notice and this permission notice shall be included in 16 | all copies or substantial portions of the Software. 17 | 18 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 21 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 22 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 23 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 24 | THE SOFTWARE. 25 | 26 | 27 | ## KZPlayground 28 | 29 | Copyright (c) 2014 Krzysztof Zablocki 30 | 31 | Permission is hereby granted, free of charge, to any person obtaining a copy 32 | of this software and associated documentation files (the "Software"), to deal 33 | in the Software without restriction, including without limitation the rights 34 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 35 | copies of the Software, and to permit persons to whom the Software is 36 | furnished to do so, subject to the following conditions: 37 | 38 | The above copyright notice and this permission notice shall be included in 39 | all copies or substantial portions of the Software. 40 | 41 | Redistribution in binary form is not permitted without specific prior written 42 | permission from the copyright holders. 43 | 44 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 45 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 46 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 47 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 48 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 49 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 50 | THE SOFTWARE. 51 | 52 | 53 | ## NHBalancedFlowLayout 54 | 55 | The MIT License (MIT) 56 | 57 | Copyright (c) 2013 Niels de Hoog 58 | 59 | Permission is hereby granted, free of charge, to any person obtaining a copy 60 | of this software and associated documentation files (the "Software"), to deal 61 | in the Software without restriction, including without limitation the rights 62 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 63 | copies of the Software, and to permit persons to whom the Software is 64 | furnished to do so, subject to the following conditions: 65 | 66 | The above copyright notice and this permission notice shall be included in all 67 | copies or substantial portions of the Software. 68 | 69 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 70 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 71 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 72 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 73 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 74 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 75 | SOFTWARE. 76 | 77 | 78 | ## RSSwizzle 79 | 80 | Copyright (c) 2013 Yan Rabovik 81 | 82 | Permission is hereby granted, free of charge, to any person obtaining a copy 83 | of this software and associated documentation files (the "Software"), to deal 84 | in the Software without restriction, including without limitation the rights 85 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 86 | copies of the Software, and to permit persons to whom the Software is furnished 87 | to do so, subject to the following conditions: 88 | 89 | The above copyright notice and this permission notice shall be included in all 90 | copies or substantial portions of the Software. 91 | 92 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 93 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 94 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 95 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 96 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 97 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 98 | THE SOFTWARE. 99 | 100 | 101 | 102 | ## dyci 103 | 104 | The MIT License (MIT) 105 | 106 | Copyright (c) 2014 Stanfy LLC 107 | 108 | Permission is hereby granted, free of charge, to any person obtaining a copy 109 | of this software and associated documentation files (the "Software"), to deal 110 | in the Software without restriction, including without limitation the rights 111 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 112 | copies of the Software, and to permit persons to whom the Software is 113 | furnished to do so, subject to the following conditions: 114 | 115 | The above copyright notice and this permission notice shall be included in all 116 | copies or substantial portions of the Software. 117 | 118 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 119 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 120 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 121 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 122 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 123 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 124 | SOFTWARE. 125 | Generated by CocoaPods - http://cocoapods.org 126 | -------------------------------------------------------------------------------- /Example/Pods/RSSwizzle/README.md: -------------------------------------------------------------------------------- 1 | 2 | # RSSwizzle 3 | Safe method swizzling done right. 4 | 5 | ## Motivation 6 | 7 | Classical method swizzling with `method_exchangeImplementations` is quite simple, but it has a lot of limitations: 8 | 9 | * It is safe only if swizzling is done in the `+load` method. If you need to swizzle methods during application's lifetime you should take into account that third-party code may do swizzling of the same method in another thread at the same time. 10 | * The swizzled method must be implemented by the class itself and not by superclasses. Workarounds by copying implementation from the superclass do not really work. Original implementation in the superclass must be fetched at the time of calling, not at the time of swizzling ([1][774],[2][775]). 11 | * The swizzled method implementation must not rely on the `_cmd` argument. _(And generally you can not be sure in it ([5][cmd]).)_ 12 | * Naming conflicts are possible ([3][SO]). 13 | 14 | For more details see discussions in: [1][774], [2][775], [3][SO], [4][TH], [5][cmd]. 15 | 16 | **RSSwizzle** avoids all these known pitfalls. 17 | 18 | ## Usage 19 | 20 | Original implementation must always be called from the new implementation. And because of the the fact that for safe and robust swizzling original implementation must be dynamically fetched at the time of calling and not at the time of swizzling ([1][774],[2][775]), swizzling API is slightly unusual. 21 | 22 | Example for swizzling `-(int)calculate:(int)number;` method: 23 | 24 | ```objective-c 25 | RSSwizzleInstanceMethod(classToSwizzle, 26 | @selector(calculate:), 27 | RSSWReturnType(int), 28 | RSSWArguments(int number), 29 | RSSWReplacement( 30 | { 31 | // The following code will be used as the new implementation. 32 | 33 | // Calling original implementation. 34 | int res = RSSWCallOriginal(number); 35 | // Returning modified return value. 36 | return res + 1; 37 | }), 0, NULL); 38 | ``` 39 | 40 | #### Alternative API 41 | 42 | Alternatively you may use an API without macros, though it is a little bit complicated. 43 | 44 | You should pass a factory block that returns the block for the new implementation of the swizzled method. And use `swizzleInfo` argument to retrieve and call original implementation. 45 | 46 | Example for swizzling `-(int)calculate:(int)number;` method: 47 | 48 | ```objective-c 49 | SEL selector = @selector(calculate:); 50 | [RSSwizzle 51 | swizzleInstanceMethod:selector 52 | inClass:classToSwizzle 53 | newImpFactory:^id(RSSWizzleInfo *swizzleInfo) { 54 | // This block will be used as the new implementation. 55 | return ^int(__unsafe_unretained id self, int num){ 56 | // You MUST always cast implementation to the correct function pointer. 57 | int (*originalIMP)(__unsafe_unretained id, SEL, int); 58 | originalIMP = (__typeof(originalIMP))[swizzleInfo getOriginalImplementation]; 59 | // Calling original implementation. 60 | int res = originalIMP(self,selector,num); 61 | // Returning modified return value. 62 | return res + 1; 63 | }; 64 | } 65 | mode:RSSwizzleModeAlways 66 | key:NULL]; 67 | ``` 68 | 69 | #### Class Method Swizzling 70 | Class method swizzling is done with a similar API. 71 | 72 | Example for swizzling `+(int)calculate:(int)number;` method: 73 | 74 | ```objective-c 75 | RSSwizzleClassMethod(classToSwizzle, 76 | @selector(calculate:), 77 | RSSWReturnType(int), 78 | RSSWArguments(int number), 79 | RSSWReplacement( 80 | { 81 | // Calling original implementation. 82 | int res = RSSWCallOriginal(number); 83 | // Returning modified return value. 84 | return res + 1; 85 | })); 86 | ``` 87 | 88 | 89 | #### Modes 90 | 91 | Swizzling frequently goes along with checking whether this particular class (or one of its superclasses) has been already swizzled. Here the `mode` and `key` parameters can help. 92 | Possible mode values: 93 | 94 | * `RSSwizzleModeAlways` **RSSwizzle** always does swizzling regardless of the given `key`. 95 | * `RSSwizzleModeOncePerClass` **RSSwizzle** does not do swizzling if the same class has been swizzled earlier with the same `key`. 96 | * `RSSwizzleModeOncePerClassAndSuperclasses` **RSSwizzle** does not do swizzling if the same class or one of its superclasses have been swizzled earlier with the same `key`. 97 | 98 | Here is an example of swizzling `-(void)dealloc;` only in case when neither class and no one of its superclasses has been already swizzled with the given `key`: 99 | 100 | ```objective-c 101 | static const void *key = &key; 102 | SEL selector = NSSelectorFromString(@"dealloc"); 103 | RSSwizzleInstanceMethod(classToSwizzle, 104 | selector, 105 | RSSWReturnType(void), 106 | RSSWArguments(), 107 | RSSWReplacement( 108 | { 109 | NSLog(@"Deallocating %@.",self); 110 | RSSWCallOriginal(); 111 | }), RSSwizzleModeOncePerClassAndSuperclasses, key); 112 | ``` 113 | 114 | > **Note:** `RSSwizzleModeOncePerClassAndSuperclasses ` mode does not guarantees that your implementation will be called only once per method call. If the order of swizzling is: first inherited class, second superclass; then both swizzlings will be done and the new implementation will be called twice. 115 | 116 | #### Thread safety 117 | 118 | **RSSwizzle** is fully thread safe. You do not need any additional synchronization. 119 | 120 | ## CocoaPods 121 | Add `RSSwizzle` to your _Podfile_. 122 | 123 | ## Requirements 124 | * iOS 5.0+ 125 | * Mac OS X 10.7+ 126 | * ARC 127 | 128 | ## Author 129 | Yan Rabovik ([@rabovik][twitter] on twitter) 130 | 131 | ## License 132 | MIT License. 133 | 134 | [twitter]: https://twitter.com/rabovik 135 | [cmd]: http://www.mikeash.com/pyblog/friday-qa-2010-01-29-method-replacement-for-fun-and-profit.html#comment-e2c2af6395d9e8fca559895bbd434ee8 136 | [SO]: http://stackoverflow.com/a/8636521/441735 137 | [774]: https://github.com/ReactiveCocoa/ReactiveCocoa/pull/774 138 | [775]: https://github.com/ReactiveCocoa/ReactiveCocoa/pull/775 139 | [TH]: https://github.com/th-in-gs/THObserversAndBinders/commit/cabe12dece2faabf5e58759363ac603be963c889#L1R231 -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Images/ImagePicker/KZPImagePickerComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 21/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import 9 | #import "KZPImagePickerComponent.h" 10 | #import "KZPTimelineViewController.h" 11 | #import "KZPPresenterComponent.h" 12 | #import "KZPImagePickerCollectionViewController.h" 13 | 14 | void __attribute__((overloadable)) KZPAdjust(NSString *name, void (^block)(UIImage *)) { 15 | [KZPImagePickerComponent addImagePickerWithName:name block:block]; 16 | } 17 | 18 | static const void *kAdjusterLifetimeKey = &kAdjusterLifetimeKey; 19 | 20 | static const NSInteger kLibraryButtonIndex = 0; 21 | static const NSInteger kAssetButtonIndex = 1; 22 | 23 | @interface KZPImagePickerComponent () 24 | 25 | @property(nonatomic, weak) KZPPresenterComponent *presenterComponent; 26 | @property(nonatomic, copy) void (^changeBlock)(UIImage *); 27 | @property(nonatomic, copy) NSString *name; 28 | @end 29 | 30 | @implementation KZPImagePickerComponent 31 | + (void)addImagePickerWithName:(NSString *)name block:(void (^)(UIImage *))block 32 | { 33 | id __unused unused = [[KZPImagePickerComponent alloc] initWithName:name block:block]; 34 | } 35 | 36 | - (id)initWithName:(NSString *)name block:(void (^)(UIImage *))block 37 | { 38 | self = [super init]; 39 | if (!self) { 40 | return nil; 41 | } 42 | 43 | self.name = name; 44 | 45 | KZPTimelineViewController *timelineViewController = [KZPTimelineViewController sharedInstance]; 46 | 47 | KZPPresenterComponent *presenterComponent = [[KZPPresenterComponent alloc] initWithImage:self.class.lastValues[name] type:@"UIImage"]; 48 | presenterComponent.frame = CGRectMake(0, 0, timelineViewController.maxWidthForSnapshotView, timelineViewController.maxWidthForSnapshotView); 49 | presenterComponent.backgroundColor = UIColor.blackColor; 50 | 51 | UIButton *button = [self setupButtonWithName:name]; 52 | 53 | button.center = presenterComponent.center; 54 | [presenterComponent addSubview:button]; 55 | 56 | [timelineViewController addView:presenterComponent]; 57 | self.presenterComponent = presenterComponent; 58 | self.changeBlock = block; 59 | objc_setAssociatedObject(presenterComponent, kAdjusterLifetimeKey, self, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 60 | return self; 61 | } 62 | 63 | - (UIButton *)setupButtonWithName:(NSString *)name 64 | { 65 | UIButton *button = [UIButton buttonWithType:UIButtonTypeInfoDark]; 66 | [button setTitle:[NSString stringWithFormat:@" %@", name] forState:UIControlStateNormal]; 67 | button.titleLabel.adjustsFontSizeToFitWidth = YES; 68 | button.titleLabel.font = [UIFont systemFontOfSize:14]; 69 | button.layer.cornerRadius = 8; 70 | [button setTitleColor:[UIColor lightGrayColor] forState:UIControlStateNormal]; 71 | [button setBackgroundColor:[[UIColor blackColor] colorWithAlphaComponent:0.8]]; 72 | [button sizeToFit]; 73 | [button addTarget:self action:@selector(buttonPressed:) forControlEvents:UIControlEventTouchUpInside]; 74 | return button; 75 | } 76 | 77 | - (void)buttonPressed:(UIButton *)button 78 | { 79 | UIActionSheet *sheet = [[UIActionSheet alloc] initWithTitle:@"Select source" delegate:self cancelButtonTitle:@"Cancel" destructiveButtonTitle:nil otherButtonTitles:@"Photo Library", @"Assets", nil]; 80 | [sheet showFromRect:[button.superview convertRect:button.bounds fromView:button] inView:button.superview animated:YES]; 81 | } 82 | 83 | - (void)actionSheet:(UIActionSheet *)actionSheet didDismissWithButtonIndex:(NSInteger)buttonIndex 84 | { 85 | if (buttonIndex == kLibraryButtonIndex) { 86 | [self showPickerWithSourceType:UIImagePickerControllerSourceTypePhotoLibrary]; 87 | } else if (buttonIndex == kAssetButtonIndex) { 88 | [self showAssetPicker]; 89 | } 90 | } 91 | 92 | - (void)showPickerWithSourceType:(UIImagePickerControllerSourceType)sourceType 93 | { 94 | UIImagePickerController *controller = [UIImagePickerController new]; 95 | controller.modalPresentationStyle = UIModalPresentationCurrentContext; 96 | controller.sourceType = sourceType; 97 | controller.delegate = self; 98 | 99 | KZPTimelineViewController *timelineViewController = [KZPTimelineViewController sharedInstance]; 100 | [timelineViewController presentViewController:controller animated:YES completion:nil]; 101 | } 102 | 103 | - (void)showAssetPicker 104 | { 105 | KZPImagePickerCollectionViewController *assetCollectionViewController = 106 | [[UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle bundleForClass:self.class]] instantiateViewControllerWithIdentifier:@"KZPImagePickerCollectionViewController"]; 107 | 108 | __weak typeof(self) weakSelf = self; 109 | assetCollectionViewController.onSelectionBlock = ^(UIImage *image) { 110 | weakSelf.selectedImage = image; 111 | }; 112 | 113 | KZPTimelineViewController *timelineViewController = [KZPTimelineViewController sharedInstance]; 114 | [timelineViewController presentViewController:[[UINavigationController alloc] initWithRootViewController:assetCollectionViewController] animated:YES completion:nil]; 115 | } 116 | 117 | - (void)setSelectedImage:(UIImage*)image 118 | { 119 | self.presenterComponent.image = image; 120 | self.changeBlock(image); 121 | self.class.lastValues[self.name] = image; 122 | } 123 | #pragma mark - UIImagePickerDelegate 124 | 125 | - (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info 126 | { 127 | UIImage *image = [info valueForKey:UIImagePickerControllerOriginalImage]; 128 | self.selectedImage = image; 129 | [picker dismissViewControllerAnimated:YES completion:nil]; 130 | } 131 | 132 | - (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker 133 | { 134 | [picker dismissViewControllerAnimated:YES completion:nil]; 135 | } 136 | 137 | #pragma mark Helpers 138 | 139 | static const void *kLastValuesKey = &kLastValuesKey; 140 | 141 | + (NSMutableDictionary *)lastValues 142 | { 143 | NSMutableDictionary *lastValues = objc_getAssociatedObject(self, kLastValuesKey); 144 | if (!lastValues) { 145 | lastValues = [NSMutableDictionary new]; 146 | objc_setAssociatedObject(self, kLastValuesKey, lastValues, OBJC_ASSOCIATION_RETAIN_NONATOMIC); 147 | } 148 | return lastValues; 149 | } 150 | 151 | + (void)reset 152 | { 153 | 154 | } 155 | 156 | @end -------------------------------------------------------------------------------- /Pod/Assets/KZNNode.xib: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | -------------------------------------------------------------------------------- /Example/Pods/KZPlayground/Pod/Classes/Components/Presenter/KZPPresenterComponent.m: -------------------------------------------------------------------------------- 1 | // 2 | // Created by Krzysztof Zabłocki(http://twitter.com/merowing_) on 20/10/14. 3 | // 4 | // 5 | // 6 | 7 | 8 | #import 9 | #import "KZPPresenterComponent.h" 10 | #import "KZPTimelineViewController.h" 11 | #import "KZPSnapshotView.h" 12 | #import "KZPPresenterInfoViewController.h" 13 | 14 | static NSString *KZPShowType = nil; 15 | 16 | void KZPShowRegisterType(NSString *format, ...) { 17 | if (format == nil) { 18 | KZPShowType = nil; 19 | return; 20 | } 21 | 22 | if (KZPShowType) { 23 | return; 24 | } 25 | 26 | va_list args; 27 | va_start(args, format); 28 | KZPShowType = [[NSString alloc] initWithFormat:format arguments:args]; 29 | va_end(args); 30 | } 31 | 32 | void KZPShowRegisterClass(id instance, Class baseClass) { 33 | if (![instance isMemberOfClass: baseClass]) { 34 | KZPShowRegisterType(@"%@:%@", NSStringFromClass([instance class]), NSStringFromClass(baseClass)); 35 | return; 36 | } 37 | 38 | KZPShowRegisterType(NSStringFromClass(baseClass)); 39 | } 40 | 41 | void __attribute__((overloadable)) KZPShow(CALayer *layer) { 42 | KZPShowRegisterClass(layer, CALayer.class); 43 | 44 | UIGraphicsBeginImageContextWithOptions(layer.bounds.size, NO, 0); 45 | [layer renderInContext:UIGraphicsGetCurrentContext()]; 46 | UIImage *copied = UIGraphicsGetImageFromCurrentImageContext(); 47 | UIGraphicsEndImageContext(); 48 | KZPShow(copied); 49 | } 50 | 51 | void __attribute__((overloadable)) KZPShow(UIView *view) { 52 | KZPShowRegisterClass(view, UIView.class); 53 | 54 | UIGraphicsBeginImageContextWithOptions(view.bounds.size, NO, 0); 55 | [view drawViewHierarchyInRect:view.bounds afterScreenUpdates:YES]; 56 | UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); 57 | UIGraphicsEndImageContext(); 58 | 59 | KZPShow(image); 60 | } 61 | 62 | void __attribute__((overloadable)) KZPShow(CGPathRef path) { 63 | KZPShowRegisterType(@"CGPathRef"); 64 | 65 | UIBezierPath *bezierPath = [UIBezierPath bezierPathWithCGPath:path]; 66 | [bezierPath setLineWidth:3]; 67 | [bezierPath setLineJoinStyle:kCGLineJoinBevel]; 68 | KZPShow(bezierPath); 69 | } 70 | 71 | 72 | void __attribute__((overloadable)) KZPShow(UIBezierPath *path) { 73 | KZPShowRegisterType(@"UIBezierPath"); 74 | 75 | CGRect rect = CGRectMake(0, 0, CGRectGetWidth(path.bounds) + path.lineWidth, CGRectGetHeight(path.bounds) + path.lineWidth); 76 | CGContextRef context = UIGraphicsGetCurrentContext(); 77 | UIGraphicsPushContext(context); 78 | UIGraphicsBeginImageContext(rect.size); 79 | UIBezierPath *copiedPath = path.copy; 80 | [copiedPath applyTransform:CGAffineTransformMakeTranslation(path.lineWidth * 0.5, path.lineWidth * 0.5)]; 81 | [copiedPath stroke]; 82 | UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); 83 | UIGraphicsPopContext(); 84 | UIGraphicsEndImageContext(); 85 | 86 | KZPShow(image); 87 | } 88 | 89 | void __attribute__((overloadable)) KZPShow(CGImageRef image) { 90 | KZPShowRegisterType(@"CGImageRef"); 91 | 92 | KZPShow([UIImage imageWithCGImage:image]); 93 | } 94 | 95 | void __attribute__((overloadable)) KZPShow(UIImage *image) { 96 | KZPShowRegisterType(@"UIImage"); 97 | 98 | KZPPresenterComponent *presenter = [[KZPPresenterComponent alloc] initWithImage:image type:KZPShowType]; 99 | if (!presenter) { 100 | KZPShow(@"Error: Unable to present image with size %@", NSStringFromCGSize(image.size)); 101 | return; 102 | } 103 | [[KZPTimelineViewController sharedInstance] addView:presenter]; 104 | KZPShowRegisterType(nil); 105 | } 106 | 107 | void __attribute__((overloadable)) KZPShow(NSString *format, ...) { 108 | KZPShowRegisterType(@"NSString"); 109 | 110 | va_list args; 111 | va_start(args, format); 112 | NSString *message = [[NSString alloc] initWithFormat:format arguments:args]; 113 | va_end(args); 114 | 115 | UILabel *label = [[UILabel alloc] init]; 116 | label.text = message; 117 | label.numberOfLines = 0; 118 | label.textColor = [UIColor blackColor]; 119 | CGSize size = [label sizeThatFits:CGSizeMake([KZPTimelineViewController sharedInstance].maxWidthForSnapshotView, CGFLOAT_MAX)]; 120 | label.frame = CGRectMake(0, 0, size.width, size.height); 121 | 122 | [[KZPTimelineViewController sharedInstance] addView:label]; 123 | KZPShowRegisterType(nil); 124 | } 125 | 126 | void __attribute__((overloadable)) KZPShow(id obj) { 127 | if ([obj respondsToSelector:@selector(kzp_debugImage)]) { 128 | UIImage *image = [obj performSelector:@selector(kzp_debugImage)]; 129 | KZPShow(image); 130 | return; 131 | } 132 | 133 | if ([obj respondsToSelector:@selector(debugQuickLookObject)]) { 134 | id debugObject = [obj debugQuickLookObject]; 135 | 136 | #define SHOW_IF(type) if([debugObject isKindOfClass:type.class]) {KZPShow((type*)debugObject); return;} 137 | SHOW_IF(CALayer); 138 | SHOW_IF(UIView); 139 | SHOW_IF(UIBezierPath); 140 | SHOW_IF(UIImage); 141 | SHOW_IF(NSString); 142 | #undef SHOW_IF 143 | } 144 | 145 | KZPShow([NSString stringWithFormat:@"%@ : %@", NSStringFromClass([obj class]), [obj description]]); 146 | } 147 | 148 | @interface KZPPresenterComponent () 149 | @property(nonatomic, weak) UIImageView *imageView; 150 | @property(nonatomic, copy) NSString *type; 151 | @end 152 | 153 | @implementation KZPPresenterComponent 154 | - (instancetype)initWithImage:(UIImage *)image type:(NSString *)type 155 | { 156 | self = [super initWithFrame:CGRectMake(0, 0, image.size.width, image.size.height)]; 157 | if (!self) { 158 | return nil; 159 | } 160 | 161 | _image = image; 162 | _type = [type copy]; 163 | [self setup]; 164 | return self; 165 | } 166 | 167 | - (void)setup 168 | { 169 | UIImageView *imageView = [[UIImageView alloc] initWithImage:self.image]; 170 | imageView.contentMode = UIViewContentModeScaleAspectFit; 171 | imageView.frame = self.bounds; 172 | imageView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; 173 | [self addSubview:imageView]; 174 | self.imageView = imageView; 175 | } 176 | 177 | - (BOOL)hasExtraInformation 178 | { 179 | return YES; 180 | } 181 | 182 | - (void)setImage:(UIImage *)image 183 | { 184 | _image = image; 185 | self.imageView.image = image; 186 | } 187 | 188 | 189 | - (UIViewController *)extraInfoController 190 | { 191 | KZPPresenterInfoViewController *presenterInfoViewController = [KZPPresenterInfoViewController new]; 192 | NSString *title = [NSString stringWithFormat:@"%@ %.0f x %.0f", self.type, self.image.size.width, self.image.size.height]; 193 | [presenterInfoViewController setFromImage:self.image title:title]; 194 | return presenterInfoViewController; 195 | } 196 | 197 | + (void)reset 198 | { 199 | 200 | } 201 | 202 | @end --------------------------------------------------------------------------------