Latest Nook App - TBS Horoscope

This post is more than 2 years old.

A week or so ago I shared my thoughts on developing for the NookColor. Today I'm happy to say my second Nook app is available on the market. The turn around time for this app was much quicker than before. I had the idea for it last Sunday. By Monday night it was almost done. Tuesday I submitted my metadata and it was approved in a couple hours. I then submitted the application and it was approved by Friday. I checked Friday and it wasn't in the store yet, but as of this morning it's there. I'm pretty sure it was out Saturday as I'm seeing a few sales already.

NOOK App : TBS Horoscope

TBS Horoscope is mainly a joke horoscope generator. Unlike serious horoscope programs (ahem), this one creates horoscopes entirely randomly. Here's the initial screen.

The icons there are scrollable. You can also see the background image I blogged about before. Once you select the sign you get a horoscope:

Yeah - that's crazy - again - unlike real, scientific horoscopes out there. (Ahem again.) One thing that's kind of interesting is the persistence. I generate a random horoscope per sign per day. If you click on Aries twice it will be the same until the next day. Here's the snippet that handles that:

protected function getHoroscope(date:Date):String {
	//A repeat of the above, but in theory, you could run the app for a while
	var today:Date = new Date();
	var dateString:String = (today.month+1) + "/" + + "/" + today.fullYear;

	//See if we have one in the db
	var stmt:SQLStatement = new SQLStatement();
	stmt.sqlConnection = sqlConnection;
	stmt.text = "select horoscope from horoscopes where sign = :sign and date = :datestr";
	stmt.parameters[":sign"] =;
	stmt.parameters[":datestr"] = dateString;
	var res:SQLResult = stmt.getResult();

	if(! {
		var newHoroscope:String = horoscopeGenerator.generateHoroscope();

		var insStmt:SQLStatement = new SQLStatement();
		insStmt.sqlConnection = sqlConnection;
		insStmt.text = "insert into horoscopes(sign,horoscope,date) " + 
		insStmt.parameters[":sign"] =;
		insStmt.parameters[":horoscope"] = newHoroscope;
		insStmt.parameters[":datestr"] = dateString;

		return newHoroscope;
	} else {

I'm using AIR's SQLite support to handle checking for an existing horoscope (I could probably cache that but it executes so fast I don't think it would be worth it) in the database. If it doesn't exist, I generate the random one and store it. In case you're curious, here's the entire ActionScript class for the horoscope generator. It's not terribly intelligent, but was fun as heck to write.

package model {

	public class HoroscopeGenerator {

		private var adjectives:Array = ["forgetful","scary","red","blue","green","yellow","orange","brown","smelly","left handed","right handed","smart","dumb",
									"blue haired","red haired","tall","short","fat","thin","remote","close","skinny","wide","high","low"];
		private var nouns:Array = ["mouse","wig","radio","computer","cat","dog","duck","desk","piece of paper","bird","werewolf","vampire","ghost",
									"dart board","chair","television","egg","table","book","phone","pillow","cactus","rose","hat","airplane"];
		public function HoroscopeGenerator() {

		private function getAdjective():String {
			return adjectives[randRange(0,adjectives.length-1)];

		private function getFinancialString():String {
			var options:Array = [
				"Today is a good day to invest. Stock prices will change. ",
				"Today is a bad day to invest. Stock prices will change. ",
				"Investments are a good idea today. Spend wisely before the " + getAdjective() + " " + getNoun() + " turns your luck! ",
				"Save your pennies! Your " + getNoun() + " is not a safe investment today. ",
				"You can buy a lottery ticket or a " + getNoun() + ". Either is a good investment. "
			return options[randRange(1,options.length-1)];

		private function getNoun():String {
			return nouns[randRange(0,nouns.length-1)];

		private function getRomanticString():String {
			var options:Array = [
				"Follow your heart like you would follow a "+getAdjective() + " " + getNoun() + ". It won't lead you astray. ",
				"Romance is not in your future today. Avoid it like a " + getAdjective() + " " + getNoun() + ". ",
				"Romance is blossoming like a " + getAdjective() + " " + getNoun() + "! ",
				"Avoid romantic engagements today. Wait for a sign - it will resemble a " +getAdjective() + " " + getNoun() + ". ",
				"Love is in the air. Unfortunately not the air you will be breathing. "
			return options[randRange(1,options.length-1)];

		private function getRandomString():String {
			var options:Array = [
				"Today you need to practice your patience. And your piano. ",
				"Meet new people today. Show them your " + getNoun() + ". ",
				"Your spirits are high today - but watch our for a " + getAdjective() + " " + getNoun() + ". ",
				"Your sign is in the third phase today. This is important. ",
				"Your sign is in the second phase today. This is critical. ",
				"Something big is going to happen today. Or tomorrow. ",
				"A " + getAdjective() + " " + getNoun() + " will give you important advice today. ",
				"A " + getAdjective() + " " + getNoun() + " has it out for you today. ",
				"Last Tuesday was a good day. Today - not so much. ",
				"A dark stranger will enter your life. They will have a " + getAdjective() + " " + getNoun() + ". "
			return options[randRange(1,options.length-1)];
		public function generateHoroscope():String {
			var horoscope:String = "";
			horoscope += getRandomString();
			horoscope += getFinancialString();
			horoscope += getRomanticString();
			horoscope += "\n\n";
			horoscope += "Your lucky numbers are " + randRange(1,10) + ", " + randRange(1,10) + ", and " + getNoun() + ".";
			return horoscope;
		private function randRange(minNum:Number, maxNum:Number):Number {
			return (Math.floor(Math.random() * (maxNum - minNum + 1)) + minNum);

So folks - if you have a Nook and 99 cents to spare, check it out. (Direct Link) I'd especially love it if you would rate it up a bit against some anonymous person who gave it one star. It's easily a two star app, right???

Raymond Camden's Picture

About Raymond Camden

Raymond is a senior developer evangelist for Adobe. He focuses on document services, JavaScript, and enterprise cat demos. If you like this article, please consider visiting my Amazon Wishlist or donating via PayPal to show your support. You can even buy me a coffee!

Lafayette, LA

Archived Comments

Comment 1 by Gareth Arch posted on 8/29/2011 at 4:32 AM

Quick question for you about deploying to the Nook. Just went and checked out the developer section and it states that the Nook uses Android 2.2. Just wondering if this means that if I write something using Flex 4.5, that I can just "export release build for Android" and it'll just work or does it have to be HTML or Java?

Comment 2 by Gareth Arch posted on 8/29/2011 at 4:34 AM

Argh! Eejit...Didn't even notice in your screenshots that you're using the AIR runtime to demo :) I guess I *can* write a mobile app in Flex and deploy to the Nook.

Comment 3 by Raymond Camden posted on 8/29/2011 at 5:28 AM

Yep, AIR can now get you on an iPhone, an iPad, a Nook, a Playbook, and all the Android devices in the world.

Comment 4 by Sam Farmer posted on 8/29/2011 at 6:19 PM

What? You mean horoscopes aren't real?