| Subcribe via RSS

OddSpotter development

May 20th, 2012 | No Comments | Posted in Apple, apps, iPad, iPhone, Titanium

In this post I would like to share details with you how my first mobile game OddSpotter came about. OddSpotter for iPad is live on AppStore now and you can download it for free here.

I’ve been developing commercial apps for iOS mostly for a while now. Mostly for large companies and some for startups. Most of the apps are to support the existing business models of a company and couple (like Alcometer and Airtumble) are a technical innovations themselves.

But, lately I’ve felt a bit dry developing for commecial clients and I need a personal project of my own.

I’ve always been fascinated by games and I play quite a lot myself. So on a weekend on March 2012 I started  to develop my first mobile game OddSpotter.

It’s ‘spot the difference’ type of game, where player will see two images side by side and they will have to spot the differences between those two.

There are three reasons why I chose this game to be my first birdie.
1. The concept itself comes from my friend Strange (strange name right) who I had a pleasure to study together with in Odense Denmark. Strange visited Shanghai, china and said people loved a game called ‘find the difference’. He said people were paying money in China to play this game.
2. I’m a hobby photographer so I have no problems with content for such a game.
3. This kind of game is relatively easy to build (especially coming from commercial apps background). So I take it as a study into in-app-purchases and game center etc. Before I move on to my next game idea.

I started with a little market research. There was some apps like this in AppStore, so I could evaluate the overall quality that is needed. I found out that to succeed I needed to have two important features: pinch&zoom for gameplay and free app with in-app-purchases as a pricing model. First would make my game to stand out among others, and other would give me a chance spread the game and to maybe earn something.

This is the first view after the splash screen

Convinced that it is worth it, the next thing in the list was to start developing. I started from the core functionality as a proof of concept. Took a photo and built the hotspots, and worked on pinch&zoom functionality. There were bugs in the gameplay, but as soon as I saw I can do it well and it is playable, I continued with everything around the game.

I was surprised that the game core is actually not the part of the game that takes the most amount of work. It’s rather everything around it. The worlds, the leveling system and their UI’s, score keeping, timing etc. Once I nailed the UI for the levels and made it functional I started to build content. That meant a lot of photo editing. I took all the photos from my showcase http://sandbox.teemusk.com/nightshots2 and used clone stamp tool in Photoshop to make them different.

Then I built a custom Adobe Air app where I could mark out the difference spots on each of these photos, and which would turn the spots to data readable by OddSpotter. Once I had my database files filled with data about the photos and their Odd Spots I included them into the app.

Note that at this point I had no clear idea how would the selling be done. Should I sell a pro version of the app? Maybe sell levels or worlds as in-app-purchases.

Anyways, although the UI was not polished I decided to show the game to a friend during lunch break. He liked it, but found it too difficult (I guess the stamp tool radius was too small making odd spots rather small too). So he was asking for hints all of the time from me. “Around where is the next spot?”, was something that I heard a lot. I ended up zooming the view to a place where an odd spot was and he was trying to find it. This worked. So he gave me a superb idea. I will sell hints via in-app-purchases. Game will come with 5 hints and when you spend them all you can buy more for real money. All levels will be free. Genial. Perfect.

Next thing I built the hints functionality and started testing in-app-purchases. The latter was a nightmare. I pulled my hair out for two days wondering what am I doing wrong, only to find out Apple’s sandbox server for in-app-purchases was down. I can honestly say that was the most difficult and stressful part of the whole development.

I waited for another two days until apple IAP sandbox came up again and was all set.

At this point I had a ready built app with my own photos as content. I was ready for more testing on real people. I took my iPad with me everywhere and let people play the game telling them the story behind it and asking questions about the gameplay. Most of the people were my friends and ofcourse they said they like the game, but also gave me a lot of insights what should be done better. As the first friend it was obvious that the levels should be easier than they were.

Also, though nobody really told me, I realized that people don’t really want to look at photography that much. The photos were all night shots and looked too much the same. Then my girlfriend came up with an awesome idea to use paintings as content and not photos. Everybody loves art. After googling around for legal stuff and good data sources I found out that I can use Public Domain art as content for free. That was settled then. I dumped all the photos as a content (lots of time wasted there) and started again with paintings.

Lots of photoshopping followed, but after couple of days I managed to make the app fully functional again with paintings as content. And I must say this really worked. It’s so much more fun and educational to look for art from famous painters and find odd spots on the artwork.

But. My struggles did not end there. I had one major problem, app ksize. The app with all the levels/paintings inside would weigh more than 40 mb. That’s way too much. A good app won’t have more than 20mb as initial download. If an app is more than 20 mb then AppStore won’t let users download the app on a 3G connection, but wifi has to be used. That means many potential clients would be turned away after “INSTALL” click.

So I had a plan. I added first 20 levels into initial app download and developed a whole new system so I can dynamically add more levels over time. The system goes shortly as follows. App will check for updates after being 10seconds active, if an update is found it will download new levels as a zip package. After download it will unpack the zip and add them to level selection notifying the user about new levels.

That was also quite a lot of work, but I pulled it off over a long weekend.

Promo screenshot which shows tutorial and gameplay basics

After giving the game final touches (like tutorials for first level of the first world), I was ready for submission.

Conclusion.
I learned quite a lot from developing the game, but the main points I should remember are as follows:

  • It is much more work than you think it’ll be.
  • It’ll take longer than you think it’ll take.
  • The game engine is a little percentage of the overall work. A lot of work is around the engine itself.
  • Test the game on real people as early as possible and modify it if necessary.
  • Try to get to acceptable build asap and submit it. You can make updates later
  • Try to think about marketing as early in the game as possible.
  • You can figure out/modify the monetizing ideas later.

OddSpotter for iPad was released 1st of May 2012.

I might write about initial sales and marketing efforts soon if there’s enough interest.

 

 

 

 

 

 

 

Tags: , , , , , , ,

Building Server Push Notifications with Appcelerator Titanium Cloud

May 5th, 2012 | 52 Comments | Posted in Apple, apps, Titanium

Appcelerator has blessed us developers with cloud services since release of Titanium 2. Even free registered users get 1 million server push messages a month free. Server push notification means that you can send users push notifications even when the app is not running on the device.
Cloud also gives lots of nice stuff for developers which eases the pain and the need of a custom back-end for your mobile app.

Although Appcelerator allows server push, many developers find it difficult to set it up. One of them being myself a couple of days ago, therefore I thought I’d give back to the community and wrote a little tutorial showing hot to make Server Push Notifications work for your app. I will concentrate mostly on certificate management, which is the most painful part of setting up Push Notifications on Apple devices.

 

1. Start a new Titanium project in Titanium studio. For this example we’ll call it PushTest and give an app ID com.teemusk.pushtest

Project setup in Titanium Studio

Project Setup. Make sure Cloud-enable this application is checked. Alternatively you can enable Cloud services on tiapp.xml editor.

Add a simple code to your app.js to open a window and run your app on simulator once so it’ll get registered and enabled on Titanium. The code for app.js looks like this right now:

var win = Titanium.UI.createWindow({
title:'TestPush iOS App',
backgroundColor:'#fff'
});
win.open();

1.3. Run your app on simulator once to see if it is ok. There should be nothing on the screen. Just white background.

2. Set up the cloud services and Certificates

2.1. Go to https://my.appcelerator.com/apps and find PushTest app from the list (you must be logged in to see that).
Your newly created app on Appcelerator

As you can see you have Cloud services already enabled for this app. That’s great.
2.2. Click Manage and check the settings for this app
2.3. Click Settings on top tabs. As you can see Apple iOS push certificates is empty. You will have to obtain a certificate from Apple iOS Provisioning Portal (you have to be an Apple developer to do this).
2.4. go to iOS Provisioning Portal through developer.apple.com and to Provisioning portal after logging in on Member area.
2.5. Create new App ID by choosing App IDs from left and then clicking ‘New App’ on top right corner.
2.6. Add PushTest as an app name and com.<yourdomain>.pushtest as an app id. Then click Done.
2.7. Now as you can see from the list your app is not quite set up for push notifications. You will have to configure it.
Push notifications not configured on Provisioning Portal

2.8. click Configure next to your app and Enable Apple Push Notifications on the following screen.

2.9. Next part is a bit tricky as you’ll have to work through some different things to do this, but basically you will have to get a certificate for your app to get Push Notifications working. Click Configure button next to ‘Development Push SSL Certificate’. The page that opens up is self explanatory. But in case you don’t want to read all this stuff then shortly it’ll go as follows:
2.10. Open up Keychain Access software on your mac. Choose ‘Keychain Access > Certificate Assistant > Request a Certificate From a Certificate Authority…’ from top menu.
Obtain a Certificate

This will open up a dialog where just click ‘Save to Disk’ and ‘OK’ and then save the incoming certificate to your Desktop. Click ‘Save’ and ‘Done’.
2.11. You have a certificate on your desktop. It’s filename is ‘CertificateSigningRequest.certSigningRequest’.
2.12 Go back to Provisioning Portal and upload this file back to Apple. click ‘continue’, ‘choose file’, choose the certificate you just saved on desktop and click ‘Generate’. This will take a couple of seconds, but after it’s done click next and download the certification with your name called ‘aps_development.cer’.

2.13. Double click on the downloaded .cer file and it’ll be added to Keychain Access.
2.14. Select the certificate in Keychain Access with the name com.<yourdomain>.pushtest and right click (or command click) on it to open popup menu. Choose Export “Apple Development iOS Push Services” from this menu and save this file with extension .p12 on your disk. You will be asked for a password. Remember what you put in there. This is the final certificate you will have to upload to Appcelerator my apps.

2.15. Now, go back to Appcelerator my app settings for PushTest app and browse and upload the newly created .p12 certificate. Also add the password you chose in 1.16. in the box next to it.

Great, you’re done with the painful part of the tutorial. Now it’s good old titanium scripting again.

3. Code the app
I consider this tutorial not to be a scripting tutorial. Therefore I will just paste my app.js code below. I tried to comment my code so you can see what each function does. This code works on your phone. To run it on your phone you will have get a provisioning profile from Apple Provisioning Portal. I also uploaded an app.js for you to download and investigate.
The results of this code will add 4 buttons on the stage. When running the app on your phone the first time start pressing the buttons from top and after each tap wait for success alert dialog. Once you reached the end you’re all set.
var Cloud = require('ti.cloud');var trace = Ti.API.info;
var user_device_token = Ti.App.Properties.getString("device_token",null)var win = Titanium.UI.createWindow({
title:'TestPush iOS App',
backgroundColor:'#fff'
});
win.open();function init(){
buildUI();
}
setTimeout(init,500);function buildUI(){
var register_local_push = Ti.UI.createButton({
width:200,
height:30,
top:30,
title:"REGISTER LOCAL PUSH"
});
win.add(register_local_push);
register_local_push.addEventListener('click',getDeviceToken);var register_user_btn = Ti.UI.createButton({
width:200,
height:30,
top:70,
title:"REGISTER USER"
});
win.add(register_user_btn);
register_user_btn.addEventListener('click',registerUser);var login_btn = Ti.UI.createButton({
width:200,
height:30,
top:110,
title:"LOGIN"
});
win.add(login_btn);
login_btn.addEventListener('click',login);var register_server_push_btn = Ti.UI.createButton({
width:200,
height:30,
top:150,
title:"REGISTER SERVER PUSH"
});
win.add(register_server_push_btn);
register_server_push_btn.addEventListener('click',subscribeToServerPush);
}//REGISTER USER ON CLOUD
function registerUser(){
trace("REGISTER");
Cloud.Users.create({
username: "new_username",
password: "new_password",
password_confirmation: "new_password",
first_name: "Firstname",
last_name: "Lastname"
}, function (e) {
if (e.success) {
alert("USER CREATED SUCCESSFULLY.");
// user created successfully
} else {
// oops, something went wrong
alert("USER not created. something went wrong "+e);
}
});
}//LOGIN TO CLOUD AS A USER THAT WE CREATED BEFORE
function login(){
Cloud.Users.login({
login: 'new_username',
password: 'new_password'
}, function (e) {
if (e.success) {
var user = e.users[0];
alert('Success:\\n' +
'id: ' + user.id + '\\n' +
'first name: ' + user.first_name + '\\n' +
'last name: ' + user.last_name);
} else {
alert('Error:\\n' +
((e.error && e.message) || JSON.stringify(e)));
}
});
}//REGISTER LOCAL PUSH NOTIFICATION HERE
function getDeviceToken(){
trace("REGISTERING LOCAL PUSH");
Titanium.Network.registerForPushNotifications({
types: [
Titanium.Network.NOTIFICATION_TYPE_BADGE,
Titanium.Network.NOTIFICATION_TYPE_ALERT,
Titanium.Network.NOTIFICATION_TYPE_SOUND
],
success:function(e)
{
user_device_token = e.deviceToken;
Ti.App.Properties.setString("device_token",user_device_token);
alert("Device token received "+user_device_token);
},
error:function(e)
{
alert("Error during registration: "+e.error);
},
callback:function(e)
{
// called when a push notification is received.
alert("Received a push notification\n\nPayload:\n\n"+JSON.stringify(e.data));
}});

}
//REGISTER SERVER PUSH
function subscribeToServerPush(){
Cloud.PushNotifications.subscribe({
channel: 'friend_request',
type:'ios',
device_token: user_device_token
}, function (e) {
if (e.success) {
alert('Success'+((e.error && e.message) || JSON.stringify(e)));
} else {
alert('Error:\\n' + ((e.error && e.message) || JSON.stringify(e)));
}
});
}

 The code above is also uploaded as a file. You can download it here

4. Send your first Server Push notification
After running the app.js code on your iPhone start to tap the buttons from top to bottom. After each tap wait for the alert message with success message.
The app looks like this:

When you’re done with this sequence you’ll ready to send your first push.
Go to Appcelerator my apps section. Choose ‘notifications’ from the tab on top and check that you have a device registered with server push. My window looks like this:

Close the app on your phone (close it totally from bottom). Fill in the fields and push send notification. Now wait a bit to receive the push on your phone.

 

That’s it. I hope you get it working and find that it’s actually quite simple once you get it to work the first time. Also I hope this tutorial saves your time a bit.

Thanks for reading.

Tanel Teemusk
teemusk.com 

 

 

 

EDIT:

An extra checklist for debugging.
1. You cannot use wildcard development certificate for trying this. be sure to use com.yourdomain.yourapp or similar and not com.yourdomain.* or anything that involves asterisk. Otherwise push won’t work. (Thanks to TaMaX for pointing this out)
2. After your app goes live to AppStore be sure to upload another p12 certificate to Appcelerator using iOS Production Push certificate from Keychain Assistant. Development Push certificate won’t work after going live. (Thanks for DevMan for pointing this out)

Tags: , , , , , , , ,
  • Ads