TestsTested | ✗ |
LangLanguage | Obj-CObjective C |
License | MIT |
ReleasedLast Release | May 2015 |
Maintained by Krzysztof Zablocki, Krzysztof Zabłocki.
Depends on: | |
dyci | ~> 0.1.5.6 |
RSSwizzle | ~> 0.1.0 |
NHBalancedFlowLayout | ~> 0.2 |
Playgrounds are one of the niftiest features of Swift. They allow you to quickly test out bits of code and see results in real time without going through traditional edit-compile-run-debug cycle.
"But surely playgrounds aren't possible in Objective-C" you say? ... In fact they can be much better than Swift ones.
Features:
and it’s just a start.
First, let’s establish naming:
KZPShow(obj)
You can implement custom debug image:
- (UIImage*)kzp_debugImage;
If you have already implemented - (id)debugQuickLookObject
that returns any of types supported by the KZPShow, you don’t need to do anything.
KZPAction(@"Press me", ^{
// Magic code
})
Picking an image from the library:
KZPAdjustImage(myImage);
KZPWhenChanged(myImage, ^(UIImage *img) {
imageView.image = img;
});
KZPAdjustValue(scale, 0.5f, 1.0f) //- for floats
KZPAdjustValue(position, 0, 100) //- for integers
you can also set default values:
KZPAdjustValue(position, 0, 100).defaultValue(50)
KZPAdjust
are also available.KZPAnimate(CGFloat from, CGFloat to, void (^block)(CGFloat));
KZPAnimate(void (^block)());
KZPAnimateValue(rotation, 0, 360)
KZPAnimateValueAR(scale, 0, 1)
Executing code only once the value is set
KZPWhenSet(myImage, ^(UIImage *img) {
//! magic
});
Executing code on value changes
KZPWhenChanged(myImage, ^(UIImage *img) {
//! magic
});
Instead of using instance variables / properties for KZPlayground class (you are fine to use them for normal classes that you create as part of playground), you should store playground specific variables that you need to reference between playground methods, eg. view you want to pan with UIPanGestureRecognizer inside transientObjects dictionary.
self.transientObjects[@"pannableView"] = view;
Implement setup method and use normal instance variables to store data you don't want to change on code change. eg. if you need to do some expensive operation.
Snapshots recorded during setup will persist in timeline.
- (void)setup
{
self.data = [self fetchBigDataSet];
}
KZPlayground is distributed as a CocoaPod:
pod 'KZPlayground'
so you can either add it to your existing project or clone this repository and play with it.
Remember to not add playgrounds in production builds (easy with new cocoapods configuration scoping).
Once you have pod installed, you need to create your playground, it’s simple:
[KZPPlaygroundViewController playgroundViewController]
To apply your changes you have 2 approaches:
kicker -sql 0.05 FOLDER_WITH_SOURCE_FILES
in case of Example project you'd call kicker from inside the project root folder (one containing the .kick
file, which you will also need.)
kicker -sql 0.05 Example
This will react to all changes in .m files in the Example directory and reload your playground.
PID_PATH=/tmp/${PROJECT_NAME}_kicker.pid
if [ -e $PID_PATH ]
then
kill $(cat $PID_PATH)
rm $PID_PATH
fi
kicker -sql 0.05 . > /dev/null 2>&1 & echo $! > $PID_PATH
Note: You will need to manually kill the kicker process when you're done since it won't be killed after you stop running your project.
KZPlayground is powered by Dyci code injection tool, you only need to install it once on your machine (You’ll need to reinstall it on Xcode updates):
git clone https://github.com/DyCI/dyci-main.git
cd dyci-main/Install/
./install.sh
In order to use the kicker gem, you need to install it as follows:
(sudo) gem install kicker
Pull-requests are welcomed.
KZPlayground is available under the modified MIT license. See the LICENSE file for more info.
Krzysztof Zablocki, [email protected]
Check-out my blog or GitHub profile for more cool stuff.
SceneKit example code has been taken from David Ronnqvist upcoming SceneKit book, recommended.