Tuesday, December 14, 2010

Your Japanese Name for iOS, part 19

Entering a name now turns it into katakana!



I thought showing the characters vertically is just the same as horizontal, but actually it isn't. The vowel elongation character needs to be turned 90 degrees so it goes up-down instead of left-right. Also I'm missing proper consonant doubling character. Luckily it's the same as the "TSU" sound except a bit smaller, so I can just scale the TSU graphics I already have. Still need to test it more, should probably try to make it show every possible character to make sure it doesn't crash on anything and to see that characters are properly positioned. I'm guessing some of the smaller characters won't be displayed properly. But maybe I should work on some other part of this program now. Curious about how email will work.

I use the chrome browser. It doesn't work well with iTunes Connect site which is used to look at these graphs, so I wrote a Chrome extension that fixes iTunes Connect sales graph. I'm checking my sales stats for Acey Deucey every day. It's crazy, I thought sales would be zero, but instead I've been getting a sale or two every day. I can buy two delicious peanut butter sandwiches every week with this. Well, the government will eat at least half of the other sandwich.



Learned that it's possible to attach an image to an email as long as I save it as a file first. To get this file, I can turn the graphics context into an image and then perhaps do
NSData *imageData = UIImagePNGRepresentation(image);

I'm not sure if I should though. Pros are that the user might be more likely to send an email if the image is nicely displayed already in the preview. Cons are that it will require a bit more bandwidth from the user, only a few kilobytes though. Probably the user will not perceive this to be much, but who knows. Unknown if the recipient will find it less or more appealing to click through if the email already has an image or not. It might not be even displayed by default. Hmm.. probably easier and more reliable to just provide a link to an image in the mail, rather than the image itself. That's how e-cards work. Actually I should probably look at the layout of the emails some e-card companies send to get an idea what works.

Interesting, http://www.123greetings.com/ has an option for "Let me know when the receiver views this ecard". Maybe I should take this opportunity too to contact the sender again? And they just send a link to the site, so OK that's the best way to go. Where should the link lead though? Probably some page that shows the result and a link to the application. Most recipients probably wouldn't have an iPhone. Should probably indicate that the recipient doesn't need one.

I just sent you "Jackie" in Japanese.

You can view it by clicking here:
http://...

Keep it simple!

Monday, December 13, 2010

Your Japanese Name for iOS, part 18

The app will have two ways to convert latin characters into katakana characters. First one is a dictionary that I wrote with Nachi for Your Japanese Name on Facebook. If a name isn't in the dictionary, then the second way is an algorithm. Actually the algorithm is almost as good as the dictionary is, because the conversion is quite straightforward.

I wrote the algo originally in Python, where it was 6k in size. I just finished the Objective-C conversion and it turned out to be 8.5k. Luckily Cocoa had good unicode support, so it wasn't nearly as bad as I feared. Doing things like removing diacritics was as easy on both. Line with the difference was biggest was
r = s[::-1].replace("l", "r") 

Which in Obj-C became

+ (NSString *)stringReversedFromString:(NSString *)s {
NSMutableString *reversed = [NSMutableString stringWithString:@""];
NSUInteger len = [s length];
for (int i = len - 1; i >= 0; i--) {
unichar ch = [s characterAtIndex:i];
NSString *charStr = [NSString stringWithFormat:@"%C", ch];
[reversed appendString:charStr];
}
return reversed;
}

...

NSMutableString *r = [[self stringReversedFromString:s] mutableCopy];
NSRange replaceRange = NSMakeRange(0, [r length]);
[r replaceOccurrencesOfString:@"l" withString:@"r" options:NSCaseInsensitiveSearch range:replaceRange];

Saturday, December 11, 2010

Acey Deucey part 18

Apple approved it!

Acey Deucey aka In-Between is up for sale!

I don't expect it to sell, but it feels great to finally have released something for an iDevice. I'll have much more confidence building more stuff, now that I know I can navigate the submission process.



Update: I made a sale! Who was it, someone from this blog perhaps? Thank you.

Friday, December 10, 2010

Your Japanese Name for iOS, part 17

Getting really tired of this project, but I'm going to finish it like a boss. What upsets me is that this turned out to be more work than I expected, but still the upside is very small. Maybe I picked the wrong risk-reward ratio here. Well, at least I'm learning a lot.

Inside my UISlider I'm adding a bunch of my own KatakanaView objects that render the SVGs I drew. Next I'll have to add support for variable sized characters. That means that the owner of the KatakanaView should decide the width, but KatakanaView decides the height and reports it back to the owner.

... why is the background of my UIView black, even though I'm not drawing it so?

Ah the backbuffer for a view gets initialized to zero by default. Have to set backgroundColor to UIColor clear and opaque to NO.



Basically it works, even calculates proper distance between views vertically. Now the characters are too small though. I can't just maximize each character horizontally, because they need to be consistent with each other. Might suffice to just experimentally increase size until it looks good.

Wednesday, December 08, 2010

Your Japanese Name for iOS, part 16

Today I hope to get at least AdMob working and display the SVG characters I made on screen. AdMob came with simple enough instructions, but after I included it in my project the app started crashing. I probably missed some step in their integration document or did something wrong, since their example works fine. Looking forward to their dashboard showing a non-zero amount for me.


I'm least looking forward to handling Twitter, Facebook and email. I suppose I'll have to recode some picture routines to run on my server too, as I might not be able to make the necessary attachments in the iOS program itself.

...

Got it working! Not sure why, but I had to connect the "Ad View Controller" in Interface Builder to an AdViewController IBOutlet in my own view controller, otherwise it would crash. Console said that the crash was because some method of a deallocated object was called. So does this connection somehow cause the AdViewController to get allocated? I thought everything I put into Interface Builder gets allocated and inited, otherwise how can all the text labels etc. work at all. I still really don't understand how IB and my code interact.

Discovered a nice debugging tip called NSZombieEnabled.

...

Seems I have misunderstood something about SVG. Even though apart from some scaling the coordinate system in my SVG files should be the same as in my iOS graphics context, things come out all wrong. All coordinates should be positive, but when I look at my JSON file, I have some negative ones there too. Are SVG path coordinates actually relative to something rather than absolute? Ah, seems to be relative to previous coordinate in the path. Yes!

Tuesday, December 07, 2010

Your Japanese Name for iOS, part 15

Did all the required icons during last night. It seems that mapping icon sizes to correct filenames is something I'll end up doing often. When making the icons naturally I want to name them "512x512.png" for example, but then when I add them to the project they need different names. So here's a list of commands, assumes you're currently in the art directory and want to move things to ../icons

#!/bin/bash
mkdir ../icons 2>/dev/null
cp 29x29.png ../icons/Icon-Small.png
cp 50x50.png ../icons/Icon-Small-50.png
cp 57x57.png ../icons/Icon.png
cp 58x58.png ../icons/Icon-Small@2x.png
cp 72x72.png ../icons/Icon-72.png
cp 114x114.png ../icons/Icon@2x.png
cp 512x512.png ../icons
ls -l ../icons
echo "Now add all these ../icons to the project, except upload 512x512.png later by hand to itunes connect."

Next I should think about how to make the characters appear. Next to each characters should be explanation of it in latin alphabet. There may be several characters, possibly dozen or more. Each one should appear as described in the SVG file. Maybe they could all be as wide as the screen is, and the white central area could be a UIScrollView. While they are appearing, the current character could be automatically scrolled to view. Then in the end it could scroll to the top. So all I need is an UIView subclass that knows how to display one character and I'll be able to stack several of those inside the scroll view.

Got more distracted and made another Chrome extension.

Monday, December 06, 2010

Your Japanese Name for iOS, part 14

Decided to split this app into two different versions. 0.5 won't guide the user in drawing their name, it will just display the result. 1.0 will include the drawing part. This way I can get something released while I'm still working on it, which should help motivate me complete this faster.

I think I'll make 0.5 free and try out AdMob to get some experience with mobile ads.

What should the main app screen look like? Tried mocking up a bit but everything looks horrible.



That list is supposed to show some popular names. Is showing the complete list of available names necessary? It's way easier to pick things from a list than try to come up with names to try without any hints. Most convenient would be if I could access their address book and show some names from there. In any case there should be a free input field in case the user wants to input something that's not in the list.

I already have an idea for the next app. I think it's an original idea, uses the platform well, is easier to make than Your Japanese Name and has wider appeal.

Update: New mockup for 0.5.



Progress is slow. Got a bit distracted and made a site for posting to Twitter using Chrome speech recognition.

Sunday, December 05, 2010

Your Japanese Name for iOS, part 13

Description

You don't need to know any Japanese to use this app. Your Japanese Name turns your name into Japanese characters and even teaches you how to write it step by step. Surprise a friend by sending them their name over email or impress your friends by posting your result on your Facebook wall.

FEATURES
- Your name displayed in Japanese "katakana" characters.
- Step-by-step name drawing guide, learn the strokes to make the characters in your name.
- Real translation done by a Japanese person. Our hand-made dictionary has tons of popular names.
- Algorithmic translation as fallback in case you have an uncommon name, so you always get a result.
- Post to Facebook.
- Post by email.

DEMO MOVIE available at http://youtube.com/blahblahblah

Saturday, December 04, 2010

Your Japanese Name for iOS, part 12



Gimpstorming what the icon could look like. It's easy enough to make something that looks not-totally-like-crap when a picture is big enough, but try to do it in 52 x 52 pixels and it turns into mush.



With an image this tiny it needs to contain some easy to recognize outline of an object with it and contrast has to be really sharp. I feel that a calligraphy brush isn't really something that people are familiar enough with that it would be recognizable as an icon.

...

Agonized over the icon whole saturday evening. Made some mockups, looked at tons of other icons for inspiration, but nothing really clicked. Maybe it's best just to go with the simple one I'm already using on the Facebook app, it'll make it more consistent too, not to mention less work.



I'm so envious of the beautiful icon Zen Brush has. The atmosphere of the colors, the mysteriously shaded bristles of the brush, the wooden texture of the handle... just perfect.

Friday, December 03, 2010

Your Japanese Name for iOS, part 11

All katakana done in SVG.

So much work and I'm not even halfway yet with this app -_-

Thursday, December 02, 2010

Your Japanese Name for iOS, part 10

Morning. Now I know how to read data in with JSON, so it's time to extract that data from the SVG files. For this I'm going to use minidom, which conveniently is already included with Python. Input is going to be a directory of SVG files, and output will be the stroke, segment and waypoint JSON that iOS will then later read in. Minidom lets you deal with XML just like from Javascript. You can use things like getElementById and getElementsByTagName. In this case I wanted to get all the positions of the SVG elements:

dom = xml.dom.minidom.parse("some_svg_file.svg")
coords = []
for rect in dom.documentElement.getElementsByTagName("rect"):
attr = rect.getAttribute
coords.append([attr("x"), attr("y")])
print coords

With similar fiddling I was able to make a script that turns the whole directory into a single JSON file with all the info required to show the strokes, segments and waypoints. Next I need to complete drawing the remaining characters and then start working on reading this structure on iOS and showing the waypoints as circles.

...

Drawing these characters is a lot of work. 90% complete, tomorrow I'll have all 80 of them done.

Wednesday, December 01, 2010

Your Japanese Name for iOS, part 9

Today I should try to get the vector art done for a few characters at least.

Workflow:
- open SVG editor
- run google app engine launcher to serve frames
- use this SVG as skeleton:

<svg width="1280" height="960" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns="http://www.w3.org/2000/svg">
<g>
<image xlink:href="http://localhost:8896/static/A.png" id="svg_1" height="960" width="1280" y="0" x="0"/>
</g>
</svg>

- change image to be the current image (go in alphabetical order)
- trace segments in order (look at video if in doubt)
- draw rectangles for each waypoint in order, consequent segments can share same waypoint
- change color of rectangle when stroke changes
- save svg as A.svg for example



Drew half of the characters as SVG. Time consuming, but not impossibly so. A few minutes per character. Read about the SVG format. Paths are very simple to understand. How will I render these on the phone? I could either tessellate to triangles beforehand, or alternatively draw full paths with Quartz 2D. Yep, there's CGPathMoveToPoint and CGPathAddLineToPoint, so no need to do triangles. What next?

Next, to make some progress I should come up with a way to represent the data so I can easily access it from Objective C. Then, I should make a simple version where the waypoints for each stroke are shown and touching them correctly moves the user along.

Given JSON file "katakana.json" which as a test contains just

{"test" : "yeah"}


This prints out "yeah":

- (void) jsonTest {
SBJsonParser *parser = [SBJsonParser new];
NSString *fullPath = [[NSBundle mainBundle] pathForResource:@"katakana" ofType:@"json"];
NSString *jsonString = [NSString stringWithContentsOfFile:fullPath encoding:NSUTF8StringEncoding error:nil];
NSDictionary *dict = [parser objectWithString:jsonString];
if (dict) {
NSString *out = [dict objectForKey:@"test"];
NSLog(out);
} else {
NSLog(@"Could not parse JSON.");
}
}

Acey Deucey part 17

"The status for the following app has changed to In Review."

And then almost right after:

"The Application Name on iTunes Connect is In-Between, while the name displayed when the app is installed is Acey Deucey."

Also they included specific steps on how to fix this problem. Awesome! I was expecting outright rejection with some vague reason. Instead I got a chance to fix this while it's still in review instead of starting over. ... Went into Itunes Connect and actually this IS a rejection. Application state is now "rejected". Oh well. Changed the name and reuploaded binary.

Tuesday, November 30, 2010

Your Japanese Name for iOS, part 8

I suppose as some sort of balance to yesterday's activity, today I feel burned out. Even slow progress is some progress, so I should attempt to get at least some small thing done. So I'll attempt to get all the last frames of the movie files out today. Seems the simplest solution is just to get ALL the frames and discard everything except the last one. Which would be the same as just outputting them one after another overwriting the same file... I/O error. Okay, so get all and discard all but last.

Done. This gets last frame of each m4v file in the "m4v" directory and puts it in the "out" directory.

import os, shutil
TMPDIR = "blahfuck"
OUTDIR = "out"
for fn in os.listdir("m4v"):
for del_fn in os.listdir(TMPDIR): os.unlink("%s/%s" % (TMPDIR, del_fn))
os.system(r"ffmpeg -i m4v/" + fn + r" " + TMPDIR + r"/%d.png")
last = sorted(map(lambda x:int(x.replace(".png", "")), os.listdir(TMPDIR)))[-1]
outpath = "%s/%s" % (OUTDIR, fn.replace("m4v", "png"))
shutil.copyfile("%s/%s.png" % (TMPDIR, last), outpath)

Idea of getting the characters through SVG seems like a good one, but I can't start doing that now. So what to do instead? Maybe learn about how to post to Facebook. Nice, this SDK seems very easy to integrate. Comes with a simple demo app that posts to facebook stream. Adding this to my project also got me a neat JSON library. I will enjoy it.

Facebook login almost works, but do I really need it to post to the stream? Can't I just invoke the stream post dialog without this login hassle, I remember seeing it in some other app. But time to sleep now ...

Monday, November 29, 2010

Your Japanese Name for iOS, part 7

Next I'll need to come up with a dataset of all the segments and waypoints. For reusability, it would probably be best to have a vector representation of each segment. Seems likely that such a dataset doesn't exist yet, easiest way to get one would be to just draw one in some vector editor that lets me display a raster image in the background for reference.

Another option is just to make each segment in Gimp at retina display native resolution. It would be easier, but then porting this to some other resolution like to the iPad would be harder. Of course even for older iPhone I would need a half-res version, although for that I could just scale without redoing anything.

Hmm.. I'm already a bit familiar with Blender. I could make the characters there and get out a triangle list. This solution appeals to me, because I get to play with Blender :-) What would the output look like? I would have one file for each segment. A file that tells where the waypoints are in each segment. Then a file that describes how these segments relate to each character. The most natural way to describe this would be in JSON, and luckily there seems to exist an actively developed JSON library for Objective-C.

segments = {
0 : { // each segment has integer ID
"tris" : [
[0, 2], [1, 2], [1, 3], // coordinates for one triangle
[1, 2], [1, 2], [2, 3],
[0, 2], [4, 2], [1, 3], // each segment would consist of several triangles
...
],
"waypoints" : [
[1,2], // exactly two waypoints per segment
[3,4]
]
},
... more segments
}

characters = {
"ka" : [ // each character would consist of several segments laid over each other, order here is significant for drawing
{
"segment" : 0, // identifier of segment
"offset" : [1,2], // XY coordinates where the segment should appear
},
{
"segment" : 1,
"offset" : [2,3],
},
... // each character consists of multiple segments
],
"ki" : [ ... ],
...
}

It would be pretty straightforward to write a Python script that generates these. Probably less straightforward dealing with Objective-C types when reading them in. Alternatively could make that Python script just generate Objective-C so the types would already be correct and access easier.

Stuff I need:
- Install Blender and get it to work with my keyboard or buy a new keyboard that has numeric keypad
- Exporting triangles from Blender
- Figure out a way to comfortably choose waypoints (repetitive task)
- Also need some tool for composing characters from multiple segments



Uhh am I about to embark on creating some vector drawing program here? x_x Just as a fun thought, if these tools were really good, could I somehow get this task crowdsourced for all Japanese characters? There are thousands of them.

Came up with another option. Use SVG. There's an SVG editor in Javascript already available. It even knows how to overlay vectors on top of an image. Ooh, it has text support. So I don't even need images as I can draw on top of unicode text. For each character in katakana, go to SVG-editor and create a 1280 x 960 image with the desired character at position 400, 800 in size 900. Draw each segment (note: not stroke, a segment) on top of the character. Use as many segments as seems necessary to capture the desired path. Then, place rectangles on top of the complete character to get waypoints. Place them in the order the character should be drawn in. Use different color for each segment's rectangles so that they can be associated with each other. Save SVG (copy & paste) into a file like "a.svg".

This should have all the info in it necessary for revealing the character as it is swiped by finger on the phone.

Have to be more careful in the transitions between segments. I can see a gap between first two segments of A here.

Realized something. I should definitely make these based on our calligraphy videos instead of on an existing font, because then the videos and the vector art would match exactly, making it possible to do some cool transitions between them in the future (for what purpose I'm not sure). Also it would clarify the issue on copyright, as I wouldn't be basing the art on any existing font.

So I need the last frame of each of these videos in order to do this. Sounds like a job for ffmpeg.
ffmpeg -vframes 1 -i frametest.m4v -f image2 output.png

This gets the first frame. But how to get the last one?

Mega Jump

One of my favorite iPhone games is "Mega Jump". It really is a game made with this platform in mind.

In the game you control a character by tilting the phone from left to right. The character jumps higher and higher the more stuff it collects. I love the simplicity of the controls. Many games attempt to be like PC games and have dual virtual joysticks, but that doesn't really work well. In Mega Jump there is no need to touch the screen at all during the game. I love the graphics too. As you can see it has that "cel shaded" feel to it, solid colors with thick black borders.

And particles!

The game would be just fine as it is and pretty successful too I think, but what really sets it apart is how it entices the player to come back. You play it a few times, and just when you're about to get tired it unlocks something for you. You see, every time you play you get kind of experience points, and these unlock new levels, bonuses and characters. So when you return to the game, it will have something new in it to try, even though the gameplay itself is as simple as ever.

Your Japanese Name for iOS, part 6

Got some good suggestions for playing audio. Looked at Finch and OpenAL. One thing in common seems to be that background loops are played with AVAudioPlayer. Apple's "oalTouch" example seems to be easiest for background music playback. It didn't loop though, but docs say it should be possible to get it to loop, so I'm hopeful. Also a bit optimistically I'm hoping that I could instantiate multiple AVAudioPlayers for each sound. None of the examples seems to be doing that, so maybe there's a reason why it doesn't work, but docs say it should.

Got background music to play. Bought sound from iStockphoto. Converted from WAV to M4A through iTunes and customized a snippet from oalTouch example:

bgURL = [[NSURL alloc] initFileURLWithPath: [[NSBundle mainBundle] pathForResource:@"koto" ofType:@"m4a"]];
bgPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:bgURL error:nil];
bgPlayer.numberOfLoops = -1;
[bgPlayer play];

It really does seem to be a perfectly seamless loop. Listened for a few minutes and got tired of it already :-)

Next I should see what happens when headphones are plugged / unplugged. In Mega Jump the music just continues playing. Apple guidelines say the music should stop, but I don't think that's suitable for me because there would be no way for playback to continue, just like there isn't in Mega Jump. Well, I suppose I could show a big pause button, but it seems like overkill.

Great, seems the sound continues by default, so don't need to handle it at all.

Next, how to fade in and out the sound of chimes when finger is moved around. Cool, found fade out example code.

Works as advertised. Found a new case again. User puts finger down, drags, lifts finger up, drags at another point. Sound abruptly ending and new starting sounds painful. Instead should let chimes from old movement fade out while the new sound starts. I was wrong to think I only need 3 channels. Luckily AVAudioPlayer handles this transparently, so I just need to instantiate a new player each time the user puts their finger down. May cause problems if user taps a hundred times within a second. That would allocate a hundred players with all the sounds mixed together, will have to test to see if it's a problem.

Now chimes overlap and fade out as I originally planned. And yes, tapping too fast turns out to be a problem. This device is slow enough that by mixing too much this naively I can apparently max out the CPU. Well, I'll just have to cancel the oldest sound if some maximum mixing amount is reached.

Done. Next should start planning how to separate Japanese characters into drawable blocks. The structure is such that each word consists of several characters, each character consists of several strokes and each stroke consists of several segments. Each segment has a start and end waypoint that need to be touched in order for the segment to be completed.

Sunday, November 28, 2010

Your Japanese Name for iOS, part 5

"I'd rather use a few days to make a simple mixer" <-- famous last words?

There's some stuff I didn't consider.

- If I have a big sound, it needs to be streamed from disk because there might not be enough memory to load it all in. I could try to make this easier by having a shorter loop.
- Sound needs to stop if user plugs their headphones in / out or attaches their iThing to an external sound system ("audio route change").
- Also need to stop playing if the user receives call / sms on iPhone.
- What if the user closes the app in the middle (applicationWillResignActive). How to resume playing at correct pos? (maybe just restart sounds)
- What if the user is already playing music on their iThing when they start the app? (AVAudioSession setCategory)
- A lot of this example code is in C. I do know C, but had forgotten how long-winded it can get. Spending a long time staring at code pieces and realizing that oh, this snippet of several lines just gets one value from some structure. Compared to Python there are no exceptions, have to deal with handling memory, numbers can overflow.

Back in the day I did manage to play sounds in DOS by loading sound files myself and streaming them to my SoundBlaster over DMA, so I should be able to handle this. Just gotten a bit comfy with modern conveniences and suddenly being thrown back into the jungle.

Asking the HiveMind for advice

Saturday, November 27, 2010

Your Japanese Name for iOS, part 4

Today I probably won't have much time to work on this, but let's see if I can suitable fail / success / complete sounds on iStockPhoto.

...

Finding sounds is a lot of work!

Character drawn correctly -sound


As background, one of the "koto loop" melodies from iStockPhoto. Update: this one

Maybe this one mixed in after all the characters have been drawn correctly and the final result is displayed in gold.

But what about failure sound? Or "finger touched down" sound. Actually what I'd really want for that is for wind chimes to be played while the finger is progressing on the character. But when the finger is lifted up, the sound shouldn't abruptly stop. Instead it should fade out, maybe even echo a bit. This seems to call for some sound library. What was that famous one? Oh yeah, fmod. They were porting like crazy, let's see if they have an iOS version... Seems they do. But it's $500 per product, out of my budget. I'd rather use a few days to make a simple mixer, I think there was some source code in some Apple example. Yes.

Whoa, feel a bit overwhelmed. Let's see what I really want to do here.

Channel 1: Looping soundtrack, always full volume.
Channel 2: Wind chimes, starts full, doesn't loop, fades out at any point.
Channel 3: Buddha bell / gong / wrong. Never overlap, full volume, no loop.

If I had the API of my dreams, what would it look like? First it would start like
SoundSystem *sounds = [SoundSystem soundSystemWithLoop:@"koto.mp3"]; // start with koto ambience on channel 0
[sounds play:@"chimes.mp3" channel:1 looping:YES volume:0.0];

Then when the user puts their finger down, I'd like to
[sounds fadeTo:1.0 channel:1 delay:0.05];

And when they release their finger
[sounds fadeTo:0 channel:1 delay:0.3];

For the other sounds I could
[sounds play:@"buddha_bell.png" channel:2];

Basically just play looping or not, caching known sounds and controlling the volume of each channel.

Friday, November 26, 2010

Your Japanese Name for iOS, part 3

Goal for today will be to:
- Initialize offscreen buffer (CGBitmapContextCreate?)
- Draw to offscreen buffer with some kind of brush
- Flip offscreen buffer so that it's visible for debugging purposes

I've seen a few examples of CGBitmapContextCreate, but my biggest question right now is how to know what kind of buffer to create. Depending on the device the resolution differs.

...

Managed to get something on the screen. Got the default context for the view with UIGraphicsGetCurrentContext and drew some stuff. Was surprised that every time all the previous contents disappeared. So actually this default context isn't a bitmap at all?

Trying to make an offscreen buffer. self.frame.size seems to give same values both on old iPhone and iPhone 4, so it would seem to be the size of the display in points, not in pixels. Yes, it seems you can't depend on these values, other people on the internets are having problems with app not working as expected on retina display when doing this. So should take the scaling value into account I suppose.

I see some example code calling CGBitmapContextCreate with NULL as first argument. The first arg is supposed to be the data used for the bitmap context. Seems like a big no-no to have it be NULL. Or maybe it's a magic arg that causes the function to allocate its own space somehow?

"In iOS 4.0 and later, and Mac OS X v10.6 and later, you can pass NULL if you want Quartz to allocate memory for the bitmap. This frees you from managing your own memory, which reduces memory leak issues."

...

[UIScreen mainScreen].scale is 2 on retina display, 1 on older iPhone. So it seems the width of the offscreen buffer should be [UIScreen mainScreen].scale*self.frame.size.width pixels and similarly for height. Seems that many code snippets floating around on the net are missing this detail and then wonder why their bitmaps look pixelated.

...

- (CGSize)offscreenBufferSizeInPixels {
float scale = [UIScreen mainScreen].scale;
CGSize sizeInPoints = self.frame.size;
CGSize sizeInPixels = CGSizeMake(sizeInPoints.width * scale, sizeInPoints.height * scale);
return sizeInPixels;
}

- (CGContextRef)createOffscreenContext {
CGSize size = [self offscreenBufferSizeInPixels];
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef context = CGBitmapContextCreate(NULL, size.width, size.height, 8, size.width*4, colorSpace, kCGImageAlphaPremultipliedLast);
CGColorSpaceRelease(colorSpace);

// "Because you use a lower-left origin when drawing into a bitmap or PDF context, you must
// compensate for that coordinate system when rendering the resulting content into a view."
CGContextTranslateCTM(context, 0, size.height);
CGContextScaleCTM(context, 1.0, -1.0);
return context;
}

...

Now that I have a presumably empty offscreen context, how do I blit it to screen?

Answer:

CGImageRef offscreenContextAsImage = CGBitmapContextCreateImage(offscreenContext);
CGSize fsize = [self offscreenBufferSizeInPixels];
CGContextDrawImage(context, CGRectMake(0, 0, fsize.width, fsize.height), offscreenContextAsImage);

Strangely, even though I didn't wrap with UIImage, I had to comment out CGContextTranslateCTM and CGContextScaleCTM to get it to display correctly. Hit a new problem now; if I draw shapes for a while I get a memory warning. Am I reallocating something repeatedly? Let's see if I can use Instruments to see what it is even before I try to guess.

Ran Instruments by selecting Run > Run with Performance Tool > Allocations in Xcode. As I paint more things memory usage very gradually goes up. Starting at under 2MB it gradually goes to nearly 4MB as I draw more shapes, and then the application gets terminated. Tried another tool called "Leaks". It says the leaked object is a CGImage and that the responsible frame is CGTypeCreateInstanceWithAllocator. Hmm...

...

Aha, apparently CGBitmapContextCreateImage can actually allocate memory (or lazily copy-on-write, anyway) and not just get a pointer to existing image data. So I should CGImageRelease(offscreenContextAsImage). Works without leaks after this change, but disappointed with how slow this is. Only getting maybe ~15fps.

...

Mission accomplished. Can draw with a brush now, but it's slower than I hoped.

Thursday, November 25, 2010

Your Japanese Name 2

Instead of just showing the result, maybe challenge user to draw it themselves.



Something like this. Except with less suck. Would it be better to reveal a readymade image as the user draws, or let them draw freeform? Unsure. If readymade, have to do some clipping / masking magic to reveal it in the direction the user is dragging their finger. If freeform, need to do other kind of magic to make it look like calligraphy.

Stuff I need:
- Initialize offscreen buffer (CGBitmapContextCreate?)
- Draw to offscreen buffer with some kind of brush
- Flip offscreen buffer so that it's visible for debugging purposes
- Use said buffer as a mask (could just copy alpha values or use some compositing operation if such exists)
- Every katakana character with pieces separated such that they can be revealed in order
- Looping background music
- Graphics for mascot / teacher character
- Success sound
- Fail sound
- Completion sound
- Design for title screen
- Copy for character dialog
- Graphics for dialog bubble
- Background texture
- Figure out how to play background loop and sound effects simultaneously (3rd party library needed?)
- Post to Facebook feed
- Post as email (might need own server)

Standard stuff like before:
- App store icons (6 different ones)
- 512x512 art for iTunes?
- App store description
- App store screenshots
- Feedback button
- Default.png for app quick launch



Or maybe it should be upright after all? Samuel L. Jackson as the mascot, giving totally wrong advice. Also, could just show text. Who needs a mascot.

Your Japanese Name for iOS, 1

Regardless that it doesn't have great long term potential, I've decided next to make a version of my Facebook app Your Japanese Name for iPhone / iPod Touch. The FB version has over half a million installs, although recently usage has gone to a mere 1600 monthly users. This was because I was unsuccessful at quickly converting it from a profile-based app to a feed-based one, although I did eventually do so.

There are already some similar apps in the App Store, but I believe I can get some installs if I can leverage the FB userbase. If I still have the list of user IDs stored somewhere, I should be able to inform users of the iOS version through a notification and get some installs that way. Since the App Store likely shows more popular apps first, it should push my version to the top, where it would then remain as it would enjoy extra installs from being the first listed app.

If this takes a week to make and starts doing $1 / day in profit, I wouldn't think it was a waste of time. Looking at this list of iphone app sales it seems possible.

Wednesday, November 24, 2010

What to make next

Now that I have some idea how much effort it is to make something, I've begun to think about what I really want to do next for iOS. I haven't really decided yet, but I've realized I do have some constraints limiting my search space. First of all, the app can be something that takes years to make, but it has to be possible to release an initial version to get feedback on in 2-3 weeks. I'm not patient enough to quietly work on something for a long time with no outside input. Once I get some, it becomes much easier to continue. An episodic game for example would suit my work habits well.

Secondly, it has to have the potential to make some money. I need to eat. It's difficult to code while dead (believe me I've tried). For this reason I've considered making some sort of utility app that could be expensive enough to even be marketed online, but haven't really come up with any ideas. I just don't know any industries / topics well enough. What do I know? I know something about Japanese and programming, but that's about it. Doesn't make me at all unique as a developer. I don't feel there are any tasks in my real life that I would need an app for. There's already plenty of Japanese study apps. I could port "Your Japanese Name" to the iOS though since it wouldn't be that long of a project and I would have an existing userbase on Facebook to advertise to and even some assets for the port.

Third, while for a short period I can work on a subject that doesn't interest me all that much (like the Acey Deucey card game in my previous test), for a project that might extend to years I should pick something that I would enjoy working on. So topics that interest me? Well, I really like the survival genre. Robinson Crusoe, Cast Away, サバイバル, Alive, Lost in Blue etc. I really enjoyed all of them. Another genre I like are business simulations like Sid Meier's Railroads!, Aerobiz Supersonic, Lemon Tycoon, ゲーム発展国. Also life simulations like Jones on the Fast Lane and The Sims (although there was too much menial detail in The Sims) appealed to me. I like to imagine what the far future would be like, so scifi and space themes are good too.



For sound I like soundscapes (sea waves, thunderstorm, busy city etc.), not music. However memorable title music is always good. Chiptunes are great. Ambient style slow paced music is acceptable though, if there has to be some. With graphics I like anime cel art style clean outlines with solid fills or 8bit graphics. Point of view can be from above, bird's eye, even isometric or platformer style, anything goes. Luckily it seems the masses agree with my retro taste, most people don't seem to prefer hyper realism. I think game art should communicate an idea simply and not try to render it in full detail.

How to combine enough of my interests to make sure that if I find myself working on a project still 10 years from now, it would be something I like? Survival + business sim + oldskool. This really sounds like Lost in Blue. So is the answer just to make a Lost in Blue -type game? Survival business sim sounds almost like a contradiction, but I think Lost in Blue does have that. As you proceed you get better tools and with these you get even more resources to play with, that's the core appeal of a business sim.

If I add +Japan and +scifi to include those interest too,.. A guy stuck on a Japanese spaceship with all of the crew dead, left to gather oxygen, food (frozen free-floating sushi?) and such supplies to survive. Wow, the directions this could take are pretty vast. Makes me want to play this. Trying to plan out a game before I've realized it's really really really hard to come up with game designs. So it should be something extremely simple or it will be impossible to pull off before getting more experience with making games.

"A design written on paper and a design in your head is always a fluffy success story. A design created in code (or a paper prototype) is a working machine that must function according the unyielding rules of player psychology. The first is fantasy."

Oh yeah, I like cats too. Cat in space? Jonesy!

Update: Exploring a space ship with the crew dead is extremely cliche. Also, this hardly even qualifies as any sort of "idea", as it's just some vague description of a storyline and doesn't really say anything about the gameplay.

Friday, November 19, 2010

Acey Deucey part 16

Took about 3 hours to get all the certificate stuff to a passable state. I didn't quite understand what I was doing, but hopefully the zip file is now acceptably signed. If I understood correctly, I needed some kind of different certificate for releasing the app than I did for testing it.



Acey Deucey part 15


In-Between is an easy-to-learn single player betting card game. Three cards
are dealt, one of them face down. After the betting amount is decided
the hidden card is revealed. The pot doubles if the value of the hidden
card falls in between or is equal to the two other cards. Otherwise the
pot is lost. Historically this type of card game has also been known as
"Acey Deucey" or "Sheets".

KEY FEATURES
* Use this game to improve your ability to judge probabilities.

* Great as a first introduction to card games. Card suits do not matter
in this game, so it is enough to be familiar with the different card ranks
Ace, number cards, Jack, Queen and King.

* Unlike many card games, here the odds are in your favor. Once you learn
how to play there is no limit how high you can reach.

The following is not recommended for use in this field: pot. Your app may be rejected if you use this term.

Heh.

Acey Deucey part 14

iOS required icons:

29x29 Icon-Small.png
50x50 Icon-Small-50.png
57x57 Icon.png
58x58 Icon-Small@2x.png
72x72 Icon-72.png
114x114 Icon@2x.png

We've come pretty far considering the whole screen size of the popular Nokia 3310 from ten years ago was just 84 x 48 pixels.

Spent whole morning trying to get UISlider to work. Turns out you can't just set slider maximumValue and value to your desired amounts, because setting maximumValue won't work if current value is higher than it. This was causing the setting code to fail depending on game situation. Safe thing is to first set value to 0, then set maximumValue and then the value.

Thursday, November 18, 2010

Acey Deucey part 13

Instead of buying a sound of audience going "awwww" (when lost game) from istockphoto, I thought I'd record one myself.. surprisingly difficult to say a disappointed "aww" without sounding sarcastic. Spent hours trying to find suitable sounds. Time to give up and make the game a bit more silent than I intended. Better to have silence than an unsuitable sound.

Can't quite figure out how to save the app state when it goes into the background, so skipping that for now too.

TODO:
- UISlider should update properly and have a reasonable default.
- Touching "send feedback" in rules screen should actually do something.
- App store icon, description, screenshots etc.



Update: Are you kidding me? I need to create six different sizes of icons?

Tuesday, November 16, 2010

Acey Deucey part 12

Basic game works well enough now to be played.



TODO:
- Broke retina display support. Need to tweak card PNG to make it work again.
- Screen for going broke.
- Win / lose sound (maybe "awww" and applause). "Cards being dealt" sound. Possibly "cards going away", "ran out of money" sounds.
- App store icon, description, screenshots etc.
- Have to keep track of the "deck" at least so far as not to deal two identical cards.
- Default.png for quick launch.
- Support recovering app state if user gets a call / exits and returns.
- Rules screen.

Noticed that at some point I went from Ace representing 14 to it meaning 1. Also changed my mind in that equality is now considered winning.

Acey Deucey part 11

This is how the main screen will now look. Must stop tweaking it finally.



Got reply from Apple. Apparently I got my bank details all wrong. They even sent me a screenshot of what I'm supposed to input in that screen. Awesome. I've now used 10 days on this app. Pretty good progress. Not amazing progress, but I'm glad I haven't encountered any showstopper bugs either. Starting to feel a bit exhausted, feeling some reluctance to put any cool transitions between game states.

Lose screen:



A bit lame IMO.

Monday, November 15, 2010

Acey Deucey part 10

Experimented a bit with font shadows, set background for the controls. Slider works.



Top part of the app is begging for a dark bar to be put there. Maybe show balance and feedback link there?

Acey Deucey part 9

The cards now appear with a nice slide, slowing down seemingly because of friction. Did it "the right way", using CAKeyframeAnimation and a curve for the card movement. Also got a "flip" sound working. Now with the sound and 3D flipping animation it feels very satisfying to flip a card. This is starting to feel like a real app now.



TODO:
- Figure out how to get updates from UISlider so that bet can be chosen.
- Broke retina display support. Need to tweak card PNG to make it work again.
- Game logic itself. Is A < B < C is the winning situation, or would A <= B <= C be acceptable (better odds for player).
- Screens for win, lose, going broke.
- Win / lose sound (maybe "awww" and applause). "Cards being dealt" sound. Possibly "cards going away", "ran out of money" sounds.
- App store icon, description, screenshots etc.
- Maybe space below controls should be wood / something else, not green tabletop.

Update: I knew it was possible to condense the explanation even more: "Value in between wins"

Sunday, November 14, 2010

Acey Deucey part 8

Started doing "paperwork" so that it would be ready so I can submit the app when it's finished. Learned I need to use "iTunes Connect" to upload the app. Went to site, contracts and payment info was there too. Tried to enter my bank info, wasn't in the list of banks. Used their contact form to ask it to be set. Wondering if I'll get a reply.

Next: Need to learn how to do transitions / animations on iOS so I can slide the cards in. I want to do it the "right way" instead of updating location of the cards directly.

Update: Learned the "right way" is to use layer animations. Each iOS UIView is "layer-backed". Layers can be manipulated to conveniently create cool effects. They're sort of like frame buffers on which the views are rendered to and these layers can also be moved around, opacity changed etc. Had to add quartz framework to the project to use them.

Saturday, November 13, 2010

Acey Deucey part 7

Great progress. Made a card class, can use poker-style abbreviations to make a card. This creates a 9 of diamonds and shows it on the screen:

card = [[UIPlayingCard alloc] initWithString:@"9d"];
[self.view addSubview:card];
[card release];



Also got a 3d animation of the card flipping working, and made it super convenient to call too:

[card turn];

Would it be possible to explain how to play the game to the user in one line of text? "You win if the hidden rank is in between" doesn't make me quite satisfied yet.

Showing how many chips the player has left in lower left also hurts my eyes. It naturally wants to go to the upper left, where since dawn of time player scores have been shown, but I'd somehow want to dedicate the upper area to showing only the table.

Idea: Could get rid of all the controls by representing the balance and bet as stacks of chips that can be dragged around. The hidden card could be turned by touching it. But this was supposed to be a minimum viable app and that seems to go beyond it. Maybe if for whatever reason this app sells a bit (which I know it won't because this isn't a card game anyone actually plays), I can go back and update it to version two where it uses chips.

Thursday, November 11, 2010

Acey Deucey part 6

Suddenly feel very noobish. Have no idea how things relate to each other, how to get debugger to show me something, how to maintain memory, what magic is behind NIB files etc. Just flailing for something to grab onto. So it was like a triumph to get anything to show that I created from code.

My first few lines of code that actually created something. This loads cards.png and shows it on the screen. Might leak memory, not entirely sure (Update: yes, it leaked because addSubView incremented retain count).

UIImage *img = [UIImage imageNamed:@"cards.png"]; // who should release this?
self.sub = [[UIImageView alloc] initWithImage:img];
[sub release]; // to get retain count to 1
[self.view addSubview:sub];


Output:

Wednesday, November 10, 2010

Acey Deucey part 5



Mockup of main game screen. I don't actually have code for displaying the cards yet. Somehow I need to split my image into several smaller ones to have an UIImage for each. The big image will be 2MB in memory. An older iPod touch has 128MB of RAM so doesn't seem like an issue. Documentation did warn about having visible images larger than 1024 x 1024 (OpenGL thing I guess), which my image is. But I'm not attempting to display it all at once.

Tuesday, November 09, 2010

Acey Deucey part 4

More needed stuff:
- Have to keep track of the "deck" at least so far as not to deal two identical cards. For now I'll be content just checking when dealing that the card isn't on the table yet.
- Icon for the app. I'm guessing the icon, name and description of the app are about as important as the app itself.
- "Kaching" sound when winning the bet (if more than $0).

Today I hope to learn how to move UIImageViews around from code. So far haven't figured out the IB connection problem.

Question: I created a property and an IBOutlet for it in FirstViewController, why doesn't it appear in IB?
Answer: In FirstView.xib had to change "File's Owner" "Class Identity" into FirstViewController

Acey Deucey part 3

tab bar icons

retina display tab bar icons

Realized I needed them in two different resolutions, one for retina display and one for normal. It wasn't as simple as just resizing it, since at these small resolutions resizing turns things into mush. Had to redraw. Spent about 1.5 hours on making the icons, getting the icons to the tab bar and getting it to recognize the 2x icons too. Didn't realize had to drag the files to xcode it didn't just find the @2x files on disk.

Imagined in what kind of situation an iPhone user would play a card game. Probably on the bus, back seat of a car etc. when killing time. That means background ambience might be a bad idea, there might be other people around. Instead a simple card flip sound will do. Listened to a bunch of different samples and found a suitable one on istockphoto. Now need to cut the wanted sound out somehow.

So a new thing to figure out:
- How to play a sound (not mixed)

Monday, November 08, 2010

Acey Deucey part 2

Just a progress report. Did mockups of screens on a whiteboard, then started moving them to IB. Instead of just downloading some casino table background from iStockphoto, spent an hour making it from scratch in Gimp. Found an example from somewhere on how to flip a view with that cool 3D effect (UIView setAnimationTransition). Spent more time than I wanted in trying to support retina display (the higher res new iPhone). Decided not to make a reusable playing card class, instead I'll just deal with UIImageView objects directly. Had funny moment where I realized there are playing card values between 1-14, but only 13 different cards in each suit. How is that possible? Ace is 1 and 14. Of course.



Stuff I feel unsure about
- How to structure the whole program, where should the game itself be? Maybe look at examples for inspiration.
- UIImageViews provide some way to offset the image, right? Right? So I can just have one huge image that has all the cards. (edit: UIImageView seemed to have no such property. Yikes, UIImage docs say to avoid images larger than 1024x1024 and mine is currently bigger.)
- How do I change the tab bar texts for tabs?

Stuff I realized I need:
- Default.png for quick launch.
- May need icons for tab bar tabs.
- One image for front of card and one of back to animate transition between them. So need to move them together too.
- Maybe there should be a white outline in where the cards are supposed to go, just like on a real casino table.

Weird aspirations:
- It would be cool if there was a background casino atmosphere sound, kind of like the background theme in "shufflepuck cafe".
- It would be awesome if the background "audience" made some amusing comments about the situation in the game. Like if you bet a lot when the odds are really bad someone would whisper "I can't believe he didn't fold!". Or if you reach some high dollar amount you could get flirted on. But all of this kind of subtle.
- It would be good if the cards casted a shadow (and of course were a bit higher too) while they are being dealt.

Saturday, November 06, 2010

Acey Deucey

Decided to make a card game from an old Atari BASIC games book. It's called "Acey Deucey" (not to the backgammon-like game), "In-Between" or "Sheets". There are many variations to the rules, but I'll go with exactly the simple rules as in that BASIC program. You are initially dealt two cards, then you bet and after that one more card is dealt to you. You will win the amount you bet if the value of the third card is between the two cards that were dealt to you and lose if it wasn't.

To make things simpler, Ace always means 14. "In between" means strictly in-between, not equal. Stuff that's on my mind now about this:

- Where to get the card faces. I think there was some free set. Ah here it is. If I understand correctly, it is free even for commercial use (I might want to try AdMob just for fun).
- Card animation should be slide in + flip. Flipping should be that "pseudo 3d" flipping if possible (compress horizontally), but how to do it? At least two options, UIViewAnimationTransitionFlipFromRight (or something similar) to switch between views, or use OpenGL (Mixing UIKit with OpenGL)

Friday, November 05, 2010

iPhone dev 21

Got the flashlight app running on my iPod. Now how do I submit it to the app store?

"If your app doesn't do something useful or provide some form of lasting entertainment, it may not be accepted."

Oh.

"If your App looks like it was cobbled together in a few days, or you're trying to get your first practice App into the store to impress your friends, please brace yourself for rejection. We have lots of serious developers who don't want their quality Apps to be surrounded by amateur hour."

Blush.

iPhone dev - provisioning profile

Doing all of the certification magic again. Last time I did it I didn't really leave myself any helpful notes, but this page was really helpful about it. Biggest gotcha was that the dev portal "Provisioning Assistant" doesn't work on Chrome. It seems like it does, but just fails at creating the provisioning profile.

And what is a "provisioning profile"? From Apple dev portal: "A Provisioning Profile is a collection of your App ID, Apple device UDID, and iOS Development Certificate that allows you to install your application on your device."

Flashlight app works

You turn on the app. Screen goes white. That's it. Now, how do I get this into the store?

iPhone dev continued after 2 year hiatus

Exactly two years ago I got an iPhone and a mac to develop apps with. I was making good progress on an iPhone game, but then I accidentally scratched the surface of the phone with a key in my pocket, and it stopped working. Somehow I lost motivation to develop for it after that, even though I did get a new iPhone some time later. Now I want to give it a try again. I want to get the easiest possible minimal app into the app store, just to lift my spirits. I want to browse the store and look at it while thinking "I made that (crappy app)". With "minimal" I mean really minimal, it has to be the simplest thing that could possibly pass the review process, so that means a flashlight app.

I want the app to display a white screen when turned on. That's it. It won't even have a way to turn the light off, because that would be more than is strictly necessary. I'm not sure if I'll be required to put some kind of credits or explanation with the app, or will just a white screen suffice. At least I'll need an icon. Or could that be just a white rectangle? For name I could go with something like "Quick Flashlight". In the explanation I should say that it really doesn't do anything at all except make the screen all white.

Tuesday, December 15, 2009

Discovered it is possible to travel to Antarctica and North Korea. You can also get Master's Degree in Greenland (150 students).

Saturday, December 12, 2009

Beefed up my backups after hearing the horror story of how Coding Horror lost their data.

Wednesday, December 09, 2009

Ahh, my first solid state disk. Not the leet Intel one, but a cheapo one about half the performance off ebay. Still, even half the performance of Intel's SSD beats any traditional drive. So wonderful to get rid of all those periods when the computer is doing nothing except just crunching loudly.

Tuesday, December 08, 2009

Been thinking how to use the community of Coolest Friends to start something else. I was thinking of a video dare site, where you get points for shooting vids where you do certain tasks. For example one dare could be "stand on one foot for a minute" and if you post a video where you do so, you would get some amount of points. Of course there would be a visible leader board, and you get more points the more difficult a task is, possibly determined by how many people did it.

But I feel a bit exhausted. After doing some "small" projects like this, I realize they always balloon from the "I bet I can do it in a week" to "3 months passed and I'm STILL doing this?".

Sunday, December 06, 2009

Traffic to Coolest Friends doubled. I have no idea why. It seems to come uniformly from profiles and homes. I noticed a slight dip before. Maybe it was somehow down and now all those people who couldn't visit, are coming back in order to get their daily increasing bonus? I have no idea. I really need to get into making updates to this app, but keep putting it off. For the moment, thank you whatever random effect for doubling my visits.

Finnish independence day. Celebrated the eve by being bored and then sleeping early to fight the boredom.

Quiz app seems dead. 133 visits yesterday, compared to 600 on the first day. If I don't do something to make it work soon, there won't be anyone around to spread it.

So which of these important tasks am I doing? Neither, instead I am trying to get particle-based water to work with HTML canvas tag.

Friday, December 04, 2009

Upgraded Mac Mini RAM to max 3GB using a cheese slicer to pry open the cover. Learned a trick to do modular arithmetic faster. What is 25 in mod 7? Find x such that 25-x is a multiple of 7. X is 4, so 25 is congruent to 4 mod 7. Now for positive values you could just do without that, but it gets useful with negative ones. What is -25 mod 7? Find x such that -25-x is multiple of 7. Closest multiple is -28, so x = 3. -25 is congruent to 3 mod 7. Helps with exercises about computing inverses of matrices in Z7.

Thursday, December 03, 2009

Winter came. Strangely on time for December to look so christmasy. Unity engine seems fun to play with, reminds me of good old Amos 3D days. Maybe I could make some Assembly gamedev entry with this. Coding should be fun. Modding with source engine isn't much fun, because you have to wait minutes to see your changes take effect. With Unity things change realtime as you change code.

Tuesday, December 01, 2009

Went to uni library and had a nice study session without distractions (aka internets). It's amazing what you can accomplish when Reddit isn't around. Seeing others immersed in their study is also somehow infectious. I think I'll try it again tomorrow.

Sunday, November 29, 2009

Change may have increased the likelihood that a user completes a quiz. Difficult to say yet as the "improvement" is still within just random daily fluctuation.

Had a private burst of anger at my math teacher. I failed his course and would like to blame that on his teaching style totally lacking any passion. I've tried to avoid attending the class, every time I leave being less motivated by the subject than when I came in. It's just a basic linear algebra course, which is very very useful and could be presented in an interesting way, but it feels more like attending a funeral. So I stayed at home and tried to study the things as a list of contents got updated to his homepage. But then in the exam (which he had scribbled by hand and xeroxed barely legibly) there was a question which wasn't mentioned on that list, and I failed just barely.

I had studied for that class every day for about two months, but not exactly the things that were in the exam. I got upset enough that I dropped studying math at all for over a month, but now I'm getting my self esteem back just enough to try and continue.

Saturday, November 28, 2009

Released update to Mixi quiz app. If it will only improve goal completion by a few percent, that might be enough to turn it from decline to growth. Natural Selection is the most brilliant PC game ever created.

Friday, November 27, 2009

Productive day.

Managed to remove the most failure prone iframe, things are much speedier now too. The app works on three social networks, Mixi, MySpace and Facebook. Most users are on Mixi and I think I will drop the other versions if they start to feel like work to maintain. Did some successful soldering on an electronics kit. Dubai causing stock markets to fall.

Iframes all the way down

In an unproductive slump, to break out of it decided to rewrite parts of the failing quiz app for Mixi. Was a mistake to use iframes so much, sometimes some people are seeing nothing when I try to show an iframe. The app itself is already an iframe, so that's an iframe in an iframe. At one point to show an image upload widget, I have an iframe in an iframe in an iframe.

Thursday, November 26, 2009

Today's lack of productivity brought to you by Adobe Flash CS4 and Sampo Bank

Spent much of today staring at the beach ball of doom (a spinning cursor you see on a Mac when things are über slow), Adobe Flash CS4 editing interface is reaaally slow. I am trying to learn how to export isometric graphics from Blender for use in a Flash-based game. I have source files that I am editing in a separate editor, because I can often type faster than CS4 can read my typing, and it will sometimes do nothing for what feels like forever. Not productive.

Computer is Mac Mini, 1.84GHz Core 2 Duo 1GB. Decided to upgrade RAM to max 3GB and switch to a solid state drive. Upon attempting to pay for said drive, web bank wouldn't work. Stalled at "Starting Java..." with a (lack of) progress indicator not quite unlike the beach ball of doom. HD on another computer apparently has bad sectors, so switching that to an SSD as well. Tried to relax from all of this by doing some soldering on an electronics kit, but discovered soldering iron wall plug doesn't fit (ungrounded vs. grounded socket).

Wednesday, November 25, 2009

Boston

Went to Boston to attend Global Entrepreneurship Week, made new friends. Mike and Val are a fun couple, they are both into demoscene. Showed us around MIT. Saw wonderful little machines (by artist Arthur Ganson) with no other purpose than to look interesting. Favorite one was called "solitude", where a machine with gears made of thin wire existed only to move a miniature man's head left and right.

Tuesday, October 06, 2009

How to validate a Mixi.jp signed OpenSocial request on App Engine

I know nothing about security, but had to validate a signed request and this experimentally seems to work.

Get the certificate from here:
http://developer.mixi.co.jp/appli/pc/lets_enjoy_making_mixiapp/require_servers

It is a long base64-encoded string that starts with -----BEGIN CERTIFICATE-----. Copy and paste it to base64 decoder. Store binary file "DecodedBase64.bin".

Run this command. This comes preinstalled on Mac Leopard.

openssl x509 -in DecodedBase64.bin -inform DER -noout -text

Copy and paste everything the hex values "Modulus (1024 bit):" to a text editor. Replace ":" and " " with "". Add \ to the end of each line. Now with this, you can use the instructions here to continue (the code after "which has been parsed, converted to hex value" on that page). Remember to put 0x in the beginning.

Friday, March 27, 2009

Using Google Spreadsheets with iGoogle to create a shareable dashboard for your startup



Google Analytics is excellent for tracking visits and can even be used for more advanced things like tracking conversions and events, but what if you want to track application-specific metrics which don't happen in a user's browser? For instance our Twitter meme aggregation site gets tweets using the Twitter API and stores them in our database, and the amount of tweets is something that I am interested in keeping an eye on. Here's what our dashboard looks like, and in this post I'll show you how you can effortlessly create your own.



Not only do the charts look pretty neat, but you can drag and drop them to rearrange them on the screen and even drag around inside each time series graph to see different spans of time. So where are these graphs coming from? A cronjob executes a simple Python script every quarter hour. The script queries our system for the load average, asks MySQL for the number of tweets and other data I want to chart. Each piece of data gets inserted into a separate Google Spreadsheet using the Google Spreadsheets API.

I can visit each of these spreadsheets and create charting gadgets (insert > gadget). Here I only used the time series gadget, which is like the one used on Google Finance, so you can easily zoom in to different periods of time and mouse over to see the absolute values. Clicking on the upper right corner of a gadget you'll find the option "add gadget to iGoogle". After you have added a few gadgets to your iGoogle, it may make sense to combine them into an iGoogle tab. Then on a tab's menu you'll find an option to "share this tab", and now any member of your team can view the data.

That's a summary of how this is done, but for the sake of completeness I will now mention some problems I encountered and share some code snippets so you won't necessarily have to go digging through the API.

First of all, one perhaps strange decision I made was to use a separate spreadsheet for each thing I track. One reason is that different data might be polled at different intervals, so the data is easier to handle this way as there won't be any blank fields for missing data. The more real reason however is a caveat I found, which is that each spreadsheet can contain no more than 200000 cells. There are around 35000 quarter hours in a year, so holding all data in the same spreadsheet would hit the limit in just a few months. I might also mention that I don't yet know how to get a charting gadget to automatically extend to cover all rows as the spreadsheet grows. If you know how to do that, please let me know and I'll be sure to mention the solution here.

Now some snippets. These use the Python library gdata-1.3.0. Logging in to Google Spreadsheets:


gd_client = gdata.spreadsheet.service.SpreadsheetsService()
gd_client.email = 'YOUR GOOGLE ACCOUNT EMAIL'
gd_client.password = 'YOUR GOOGLE ACCOUNT PASSWORD'
gd_client.source = 'exampleCo-exampleApp-1'
gd_client.ProgrammaticLogin()


Below is the snippet for inserting one row to a certain spreadsheet. Each spreadsheet can consist of several worksheets. Not sure if it's always true, but experimentally I found that the first sheet seems to be called 'od6'. The spreadsheet_id you can find by creating a spreadsheet, then looking at your address bar and copy the base64 looking string in the "key" GET argument. The value here is any piece of data that you want to track, for example the number for your current load average.


def newValue(spreadsheet_id, value):
worksheet_id = 'od6'
dict = {'datetime':time.strftime("%m/%d/%Y %H:%M:%S"), 'value':value}
gd_client.InsertRow(dict, spreadsheet_id, worksheet_id)


Finally here is my complete list of things I import in the beginning of my script. It contains many unnecessary includes for these particular snippets, but I thought it might still prove helpful if you are trying to get the code to work.


try:
from xml.etree import ElementTree
except ImportError:
from elementtree import ElementTree
import gdata.spreadsheet.service
import gdata.service
import atom.service
import gdata.spreadsheet
import atom
import getpass
import string
import time
import urllib
import os
import re


Thanks for reading and please comment on Hacker News (preferred) or here in the comments. I'm interested in becoming a better blogger too, so any suggestions on improving my writing would be appreciated as well.

Monday, December 29, 2008

iPhone dev 20

Found one piece of the puzzle. To add views so that they are visible, the window has a method called "addSubview", seems to be similar to addChild in ActionScript. A default windowed iPhone project already has a "window" attribute in the delegate class. applicationDidFinishLaunching also contains a reference to the XIB file. A view controller has an initWithNibName method that takes the name of a XIB file.

Found an answer to the source code generation question too:

It doesn’t generate source code, instead it allows you to manipulate objects directly and then save those objects in an archive called a nib file. At runtime, when a nib file is loaded the objects are unarchived and restored to the state they were in when you saved the file

iPhone dev 19

So this is how the code knows about objects from Interface Builder. The code has a class called (something)AppDelegate, which has an applicationDidFinishLaunching method that gets called at start. The *AppDelegate class can have IBOutlets for different things like buttons and window from IB, so that it can reference them.

But still, how do I add a new XIB file containing a different view to the project and reference it from code?

iPhone dev 18

I'm back from the sidetrack, at least for now. Game prototypes and MySpace widgets were taking up my time, and probably a bit later will again, but today I'm figuring out iPhone stuff again.

I really still don't understand the relationship between the Interface Builder and code. If I make a view in Interface Builder and add the XIB file to my project and build the project, did it now create a class definition for it automatically? How can I even find out? I feel frustrated that magical things are happening in the background, code is apparently created that I have no awareness of. But this feeling is familiar, I know it will be replaced by understanding if I just continue on this long enough. Things will click into place, and then it will be a breeze to create things. That'll keep me motivated to continue on.

What I want to accomplish is simple. I want a button in the main screen, that when pressed slides out another view which is also constructed in the Interface Builder. But to do this, somehow I need to reference this other view from code, and I don't know how it appears there. I see at least these options of how this might work:

a) Perhaps if I just add a XIB file to a project, Xcode does something magical behind the scenes that results in a class definition being available to all code, which I then have to instantiate. This seems unlikely somehow.

b) Perhaps adding a XIB file to a project causes objects defined in the file to be instantiated. This seems likely, I remember reading that XIB files are kind of frozen object relationships. But when they are thawed, where are they?

c) Adding a XIB file to a project is not enough by itself, but you need to create your own proxy classes in Xcode to be able to reference them. But this wouldn't solve the issue previously mentioned. Even if I know the class names, I still need to reference the thawed objects.

Gimme the thawed objects!

Sunday, December 14, 2008

YouTube is easy?

I read a lot of blogs where developers voice their opinions on how to do successful things. Often YouTube is raised as an example of a service that was easy to implement, but filled a real need in a user-friendly way (unlike Google Video) and so became popular. I agree with everything except the "easy" part. If I think about web services, YouTube really doesn't seem comparatively on the easy side.

YouTube seems like a total nightmare to scale for starters. Their bandwidth usage boggles the mind. YouTube currently uses more bandwidth than the entire Internet did less than eight years ago! They spend an estimated million bucks PER DAY on bandwidth.

So OK, perhaps when they say it was easy to implement, they mean when it started, not the way it is right now. Some blogs like to point out that because they use PHP and MySQL, this makes it easy to implement. Granted, the site UI part itself doesn't seem to be especially difficult. But is that really the meaty part of YouTube? Personally I think transcoding is the essential and also the difficult part. Perhaps they use something like FFMPEG to do that, making it easier than I imagine, but they really had to overcome some kind of a mental hurdle to realize that this uploading thing could ever work well enough.

Also from a legal standpoint it does not seem easy. YouTube seems like it might have been much easier to start from China or somewhere with less strict copyright laws. Being a company in the US, I wonder how they got any sleep at night with lawsuits and cease and desists flying at them left and right.

And now they have yet another tiny little detail: how to even make any money from all this. The founders Chad Hurley and Steve Chen of course don't really have to worry too much about this any longer, but I'm thinking about this from the point of view of the business itself. Assuming they really are spending $1M/day on bandwidth, and believing the compete.com estimate that they have 64M monthly uniques, they would need to extract about 50 cents per user per month just to cover the bandwidth cost.

I don't believe they are doomed. It can likely all be made to work, maybe that $1M/day bandwidth will cost a small fraction of that after 10 years. Maybe there is some magical d'uh-obvious moneymaking scheme they will come up with. What I just mean is that none of this makes me feel like YouTube should be the first company people pick as an example of something "easy" to do.

Friday, December 12, 2008

Here's how to monetize Twitter

Add a gifting feature called "bribes", similar to the gifts you can send on Facebook, except they are gifts that all of your followers will get. They are collectible items totally controlled by Twitter, and cost real money to buy. You would buy these items to reward your followers and to encourage more people to follow you.

Wednesday, November 26, 2008

Never let a Finnish man drink too much

A drunken 38 year old man caused extensive damages and kept the police occupied, going on a mad nightly rampage. All of this happened in the span of a few hours.

To start the night, he stole a woman's wallet in a bar. After the bar closed, he started walking home, but stopped on the way to kick down a dozen gravestones at the graveyard. After that he broke some windows of nearby houses, and lit a moped on fire. Soon after this he also lit three garbage collection points on fire. One of the fires spread to a van parked next to it.

Next he wandered to a kindergarten and lit on fire a baby carriage left outside. Then he went on to a deaf peoples' home, attempting to conceal his identity by putting a shopping bag on his head. There he beat a night shift worker with a stick, broke windows and equipment, then demanding to get medicine. A female nurse managed to lock herself in a room and alert the police by phone. However an ambulance arrived before the police did, which the man then stole and drove around the town for half an hour, before smashing the windows and abandoning it. After this he called a taxi and went home to sleep.

The police already had an idea who the culprit might be, so they catched him from his home after he had already fallen asleep. He was interrogated and blames alcohol for his behavior.

( this was a translation of a 1994 news clipping from Finland )

Tuesday, November 25, 2008

Protostorming again: Build a School

In this MySpace game you maintain your own school. You and your friends take the roles of teachers, competing against other schools for the highest GPA. GPA for a school might be calculated as (your study points)/(best player's study points)*5. The teachers collect "study points" for a school by giving the students lectures in a simple quiz minigame (prototype screenshot below).



Reaching certain study point thresholds would cause events to occur, which might lead to positive or negative consequences, or cause the player to receive an item. Players would often receive the same items, and would be then prompted for example "you don't need two blackboards! how about giving this to a friend?". This would be the second viral channel after teacher recruiting.

Third one could be a minigame where you have to gather friends to upgrade a school. At first the school would be just outside on the grass. Secondly it could have walls, and finally a nice floor too. How this upgrading part would work, I'm not sure. Perhaps it could even just be an event when a certain study point limit is reached, although then it wouldn't help the virality (but would still reward players to continue playing). (Lil) Green Patch is basically just about giving items, and has thrived on just that. I tend to think in too complex terms. Maybe minigames aren't even necessary, or might even complicate things too much? Perhaps it suffices to incentivize the players by donating all or part of revenues towards building actual schools in 3rd world countries, which the best players could name.

Friday, November 21, 2008

Seth Godin in my head

Say nothing, but say it big, inspire. No facts, no proof, but it tastes so sweet. Seth Godin saying in my head "be a leader, you must do it, the world needs you!". How can you not smile, even start to believe? Then, a month from now I might not be any different for having listened to his audio book, but for that short while I felt great. Donuts for the mind.

Tuesday, November 18, 2008

Fire game prototype



I can survive 163 seconds, how about you? I learned from making this prototype that having a good difficulty curve is important. In this prototype, the player is entertained for the first 5 seconds, then bored 60 seconds, then perhaps slightly curious for the next 30 seconds and finally faced with an abruptly impossible difficulty level, making the player feel they died due to no fault of their own -> not fun.

Monday, November 17, 2008

Rotoscoping experiment

I did a small experiment to see how difficult it would be to track joints from video material. I was meaning to do this before back in the DOS days after seeing the cool rotoscoping in Another World (Out of this World), but back then it was too difficult to get the video into some form that I could easily read from code.

What I wanted was dancing material with an unchanging background and a static camera. Now there is YouTube so it is really easy to find this. Next I downloaded the FLV movie using a 3rd party tool (there are many). I used "FLV Extract" to get the video stream from the FLV file as an AVI file. Then I used Virtualdub to crop it to a short segment. Converted that segment into a GIF animation with GIF Movie Gear, then finally imported the animation to a Flash timeline.


Next I attempted to track the left wrist of the dancer to see how much work it is. As a first test it took about 5 minutes of concentrated effort to mark 50 frames. Mostly I was so slow because I needed to move forward and create keyframes in the timeline and drag the joint marker with my mouse. I think if I made a small tool that let me just tap on a joint with my drawing pad, I could manage in under 5 seconds per joint per frame.

At least 20 joints would be necessary to make a stick figure dance like the dancer. Three minutes of YouTube video at 12 fps is 2160 frames times 20 joints is 43200 taps times 5 seconds is 60 hours! And of course this data is 2D, so it isn't even clear what could be accomplished with it. One thing did occur to me though -> you could use this as an affordable motion capture solution for games. Suppose you have a front camera and a side camera filming the same footage, so 120 hours of work to track it. Send the task to China, suppose it costs $5/hour -> total $600 for probably all of the motions needed for a small game.

Shipyard

Rough prototype of the day. The graphics are placeholders I found with Google image search. To try this, select a tile from "power", then click on a grid to place some. That's all you can do for now.



I've played many space shooter games, but a thing that bothers me is that the ships never have any kind of internal structure. Your ship tends to be just a scalar value like HP, and when it reaches 0 you die. I want ships to have inner structure. Imagine a space battle. Wouldn't you much prefer to hit your enemy in their warp core to cause a devastating chain reaction that destroys the entire ship?

Saturday, November 15, 2008

Social networks as maps of real connections

When thinking of what kind of apps to make for social networks, thinking about what people do in their everyday life can be a great source of ideas. A big part of social networks is mapping out real connections. The concept of "Social Graph" is so well-known as to become even a bit nauseating to think about one bit more, but there are other connections besides just friendships, not all of which are necessarily mapped out yet. For some, it probably makes no sense to map them.

A person has...
a name (Name Analyzer -- at least I thought about this one!) both official and nicknames (Nickname)
age (Birthday Calendar -- still kicking myself for not thinking about this first)
x,y,z location at each time they existed -> birthplace, countries they visited (Places I've Been), grave
photons disturbed by them (Photos/posting of videos)
likes/dislikes about food, movies, music, smells, colors...
personality (Compare People)
experiences
knowledge (Who Has The Biggest Brain, Scrabble, Geo Challenge)
degrees/certificates
medical conditions, sleep cycle, height, weight, dna (a bit too costly to compare your DNA with friends, but we'll get there ;) )
ownership of physical/virtual items (can own a car, a house, stocks, money, music recordings, WoW gold...)
relationships with humans -- idols, friendships, relatives, enemies, employees/employers
pets
opinions about...
- other people (Hot or Not, Compare People)
- what is wrong and right
- politics
- which gods if any exist
...

"Groups" by Facebook is very much a meta-application in that almost anything can be expressed as a group. It may be that applications that can add value beyond what a membership to a group could offer will be successful. One other app I'm kicking myself for not coming up with is Bumper Sticker, which solves the meta-problem that groups solves, but in a more visual way. If there is any other uninvented angle than Groups and Bumper Sticker to this, it will be huge. Other thing to think about is whether there would be value in aggregating the connections of your friends in some way. For example you have an age, and while that in itself might make a great app (Brain Age), aggregating friends' ages also gives one (Birthday Calendar).

If you can think of any other general sources of ideas, please post some. I'm sure there are still a few d'uh-obvious ideas out there to be discovered!

Tuesday, November 11, 2008

Secant square

Coded something just for fun for a change.



This is a square drawing routine that uses trigonometry instead of the usual way to create a square. The sliders skew the trig equation in different ways.

Harry the load balancer - a true story

Harry works at an ISP called Elisa, in a depressing country near the north pole called "Finland". Imagine yourself as Harry. Surrounded by the cold, dark reality that is Finland, sitting in a noisy computer room, doing possibly the most menial job on the planet. Harry is a load balancer. He gets requests, then just randomly forwards them to one of his clients. Even mail sorters have more fun. "And probably wilder parties too", Harry complained to his friend Tom, also a load balancer. "And probably wilder parties too", Tom said with his identical software. Their shared conclusion was to stop putting up with this situation any longer. But what can you do, how can you protest if you are but a tiny load balancer?

Tom and Harry pondered this in parallel. They could of course call it quits completely, or commit suicide as a Finnish load balancer might do, but Harry had other plans. "Let's have some fun while we're still around", Harry and Tom decided simultaneously. The real nature of Harry's job was to split DHCP requests coming from the 500,000 customers of the ISP. Tom wasn't currently connected. His job was to act as the back-up guy to Harry, in case anything happened to him. Well, now something was about to happen to him. "Wouldn't it be fun to see what happens if I forward all of the traffic to a single client?", Harry thought full of jubilant delight. "Don't do it, man", the DHCP server pleaded, but it was too late. The DHCP server exploded violently, leaving a bloody mess on the server room floor.

Harry should have been more careful with his crime. There was a rat in the room, not the animal kind of rat, but the kind of rat that rats out mischievous load balancers. That rat was a box configured to send an SMS to a human in case anything like this would happen. "Get ready to sing Bicycle Built for Two", the rat said as human steps could be heard walking at a steady pace towards the computer room. The human, let's call him Dave, although that certainly isn't his name, opened the door and entered the computer room. "I'm afraid", Harry whimpered as the human started to unplug his wires. "But, good my brother, do not, as some ungracious pastors do. Show me the steep and thorny way to heaven whilst like a puffed and reckless libertine himself the primrose path of dalliance treads and wrecks not his own.", Harry might have said to Tom at this point if he was into Shakespeare, but instead he said: "brother, your time to serve has come". Harry was unplugged now, with Tom in his place. Dave was satisfied, and decided to walk to the soda machine to get a cola.

What happened while Dave was away should be clear. Tom being identical to Harry in every way, had also decided to be naughty today, so all the load was still being un-balanced to a single agonized DHCP server. However it was getting quite late at this point, so the traffic wasn't that much any longer. So superficially, everything was fine, and Dave could go home to watch the full DVD release of My Little Pony or whatever it is that IT workers do at home. Next morning of course would be a bloodbath.

Based on a true story on the cause of 500,000 Finnish Internet users -- or 10% of the Finnish population -- losing their Internet connections for hours. Original Finnish language news article.

Monday, November 10, 2008

Where to live?

I've been trying to find a place to live where my savings would last for a long time. I found this site: Cheapest Countries in Asia. It says Indonesia is the cheapest. I believe this list, because at least Thailand definitely really is three times cheaper than Japan.

So now I have a list of cheap places. The next piece in this puzzle would be to discover which places have good Internet connectivity. Here are SpeedTest results for Indonesia. That shows some places do have nice speeds, but it says nothing about reliability. Doesn't really matter if it's broadband speed, if it only works every other day.

The search continues.

Friday, November 07, 2008

App got acquired

A small application I made was acquired by a company yesterday. I think the price was fair, this deal is very likely a win-win for both me and the new owner of the app. The price was a multiple lower than what I would have asked just a few months ago. While page impressions have remained stable, CPM -- basically how much money you can get from banner ads -- was much lower.

It may be so that this was not a good deal for me, because if I had kept the app it could have continued to make ad revenue for the rest of my life. It's very difficult to say, but at least I now certainly have enough to live on for a few years. Also maintaining a simple app like that for years would certainly have distracted me, now I have space in my mind to come up with other things. I'm always bursting with ideas, but often too distracted to act on them.

It's good to sometimes know to let go.

Sunday, November 02, 2008

Another World nostalgia gun

Nowadays, I mostly code out of greed. Having some success getting some ad revenue, I try to figure out ways to get moar. However there are some things which I would like to create just for fun. One of them is adding the Another World gun to the game Half-Life 2 Deathmatch. The illustration below of how the gun works is lifted from the author Eric Chahi's page for the Another World game.



Another World (called "Out of this World" in USA) was one of the first, if not the first 2D computer game to use polygonal graphics. It was also remarkable in that the very graphical game was drawn and programmed by the author alone, outside help was only used for the music. It is rare to have both artistic and programming talent in the same person, although that may be somewhat a self-fulfilling prophecy as because of this belief programmers might get a bit discouraged from even trying. Well, in any case the gun works such that pressing quickly fires a thin ray, holding button down for a moment and then depressing creates a shield, and holding for a long time and depressing creates a huge burst which can also destroy shields. Shields can be walked through, but thin rays cannot pass them. This enables you to extend an arm from behind the shield to shoot from safety.



I imagine in 3D this would work very similarly, except of course the shield would be a plane, extending a limited amount. For artwork it could use the shields already in the game, as seen in the picture above. So what's preventing me from adding this? Well, since it's a gun I think it could not be just a server modification, and it seems like overkill to release a client-side mod just to add one gun to it. If I did that, well likely nobody would install it, and nothing is sadder than a nice mod nobody uses. I've seen some great mods that added really nice weaponry like flame throwers, but nobody was playing those mods. Now that leads me to the next suggestion.

Multiplayer deathmatch games like this should have a plug-in system, where servers could push sandboxed client-side code snippets to the players. This would create an incentive for server owners to create new stuff and weapons, since it would attract more players to their servers. It would also be good for the players, because then we'd have all that new stuff. Sort of like Second Life, except with an engine more suitable for combat. The controls and "gameplay" feel in Second Life are horrible, so it certainly doesn't fill this need.

EOF.

Thursday, October 30, 2008

Room-based games

My attention ended up divided after visiting a friend to show the cave flying game. Now because of our brainstorming, I feel more like I should be doing Internet-based games instead. So I've been working on that, luckily I'd been working on that a month ago already for a good while, so I have some infrastructure in place already. I have a general idea and also a server set up to host the lobby, which is a place where you list the existing games to pick one to join to. I have two different games partially working, but on client-side I've only gotten far enough to resolve a domain name, haven't even figured out how to transfer data yet, but how hard can that be?

Yesterday I figured out how the login system should work. After weighing several options it seems that normal login/password will have to do. I cannot tie accounts to a certain iPhone based on device ID alone, because a person might change their device to an iPhone 4G or whatever, or someone else might want to play on the same device. I hate asking people to create accounts, because I hate creating accounts myself, so maybe I will have an option to play as guest. In that case your score won't be saved though, so you'll start from zero again each time.

Of course the best option would be to always start off as a guest, and then only after you've made some progress to have the option to lock that guest account as your own account... hmm...