Sep 08

Cocos2dx Migration -> Sixth update (40 hours) JNI We meet again

Things were moving ahead quite nicely, converting my obj classes to C++ went smoothly, cocos2d-x is really well refined. I even found out that there was a problem in my declarations for using sprites with sprite frame names, so I fixed that code. I also wrenched in some ad frameworks, and most of all I’ve been working back and forth with the folks at Kiip. After my first (bad) impression, they were kind to follow through with all my information requests and clarifications. So in the end I said ‘if it’s not too hard to integrate, i’ll give it a go’. Well the issue we have here is that Kiip is native for iOS and android, but I want it to work on both. Plus, all my code is cocos2d-x (c++) with no calls to Java (well very few), so I’d need a JNI wrapper to handle Kiip. I’ll get to that in a second.

First things first, I think my first post I mentioned I love the new ‘create’ initializers, however I had an issue with create(), well that’s because I called the wrong init! There is actually a createWithSpriteFrameName(”). If you use just create(”) it’ll look for that file, not a frame name, hence the second initializer. It just brings it inline with what they’re doing, and it’s great. So to sum up.

To create sprite with a file call this:

CCSprite *mySprite = CCSprite::create("filename");

To create one with a spriteframename

CCSprite *mySprite = CCSprite::createWithSpriteFrameName("frameName");

Ok that’s cleared up let’s keep moving, as we have some more work to do! So Integrating the ad networks (I use mobclix and admob open allocation) was pretty easy, I actually migrated the code from my other app ‘Retro Art Studio’ for android, and dropped it in. I did have an issue doing the layout in the XML file, so I just did it programmatically and it worked fine. The only thing I’m not doing which I’d like (which I do on iOS) is control when the ads show and hide. Right now they just are a view and show over the game when the app opens, sorry I just don’t have time right now to fix that. Ideally I’ll plug in some JNI calls and have them hide / show during the right times.

JNI… first of all, I write code in many many languages, C, C++, OBJC, Python, (some ruby, basic, shell, action script, javascript), etc. One language that I’ve used in the past, and try to avoid at all costs is JAVA. I find it repulsive, I won’t go into the details, but the sum is ‘write once run everywhere’ the original motto never worked, so everyone who jumped on it got screwed. It’s the most difficult to develop and debug language around. By attempting to simplify (‘HEY NO POINTERS NEEDED!’) they’ve encouraged sloppy programming standards, and an over complicated way of delivering underperforming code. — Sorry for the rant, just got stuck in the Java mud and it pains me every time — Professionally I tell clients I don’t do Java, and they assume I don’t do android, on contrary I do android, via C++, if you want a Java / web based app, there’s plenty of people out there for that. I’ve worked at Apple, I’ve used Java (not at apple), I’ve used Windows for many years (prior to my job at apple), and in the end I choose the tools I like, which are Linux/Apple OS’s, C based languages, Xcode (for C++/OBJC/etc), Python for scripting, vim for editing on the command line. P.S. I have zero fear of managing memory, I actually enjoy it.

OK! Rant over, back to work. So Kiip, these guys have an interesting idea, but like I said I wasn’t sold on their initial pitch, but going back and forth it seemed like something I’d be willing to try on this android version of the app, and if it worked well I’d put it in the iOS version. The basics of Kiip is that you can reward players at certain levels with unlock able real-world items. Mainly coupons, vouchers, gift cards, etc. I don’t provide them, they are provided by the advertisers, e.g. If you unlock level 20 in your game, then you’re rewarded a coupon for a bag of Chippy brand Fish Sticks. Which apparently you can take and redeem at your local Chippy brand grocer. (Or something like that).

So to integrate I needed it to work on both iOS / android. First thing is their setup is pretty good, I’ll admit the walk through was easy to follow. And I called into the iOS api instantly and was up and running in about 20 minutes. Their website has great debugging as well, you can real time watch the log of you logging in and unlocking achievements. Impressive. Now for android… My contact at Kiip was great, when I mentioned I was doing cocos2d-x he sent me a wrapper class another dev had created for JNI. This was a huge help, until 6 hours later I realized it didn’t work. No fault of Kiip (they said it wasn’t their code, and was unsupported), and no fault of the original Dev. It was built against a different version of cocos2d-x and Kiip, so it just wasn’t up to date.

I had to put on my JNI hat again, and grrr… go to java. Well I hit so many roadblocks, first this code was made without JNIHelper, which simplifies a lot of code that was written, second I couldn’t get the method signature right for the kiip call to the ‘saveLeaderboardScore’ method. I could get access to the static singleton, but couldn’t call the method inside. I tried every combination I could think of, and it just wasn’t going. So after a while, I just implemented JNIHelper and that simplified the code by about 140 lines. However it still wasn’t doing what I needed, the signature was wrong. I called it the way the API said, no luck, I called it the way javap said, no luck, I made up ways to call it, no luck. So in the end I did a ‘hack’, but it worked and it was clean and easy.

I implemented a method in my root java class (the one called by the app that loads up my c++ code), and in there I added a simple static method that called the actual lib and submitted the score. Then in the JNI wrapper, I replaced all the code in there with a call to my simple static method and hey, it worked! Ideally I should call the method directly, but that wasn’t going well, and I feel that if I can do the same in < 10 lines of code that was done in > 100 then I’m probably ok. Obviously you don’t want to add a ton of new methods to your .java file, but this really is a single one as I’m only using leader boards right now, so I didn’t mind.

Here’s the code I ended up using in my .java file

	 static public void kiipSubmitToLeaderboard(String boardName, int score)
	     Kiip.getInstance().saveLeaderboard(boardName, score, null);

Then to call it from my wrapper class.

void GameResults::SubmitHighScore()
    KiipWrapper::sharedKiipWrapper()->reportScoreForLeaderboard("highscore", _score);

You can have multiple leader boards, so just create a const char * for whatever the name of your leader board is along with the score amount. There’s probably many other ways to do this, but for 6 lines of code, not bad.

After that, the kiip code was up and running and I just tweaked out the alignment a bit (which is done via their web interface, in real time which is cool.)

Depending on how my (and my users) experience with Kiip goes, I’d be more inclined to explore it more on my other apps, as well as provide a step-by-step approach to get it up and running in cocos2d-x. But first I have 8 more hours to go to hit my deadline!

Sep 03

Cocos2dx Migration -> Fifth update (32 hours) The meat of it

I’ve done thousands of lines of code in the last few days, and 32 hours. The main benefit I have is the speed at which I can type, moving between the languages is easy enough, the only slowdown is when you hit something platform specific (reading / writing files for example). Once you get over those hurdles things move quick. Now I’m in the much of the ‘boring bits’, this is where I’m basically just going through the code and translating it.

The benefit I have is the existing OBJ-C app has shipped on two platforms already (iOS/MAC) so I know the code all works, and when something doesn’t it’s usually something as simple as a variable not copied correctly. I wish I could say I have a real easy method of doing this that I can share with others, but the truth is, I have a single workspace and I jump from the original code to the new code and copy and paste, then re write the methods using the original code as a reference. It’s all pretty easy going, just time consuming.

I was on holiday for a few days, so I just got about 2 hours a day in, but still I’ve made a lot of progress, and have just 16 hours left to go (hopefully). Here’s the major bits I did.

Since android will be the first release, I started doing some Android specific things. First was to implement the ad networks for the app (as it’s free on mobile and ad supported). I had done this before, but anything with Android / Eclipse is always a new learning experience for me no matter how much I do it. I just never enjoy it and my brain flushes it out immediately after I do it. Regardless, after a few hours it’s all up and running. Now I’m going through and porting more of the core classes and views into the app. The good thing is about 20% of this code comes from shared classes I use on my other apps. When I do an iOS project I usually have about 25% of the code ready to go from frameworks / root classes I’ve created. Now I have these in cocos2d-x (versus obj-c cocos2d).

I’ve always prototyped in OBJC because it was easier to get started because I have so much pre-work done. But now with this project I’ve translated a bunch of shared things from OBJC->C++, so possibly (and hopefully) I’ll start doing my prototypes in C++ using cocos2d-x now, so I don’t have to revisit this exercise again! The cocos2d(x) framework is very easy to understand once you use it a while (i’ve used it exclusively for > 2 years, and have done about 130 prototypes, 8 commercial apps in it. The only thing officially missing from cocos2d-x is full MAC support, I know it’s in development, but with cocos2d I have it out of the box currently, which is why I start there. Also other platforms (aside from iOS/OSX) haven’t proven fruitful yet. But I do like the idea to grow, and is why I like the C++ work in cocos2d-x.

Anyway, so we have the core game up, we have the ad support, the main menu brings you to the game, you can play it, start a new match, all the animations works, etc. What’s missing, scoring, game over handling, other menu items, pop up notifications within the game.

Sep 03

Word Jumblerama Blitz for OSX Released

Word Jumblerama Blitz, our popular quick fix word finding game is now available for OSX. Featuring the same great gameplay as on the iOS version the OSX version includes unlock able achievements, multiple themes, and the fun quick action you’ve come to know.

The OSX version is ad free and only $1.99! If you haven’t played Word Jumblerama Blitz yet, check out the free iOS version (ad supported) and give it a try.

Word Jumblerama Blitz - Six Foot Three Foot

Aug 28

Cocos2dx Migration -> Fourth update (22 Hours) Kicking down the wall

Well just like a Thursday morning, I’m over the hump. Getting into the android slump is always discouraging, but once through the middle of it (you’re never always out), things start to look up. I had a rough few hours last block, and I waited until I was done until I posted to keep my mood light. So, where are we now? We have all the core gameplay working, the tile selection works, the word lookup and matching works, and it’s blazingly fast.

So as I mentioned before we had some issues with Android, the question always comes up ‘You don’t care for android, but why do you develop for it?’. It’s true, I don’t care for it, for a few reasons, mainly the JAVA bit (which I don’t need to touch much thanks to cocos2dx), the fact that I have to write for 2.3 devices which make up 60% of the market today (shocking as 4.0.3 is out). [Devices can’t update, and most manufacturers still ship 2.3 for low-end phones as it has much cheaper licensing costs, and less restrictions from google]. So that’s never fun. So the reason why I do develop for it… I simply like a challenge, and I like keeping my coding skills up to par. I can write OBJ-C in my sleep, it’s my day job, and I do rather well at it. That’s work for a client, I always tell clients to avoid Android when they can, as the work / cost is 10 times that of iOS and the return is about 1/10th. This is pretty well known now in the market, unless you’re doing a utility app (banking, finance, fart app), for games it’s not viable yet.

But I like c++, but I really love cross platform development. I always write my objc projects in a a custom environment which runs on Mac, iPhone, iPad all within the same code. It is a bit of setup work, but in the end I have one code base for 3 platforms. With cocos2d-x I can get 5 platforms potentially (more, but only 5 I’m currently interested in), all on the same code. That’s a really cool concept, and Android does have a market. I may not like the software, but the hardware is kind of cool, and I really like users, as well as my games. My games do well on iOS ratings wise, so that encourages me to port them to other platforms. They don’t move many units on Android, but the feedback is great, so that’s encouraging. So yes, in short I bury the hatchet with the platform to deliver to the customer.

Ok so some technical things! Wow reading a huge plist / processing it on Android was unbearable, something that took 1 second on a iPod takes 11 minutes on my android tablet (same chip as an iPad), I blame the os. So that led me to some cool programming which I carried over to all the platforms. Basically I already was generating this huge dictionary from the plist on Mac, so I then just added a call to save it as a binary file to disk. I then take that binary file and load that into memory, and parse it into an array. Basically doing the same thing, but pulling out the middle man of reading in a plist / parsing it into a primitive array. That said, I got the loading time down to 200 milliseconds on android. That warrants a smiley… 🙂

Next thing I hit was errors on Android which I didn’t see on iOS. These were memory issues. I created a custom class that will determine your resolution and pull up the right assets. If you’ve done android from iOS in cocos, you’ll know you really want your ‘-hd’, ‘-ipad’ files to work instantly. Well they don’t, so I created a simple class that does similar logic and appends the file suffix depending on your resolution. Anyway, the issue I hit was that the memory sometimes go bad after making the call. I was passing const char* pointers out of the methods, which ‘is’ correct, but when setting multiple labels, etc to the same variable it would get lost.

I didn’t set up the overly complex way of debugging c++ code in eclipse on android, so I had to do some logging to catch the issue. It was pretty apparent after a while it was memory gone missing, as it would work on a relaunch, and fail somewhere else. (It always worked on iOS). So I then looked at ways to keep that memory around, using strdup worked great, but it caused leaks, as I was returning the value with a strdup, so no way I could release it. But then instead of fighting c solutions, I put on my cocos2d-x hat, and then simply returned a const char* as before, but fed that into a CCString, that then worked until the end of the method and cleaned itself up properly, no leaking! I had that issue a couple places, as it’s a word game, very character centric!

Anyway, not much insight here, this is more of a log than a development lesson, if I had the time and there was interest I could cover some of these topics in more depth. For now I’m just fighting the clock to get the app done. But we’re getting close the core gameplay is working, now I just need to start adding some of the other displays, (timers, lists, etc), which should prove challenging as they’re custom drawn views, but challenges are fun. (Usually after the fact)

Aug 26

Cocos2dx Migration -> Third update (14 Hours) … Hitting the “Wall”

Things were moving along so well I thought i’d jump a head a couple steps, and get Android builds up and running. Something I knew would be painful, and as expected it was.

Before that I have most of the core logic in the game, it’s not all up 100% but we’re now registering interactions and some of the core gameplay. I guess I’ll explain a bit how I do this. I grab a method, for this example ‘TouchMoved’, this is where I detect if a tile is being selected or not. I then simply take the existing cocos2d (objc) code and translate it to c++. Everything maps about .95:1 a very few exceptions, and those are easy enough to sort out. And then when I hit a method call that’s not implemented, I then add that stub and write out the code for it.

Example (pseudo code), in my ‘TouchMoved’ I have a call within, ‘if touch is valid, then execute draw connection code’, well when I got to that part, the draw connection code wasn’t implemented, so I then stubbed out the m ethos ‘drawConnections’, and then translated the code again from the origin objc to c++. Pretty easy, instead of going top to bottom through the old code, this way I can work in snippets of code of the same logic. Sometimes I find improvements in my rewrite this way, because I can see the flow of actions calling the methods.

I had to write some custom wrappers, because I have an interaction handler which uses touches for iOS devices, and mouse / keyboard for mac. I then use that class to send messages, so my core code doesn’t know / care if it’s a touch or a mouse click, to it it’s the same, and it simplifies the code. I had to re-implement that class in C++, and in there I found a limitation that I couldn’t use CCPoint as an argument to a notification. I then created a wrapper class which is a child of CCObject *, (cocos2d-x root object), which I can now easily pass around between the classes to handle my points. It was simple, clever, and it worked, the way good code should!

Now the wall —

So I decided to build up for android, and to do this I had to create an android project with cocos2d-x, and then integrate it into my iOS code. I’ve done this before with ‘Retro Art Studio’ for Android, but that was ages ago, and I’m using a much later version of cocos2d-x now (2.0.x). The configuration is one of the most painful parts of this whole project, and doing anything on Android. Android is hands down the worst platform to develop for period. It’s not that I don’t like the hardware or anything, it’s just very very difficult to configure, debug, etc, especially when doing this type of coding, where everything is custom drawn. iOS has basically 4 devices, iPhone/iPod normal (320×480 screen), the iPhone/iPod retina (Double resolution 640×960), easy as it’s just double. Then the iPad (1024×768) (very close to the iPhone Retina so we can re-use a lot of layouts), and the iPad Retina (Huge but once again, double 2048×1536). I have a couple extras I through in for Mac, which mainly re-use iPad assets. But that’s it, really 4 devices, some nuances in hardware, but displays are pretty easy to accommodate. Android on the other hand has over 2,000 devices with over 325 different possible resolutions, things from watches, to TV sized components. The other thing is the quality of the hardware / type of hardware is almost always an unknown. You don’t know if it’s a touch screen like iPhone, or if it’s an older one which requires a pen.

It’s easy to just go after the new fancy samsung phones, but still to this day only 15% of android users use the new software (4.0.x at this time), 60% are on 2.3, a really old archaic by mobile software terms software version. Unfortunately 2.3 is still being sold, because it’s cheap and widely used. So as a developer I have to support it, but with it you lose a lot of advanced functionality of the later operating systems, most importantly the ability to detect the screen type. On Android 3.x you can simply say ‘only run on a device that can support X resolution in pixels’, below that, (2.3) they don’t read / honor that flag, so users may install an app not designed for their phone. You have a choice, #1 don’t support 70% of the market (other 10% use < 2.3 still), #2 try to support low-end devices while trying to make high end games. It's painful to be blunt. So, the setup was painful to get cocos2-x to use android, to compile then run using Eclipse, while sharing all the code / doing all development in Xcode. It's something that I have to relearn every time, and I really wish I could document it and make it easier on myself and others going forward, but it's literally 4 hours of just hacking, trying this, modifying that, tweaking here, until it works, then you just back up slowly as it's a thin thin ice you don't want to go near. One last note on differences between iOS / Android in our app: WE parse a 80,000 word dictionary at the launch of the app, it's stored in a NSArray Plist, which is readable by cocos2d-x regardless of platform. On iOS (same code) it takes < 1 second, on Android (4.0.3 tablet) it takes 11 minutes. Ponder that, the hardware is virtually the same, actually I can get it in a couple seconds on an OLD iPod touch, 3rd generation, but a new Android Tablet takes 11 minutes. I'm pretty sure users aren't happy with the idea of a 11 minute loading time, so I'll look at other ways to do that file parsing, just unfortunate as it's so quick and easy on ios. It's not a limitation of android nor the hardware, just the limitation of they implementation. But it's small things like this which will take more time than rewriting a core to the game. Anyway, that's where we are hoping our next update has a basic playable version, but we need to fix this file loading issue first.

Aug 24

Cocos2dx Migration -> 2nd update (8 hours)

Right now we have the basics of the menus all loaded, and the main game screen is now loaded and displaying some of the core assets. I did hit an issue on the cocos2dx code, not sure why but for now I reverted back to the original code. I’ll summarize below.

Cocos2d-x has a cool constructor for it’s core objects, instead of multiple different constructors depending on your argument, you can now just call the same one, and feed in your arguments. In plain english…

To create a sprite from a sprite frame name we used to do this:
CCSprite *sprite = CCSprite::spriteWithSpriteFrameName(“frameName.png”);
Create a sprite from a file:
CCSprite *sprite = CCSprite::spriteWithFile(“frameName.png”);
Now we can just do this
CCSprite *sprite = CCSprite::create(“frameName.png”);

The new create() has now replaced just about every constructor in 2.0.x. I found it really easy to use mainly because I’m used to all the constructors and cocos2d lingo, it could be a bit overwhelming if you don’t know cocos2d that much, because it’s nondescript. But I found it easy to use, until it didn’t work.

The issue I had was the one above, adding a sprite frame name from a sprite sheet added to the cache, it didn’t work. So, I had to revert to the original call, spriteWithSpriteFrameName(“frameName.png”);. I’ll keep watching the cocos2d-x source and see if a fix comes in, or better yet understand if I did something wrong. As I’m using the old style, it’s marked as deprecated, so I’ll be reminded to check for updates along the way.

Aside from that hiccup, things are going well, and we have 40 hours to go. Most of the core logic is ported, once the main view is up, we have some custom scrolling views we’ll need to port over which I presume will be time consuming.

Aug 21

Cocos2d -> Cocos2dx rewrite Update 1 (4 Hours)

I am 4 hours into the conversion. I decided to just go scene by scene, so I began by loading in my splash screen and loading scene. The loading scene is something I wrote for cocos2d a while ago and use it in many apps, it’s available on github (although I do need to update that one as I’ve made a couple small enhancements). So I took that and ported it all to cocos2d-x. This was a great place to start because it has some file reading / parsing code in there.

I haven’t done this before on cocos2d-x, and I must say they’ve done a great job. I am able to use all my existing dictionaries (plist) files and parse them just as I did previously, so it was just a matter of updating the syntax to C++ from OBJC and away I went. So in my loading class I do a few things, first I cache all my sprite sheets, sounds, images, etc, then for this game I generate the dictionary which will be used for the game. This is some custom code I have, so it needed to be converted as well. Thankfully most of the code was in C++ already, as that’s usually how I write my performance code. So it was simply going from NSArrays to CCArrays, and changing a few types here and there.

All in all, after 4 hours, I did the whole loading screen, splash screen, and 90% of the core engine. So by going this path, I’ve actually tackled the more technical bits first, as displaying things on the screen is much easier code to migrate. So I think at 8% done I’m making great time.

Next Post:

Aug 21

Rewrite a cocos2d application in cocos2dx in 48 hours

We have an app that is on the iOS store and still waiting review for Mac store. Word Jumblerama Blitz. It’s a quick word game that was a lot of fun to make, and people seem to enjoy playing it. We made the initial release in a week, and now are thinking of porting it to a wider platform to support more devices.

Originally it was written in Objective-C using cocos2d (v2.0). We will now rewrite and migrate the app to c++ using cocos2dx (v2.0). We have done cocos2dx work before, and migrated a smaller app. There are a lot of nuances with this app, such as file reading, writing, parsing huge dictionaries on the fly, etc. So it’s a learning exercise as well as an excuse to do a little android work (which is truly punishing, it’s really not our favorite platform by miles), but cocos2dx does help a lot. Along the way we’ll probably do some JNI to talk to java, but at the same time we don’t just want to do an android port. I want the whole app to be on cocos2d-x, so the next version for Apple will be on the cocos2d-x (C++) code.

The goal is to truly have a cross development / cross platform solution. I always dev iPhone/iPad/Mac on the same code, this time we’ll push it to more platforms including Android, and Windows. Our target is a complete app feature set to our latest release, (minus the iOS specific game center, iAd, etc) running on cocos2dx. Initially we’ll just aim for a iOS version in this first pass of the code, then use that to migrate to other platforms.

And we’ll time cap this at 48 hours (however, it may be broken apart in multiple days, depending on other work).

First Update (4 Hours)

Jul 13

Word Jumblerama Blitz for iOS Released

Word Jumblerama Blitz Icon

Our new iOS game is released! Word Jumblerama Blitz, is a fast paced word searching game. The game is a free download from iTunes, and supports Game Center.

If you like word games, and are a quick word finder then give the game a shot and see how you fare on the game center leaderboards! This is the first release, and we are planning to incorporate two player vs match making very soon.

Game information Page

Word Jumblerama Blitz - Six Foot Three Foot

May 23

Retro Art Studio 1.3.0 for iOS Released – New Features

Retro Art Studio has just received it’s latest milestone for iOS. This release was a quick release after 1.2.0 to address some additional customer feedback.

Most importantly, our top requested feature was a way to purchase the app. It seems Retro Art Studio is a hit with young ones and others alike, so to stop those small hands from accidentally clicking on ads, they can now be disabled via in app purchase. We also added a way to blend colors together, by clicking on two different colors on the color bar. (Click Red then Green to get a gradient between the two).

Also a request on iPhone was the ability to have larger LED / Pixels for the smaller device. Now on all devices you can select the size of the LED / Pixel via a configuration menu.

We removed the ‘undo’ button as well to make room for the configuration, also it was not really necessary as we have a nice eraser that’s ready to use.

Thank you so much for all your feedback, and we hope you enjoy playing our games.

Older posts «

» Newer posts