I’ve merged Ole’s changes into my Git repo, albeit with a few modifications. This article outlines the changes to the changes.
What has changed?
I’ll not dig too much into Ole’s enhancements. Ole does that on his page. In summary:
- Shader sources compile for OS X and iPhone OS.
- Has two sample projects, one for OS X and the other for iPhone.
Why does it need porting?
The fundamental difference between iPhone and OS X for the gloss-caustic shader concerns its use of NSColor. Simply put, iPhone does not have such a class; instead, it has UIColor with limited support for colour spaces and no support for RGB-to-HSB conversion.
Strangely, you can make the reverse conversion, from HSB to RGB by invoking class method
and UIKit answers with a colour with triple RGB components whence you can access the red, green, blue and alpha component values. But iPhone has no instance method
as does OS X.
The basic approach
The simple approach Ole takes is to surround the difference between OS X and iPhone with
#endif blocks. Xcode defines
TARGET_OS_IPHONE only when compiling for iPhone.
Under normal circumstances, I would avoid this approach since it makes code difficult to read and maintenance harder in the long run. Nevertheless, the pre-processor conditional blocks turns out relatively small in number and in extent. Each one in general surrounds just one line of code: the first condition presents the iPhone’s UIColor-based alternative, while the second condition presents OS X’s NSColor-based alternative.
Ole has included a number of useful functions for colour conversion, based on work by Erica Sadun and some standard RGB-to-HSB conversion code. I’ve repackaged these as extensions on UIColor with semantics mirroring that of NSColor.
UIColor(RRUIKit) as follows.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
Ole implements a set of extensions on
RRGlossCausticShader for saving shader setting to a dictionary. I’ve enhanced this functionality by implementing the
NSCoding protocol for shader and matcher classes.
Coding adds a level of extra flexibility. The coding protocol lets you serialise trees of objects (the shader and its enclosed matcher) by archiving to any data stream.
I’ve also simplified the iPhone sample’s view controller. iPhone OS does not include bindings. Hence implementing the update cycle within the controller can become rather tedious when there are many control elements, such as with gloss-caustic shaders.
My enhancement on Ole’s enhencement employs key-value coding, i.e. accessing properties via
-setValue:forKeyPath:. It makes things a little less long-winded.