If you follow me on Twitter (@RiczWest) then you’ll know I was working on an iOS game called ASCIItrek which is derived from Super Star Trek that was written in C. I’ll eventually do a complete rewrite in Swift, but before that I’m taking the existing code and integrating it in to an iOS interface. In order to do this I’ll need to call C code from Swift. The Architect in me however wants to cleanly separate things and use Objective-C as a “bridge”, which as you’ll see later is probably a pretty good idea.
It’s always been “theoretically possible” to do this in earlier releases of Xcode prior to 6.3, but the whole process seems fraught with potential errors and I could never get it fully working. With the recent release of Xcode 6.3 I thought I’d give it a go and am glad I did as it seems to work relatively easily as I’ll describe.
Note: In this post I’ll assume that you’re relatively familiar with coding in Xcode
Firstly, you’ll need to create a project, which is no-brainer – just create a Swift one which we’ll adjust as we go… At the highest level we’ll have some code which acts as a test harness which I just added:
where chopper (tribute to American Chopper :) is an Objective-C method and c_chop is a c one which is invoked from Objective-C. First, the Objective-C one which is relatively simple:
if you just look at the chopper method where I’m basically doing a string concatenation – we’ll get on to the c_chop method after we’ve examined the C code:
which has one basic method/function called chop that like the Objective-C one just prepends the parameter which is obviously more complex in C. The one thing that worries me slightly is the fact that I’m mallocing memory which is passed to Objective-C which I’m kind of assuming will be deallocated – I’ll probably revisit this later…
If you go back to the Objective-C code above for c_chop you’ll see there is a bit of complexity, which is why I think it’s better to wrap a C call in Objective-C. The stringWithFormat: method is just a concatenation, but notice that you have to convert the Objective-C/Swift string to UTF8Sting before passing and then convert the result back with stringWithUTF8String. To me, this is enough reason to have an Objective-C layer interposed between your Swift and C layers.
Hopefully this post has made it easier for anyone else who is on the same path – the code is on GitHub at https://github.com/RiczWest/swocc – feel free to mail me if you have any questions. Later, I’ll be doing another post on C to Objective-C to Swift (which I also need)
PS Having HUGE problems with syncing GIT, which I have just checked and they are a BUG – I will attempt to fix later…