Rhodes – seeding the database

Posted by Jonathan | Posted in rhomobile | Posted on 26-10-2010

0

If you have an app and you need to seed it with data when the app opens, create a model as you normally would -

rhogen model sports id,name,abbreviation,icon

Then place the following code in your application.rb file in the initialize method. Since this code executes each time the app loads, we need to check the model first – so we don’t duplicate the seed data. The code looks like this -

    @sport_count = Sport.find(:all)
    if @sport_count and @sport_count.size<1
        vars = {"id"=>"1",
                "name"=>"Swimming",
                "abbreviation"=>"swim",
                "icon"=>"icon_swimming.png"}
        @Sport = Sport.create(vars)
        vars = {"id"=>"2",
                "name"=>"Cross Country",
                "abbreviation"=>"cross",
                "icon"=>"icon_crosscountry.png"}
        @Sport = Sport.create(vars)
        vars = {"id"=>"3",
                "name"=>"Track",
                "abbreviation"=>"track",
                "icon"=>"icon_track.png"}
        @Sport = Sport.create(vars)
        vars = {"id"=>"4",
                "name"=>"Other Races",
                "abbreviation"=>"other",
                "icon"=>"icon_other.png"}
        @Sport = Sport.create(vars)
    end

NOTE: the vars lines can be all on one line, I broke it up for readability.

-Jon

Code it right
theCodeDog
theCodeDog

iMessiah is complete

Posted by Jonathan | Posted in rhomobile | Posted on 21-10-2010

2

iMessiah app homescreen

I’ve completed my first mobile app – iMessiah. It’s an app targeting prospective students and contains functionality such as Apply Now, Messiah News, Schedule a Visit, Department Directory, Sports Scores, Campus map and a few other features.

To the right is a screenshot of the home screen. Its been uploaded to Apple and awaiting review. I’ve heard this is a bit of a black box operation, where apps go in and sometimes don’t come out. Actually I think the acceptance procedure is black-box-ish, meaning that if you’re app is not accepted, you don’t know why.  I guess I’ll find out as I wait for a response.  I guess its kinds of like a school girl waiting for that special guy to call and ask her to the big dance.

Read more about it

Code it right
theCodeDog
theCodeDog

RSS Reader for Rhodes

Posted by Jonathan | Posted in rhomobile | Posted on 28-09-2010

2

Part of the app I’m creating for Messiah College is a News Release screen, that pulls all the news releases for the college from their website.  Luckily they have an RSS feed for this, so we’ll exploit that and built a 2-screener model for my app.

The first thing I did was investigate, or do some Free-App-Investigative-Research.  I’m a Redskins fan and I use a free app called Skins Radar.  This has the perfect implementation of a news type feature.  More importantly – it utilizes a great feature for offline reading, so if you don’t have a connection, the page doesn’t error out.  So we’ll use that idea as well.

Our Newsreader model will have two screens – the first a summary listing the Title and small 125 character summary block.  When you touch the block, it’ll load the full post on a 2nd screen.  We’ll use the index method to check to see if the file is there yet, and if not, we’ll call the method to grab it.  If the file is there (we’ve pulled it already) we’ll parse and display the list.

Here’s your index method -

def index
  #build filename with proper location path
  @@file_name = File.join(Rho::RhoApplication::get_base_app_path(), 'messiah_press_releases.rss')
  #check for file first (uncomment to log the check):
  if File.exist? @@file_name
    #puts "\n\n\nITS HERE !!! \n ------------------------------\n\n\n"
    WebView.navigate ( url_for :action => :feed_display_static )
  else
    #puts "\n\n\nGO GET IT !!! \n ------------------------------\n\n\n"
    WebView.navigate ( url_for :action => :feed_refresh )
  end
end

Now then we’ll create this method to fetch the file (or refresh it if its already there).  Since this doesn’t care if the file is there before it pulls it down, it’ll overwrite it with the new one (refreshing it), thus the name “feed_refresh”

def feed_refresh
  #Refresh our feed to local file
  Rho::AsyncHttp.download_file(
    :url => 'http://blogs.messiah.edu/news_releases/feed/rss/',
    :filename => @@file_name,
    :headers => {},
    :callback => (url_for :action => :feed_display_static),
    :callback_param => ""
  )
  render :action => :wait
end

Since we’re using AsyncHttp.download_file – it will well, download the file and name the local copy whatever you named it in the index method.

If the file is already there (we’re returning to this screen from somewhere else) we’ll parse it with the method : feed_display_static

def feed_display_static
  #open the file and read it in :
  file = File.new(@@file_name)
  begin
    require 'rexml/document'
    doc = REXML::Document.new(file)
    @@get_result = "Success"
  rescue Exception => e
      puts "Error: #{e}"
      @@get_result = "Error: #{e}"
  end
  @@xml = doc
  WebView.navigate ( url_for :action => :show_result )
end

Here’s where my ruby / Rhodes experience lacks.  This doesn’t really do the displaying as the method name states, because when I did the parsing of the document here, I had problems sending that parsed information back to the view, so I just parse the returned feed using REXML.  There has to be a better way, but this works for me, so that’s what I’m doing.

I also have this method so we set the @@xml variable and call that from the view

def get_res
@@xml
end

Now we need to make our index.erb file, this is how I did it -

<% xml = get_res()  %>

{snip out the toolbar and header stuff}

One part we won’t snip out is the refresh button :

<div id='rightItem'><a href="feed_refresh"><img src="/public/images/bar/refresh2.png" /></a></div>

put this in the toolbar div and it’ll create a nice right justified refresh icon area. Just add your own icon.

<ul style=’margin-left:10px;margin-right:10px;’>
<%

counter = “0″
data = {}
data['title'] = xml.root.elements['channel/title'].text
data['home_url'] = xml.root.elements['channel/link'].text
data['rss_url'] = @url
data['items'] = []
xml.elements.each(‘//item’) do |item|
it = {}
it['id'] = counter.next
it['title'] = item.elements['title'].text
it['link'] = item.elements['link'].text
it['description'] = item.elements['description'].text
if item.elements['content:encoded']
it['content'] = item.elements['content:encoded'].text
end
if item.elements['dc:creator']
it['author'] = item.elements['dc:creator'].text
end
if item.elements['dc:date']
it['publication_date'] = item.elements['dc:date'].text
elsif item.elements['pubDate']
it['publication_date'] = item.elements['pubDate'].text
end
data['items'] << it

long_desc = it['description'];
brief_description = long_desc[0,125] + “…”;

%>

<li class=’li_detail_disclosure’>
<a href=”<%= url_for :action => :show, :query => {:title => it['title'],:description => it['description'], :link => it['link']} %>”>
<div class=’rss_summary’ style=’width:250px;’>
<span class=’rss_title’><%=it['title']%></span>
<span class=’rss_description’><%= brief_description%></span>
</div>
</a>
</li>

<% end  %>

</ul>

Now, I know you’re supposed to limit the ruby you place in your .erb files, and this is a prime example of my inexperience.  I know this should go into the controller, and maybe in the display method we created above, but I wouldn’t get it to pass to the view.

Now all you need is the show method we call when you tap a summary block.  And here it is pulling the parameters from our query string in the block link -

def show
    @title = @params['title']
    @description = @params['description']
    @website = @params['link']
    render :action => :show
end

And our show.erb file

{snip out the toolbar and header stuff}

<ul><li>
    <span class='rss_detail_title'><%= @title%></span><br/>
    <span class='rss_detail_description'><%= @description %></span><br/>
    <div class='rss_website' align='center'><a href='<%=@website%>'>Read it on the web</a></div>
</li></ul>

Depending on the classes you play with in the css files, you can get this to display quite nicely.

So there you have it in a nutshell.  The basics of an RSS reader.

You can download the entire model here –  just expand it to your app directory, and link to it like this from the main index.erb file in your app -

<li>
  <a href="Newsrelease">
   <span class="title">Messiah News Releases</span>
   <span class="disclosure_indicator"></span>
  </a>
</li>
iPhone App Screenies of NewsReader Model

RSS List

RSS List

RSS NewsRelease Article DetailRSS Article Detail

ISSUES / IMPROVEMENTS / CALL FOR HELP

So – Please let me know how I can improve this – I mentioned how the rendering should get moved to the controller.

I also uncovered an issue with the renderer in index.erb.  When I leave off the “rss/” portion of my url, it will pull FULL articles, and the entire format changes.  The full feed allows for embedded HTML which causes a problem with this parser.  I’m not familiar enough to know how to fix it, so if  you do know, I’d appreciate a comment about it.  I’ll list you in the app credits :)

Code it right
theCodeDog
theCodeDog

Passing parameters with Rhodes

Posted by Jonathan | Posted in rhomobile | Posted on 23-09-2010

1

So I struggle with this with every little thing I try – passing parameters between the view, model and controller.  I never get it right the first 10 times, and just 10 minutes ago figured it out yet again, so I figure I’ll share it.

Here’s the tip – more so I can look it up next time I have a brain fade.

In the view :

create a link like this :

<a href=”<%= url_for :action => :show, :query => {:title => ‘CodeDog.net Rules’, ‘:author => ‘Jonathan’} %>”>

Then in the controller show method

def show
@title = @params['title']
@description = @params['description']
render :action => :show
end

And in our show.erb file simply display with the @variablename

<%= @title %>
<%= @author %>

Very simple. So simple in fact, I’ll forget it in a week.

Code it right
theCodeDog
theCodeDog

iPhone app deployment
using Rhomobile

Posted by Jonathan | Posted in rhomobile | Posted on 31-08-2010

1

Rhomobile LogoSo here is the listing of my heartache when attempting to deploy a Rhomobile app to my phone and how I _finally_ got it working.

Hopefully this will help anyone that is attempting this. I’ll try to post every step I do so its easy when you try. I won’t go into gory detail in the beginning because there are a host of other tutorials out there walking you through these various items. I will however, at least cover them so you know overall what you have to do. (here’s a great one)

Step 1 : Create a (free) account on http://developer.apple.com, this will get you access to the iPhone developer center, docs, XCode, SDKs, etc. You actually NEED to do this if you’re going to use Rhomobile for iPhone development. Its all free and you can develop to your hearts content, however you can’t deploy the app to any phone, or upload it to the app store until you sign it. To do that, you must become a certified Apple Developer (next step)

Step 2 : Pay the Piper purchase yourself a developer account. This is the only way to deploy an app to your phone, unless you jailbreak it (more on that in another post if I get to it). Its quite easy actually, you simply choose whether you want to be certified as an individual or as a company, the price is the same (as of this writing) and the only difference is in the app details listing your name or your company name. Complete their account wizard and your request goes off to Apple for approval. I did a company account and they contact your company for proof that you’re actually a valid company. When in doubt, they can request further proof. Once they’re satisfied you’re you, they send an email allowing you to pay the $99 annual subscription fee and then you’re officially a certified developer.

Step 3 : Set up the Certificate / Provisioning – Once you’re a developer, you gain access to Apples iPhone Provisioning Portal, a website dedicated to managing your (company’s) certificate and development team. Instead of you reading it all here, the best thing to do is to log into the Development Center, access the Provisioning Portal and watch the 4 videos on the right side. They cover topics like – Obtaining Your Certificate, Assigning devices, Creating your app IDs, Creating provisioning profiles. Although you may think watching a tutorial video is stupid, I highly recommend this. Reading a tutorial was confusing, watching it being done made sense.

In order to actually deploy (copy) an app to your phone you need to set up XCode using the various bits of data that the Certificate and Provisioning Portal gives you. The best thing to to – is to watch the 4 videos on the Provisioning Portal (on the right) and follow each one, when you’re done, XCode will be set up and your iPhone (iPad / iTouch) will be set up for development. This in no way hinders it use as a phone though, so don’t worry.

Getting Closer Now

I’m going to assume you were able to get your provisioning profile all set up, so when you open XCode and connect your iPhone you see your provisioning profile name listed on the organizer. This is good.

ENTER RHOMOBILE – Here’s where the fun starts.
I’ll make another assumption, and that is that you’ve been developing with the Rhomobile framework and have a Rhodes app working in the iPhone simulator and you’re ready to copy it to your phone to test it out some more. We’ll say for this example that our Rhodes app is called ‘college’ and located in /Code/iPhone/college

enter in the college directory and edit your build.yml file.

The few settings you’ll need to change are :

iphone:
sdk: iphonesimulator4.0
provisionprofile:
codesignidentity:

Explainations:
sdk : change this from ‘iphonesimulator4.0′ information to ‘iphoneos4.0′

Your provisionprofile is the nasty long ID number you’ll get from XCode Organizer, by clicking on Provisional Profiles on the left, and the Profile name you created in the top pane. You’ll see details in the bottom pane. Copy and paste the Profile Identifier, its a 5 section HEX looking string.

The codesignidentity is actually “iPhone Developer” – not your name, or anything you’d expect.

Make sure when you set these you leave a space after the :
Change these to look something like this -

iphone:
sdk: iphoneos4.0
provisionprofile: 0F6611944-33EA-44AA-A11B-34AAE253A1BBFF (ok, I made that up)
codesignidentity: iPhone Developer

save it.

run rake run:iphone and let it error out if it does indeed error out, which it may. That’s ok … I think :) I can’t remember.

Plug your phone into your computer, and open XCode. Open the Rhorunner project file (rhorunner.xcodeproject) located in \Library\Ruby\Gems\1.8\gems\rhodes-2.0.3\platform\iphone

Once that’s opened, scroll down and double click (to edit) Info.plist

edit the Bundle indentifier to the reverse domain setting thing you set back when you created your app ID. Mine looked like edu.messiah.admissionsprospect. Here you can also – if you want modify other setting for your app, including the icon and name. For some reason, my app was named Rhodes instead of college from my build.yml file, and my icon wasn’t happy so I set that here as well. Save the file.

You’ll want to click the drop-down that probably says Simulator and do a couple things.  First choose the 4.0 at the bottom of the list.  Then click the drop-down again and choose Device.  This sets up XCode to deploy to your attached phone.  Obviously of you set it to Simulator, it’ll run the Simulator for you.  Once you’ve changed to Device and 4.0 – you should be ready.

If I did everything correctly, you can now click Build and Run, and it should build and deploy over to your phone.

app signing permissionYou should be prompted to allow XCode to sign your app as it builds. When this happens, you’re golden. Not only is the project compiling properly, you’ve made it to the signing part and all the puzzle pieces are in order.

When prompted to sign, You can Allow or Allow all the time, you can pick. It takes maybe a minute or two and it will automatically run your app when its completed. You can click your home button and it’ll display your app and its icon on the phone.

I just wrote most of this from memory, I just accomplished this yesterday, so if I missed something or mis-represented something, PLEASE let me know and I’ll change it.

If you have problems, I can try to help, but I’m a green at this as you are.

Code it right
theCodeDog
theCodeDog