The GigaOM Network: Cleantech | Tech Insider | Gadget Gurus | Online Video | Open Source | Web Life | Research | Live Events | About | Contact

iPhone SDK Tutorial: Build a Simple RSS reader for the iPhone

Written on August 04, 2008 by Jason Terhorst and 165 people have commented

With this I’m assuming you have a bit of familiarity with the iPhone SDK – you can download it for free from Apple’s site, and follow along here. We’re going to build an RSS feed reader for a simple feed (from The Apple Blog, no less).

Let’s get started

  1. Open Xcode and choose the “File” menu, in which you’ll click the “New Project…” item.
  2. Click “Application” under “iPhone OS” in the list at left.
  3. On the right, choose “Navigation-Based Application”. Then click the “Choose…” button. You’ll be prompted to pick a name and location. Type in the name “TAB RSS reader”.
  4. Save it wherever you wish.

The Xcode project window will appear, with the standard 3 panes – I recommend pulling the horizontal divider on the right side all the way to the top, since you’ll need that editor area and all the real estate you can give it.

Do you see a “Build and Go” button in the toolbar? Click it, or go to the “Build” menu, and click “Build and Go (Run)” there. It should open the Simulator application and launch a simple iPhone app that displays a blank navigation bar and blank table. Whee! Your first iPhone app. Now let’s sculpt it into something.

The project template that Apple provides has a lot of things already set up to get us started. On the list at the left of the project window, find “MainWindow.xib”, and double-click it. This is the basic framing of your application’s UI. Be careful not to mess around here too much. You just need to do one thing: you should see a “Navigation Controller” window with a basic interface mocked up – double-click on the navigation bar (which has no title in it), and type “The Apple Blog”. Press return. Save and quit Interface Builder.

Click once on “RootViewController.h” in the list, and see the code on the right. Make it look like this:


@interface RootViewController : UITableViewController {
	IBOutlet UITableView * newsTable;
	UIActivityIndicatorView * activityIndicator;
	CGSize cellSize;
	NSXMLParser * rssParser;
	NSMutableArray * stories;

	// a temporary item; added to the "stories" array one at a time, and cleared for the next one
	NSMutableDictionary * item;

	// it parses through the document, from top to bottom...
	// we collect and cache each sub-element value, and then save each item to our array.
	// we use these to track each current item, until it's ready to be added to the "stories" array
	NSString * currentElement;
	NSMutableString * currentTitle, * currentDate, * currentSummary, * currentLink;
}
@end

That’s the declaration file, where we’re telling the compiler what to expect when it runs through the controller logic. Here’s where the real work happens… Open “RootViewController.m“.

You’ll see that there’s more of the basic code to make that table view display – this controller is the table’s “delegate” – the table looks here to find out what it’s supposed to see/display/do in various situations, and sends calls for methods when the user performs various actions.

Change the value of - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section to return [stories count];

In our declarations, we told it we would have an array (NSMutableArray – a modifiable collection of objects), which we called “stories”. The [brackets] around that bit signify that it’s a message – we’re asking the stories array what its current count is – that is, how many items it has. Our RSS reader will grab as many items as it can (one for each story in the RSS feed), and place them in that array, so this method will tell the table This is how many rows we need: one for each item in the array, or for each item in the feed. Before, it was set to 0, so you’re giving it more information on our array.

Next up, modify the method below the one you just changed, like so:


- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
	static NSString *MyIdentifier = @"MyIdentifier";
	UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier];

	if (cell == nil) {
		cell = [[[UITableViewCell alloc] initWithFrame:CGRectZero reuseIdentifier:MyIdentifier] autorelease];
	}

	// Set up the cell
	int storyIndex = [indexPath indexAtPosition: [indexPath length] - 1];
	[cell setText:[[stories objectAtIndex: storyIndex] objectForKey: @"title"]];

	return cell;
}

As you can see, we used the “setText:” method to tell the cell what the contents will be. Each row in the table is basically a cell, and its properties are set in this method.

There are 4 methods highlighted in green about 3/4 of the way down – you can delete those if you wish, since we won’t be using them. They have to do with adding/deleting items.

If you were to run the program again now, it still wouldn’t do anything: we haven’t added the ability to download the feed and use it yet, so let’s do that now.

Edit the “viewDidAppear:” method to look like this:


- (void)viewDidAppear:(BOOL)animated {
	[super viewDidAppear:animated];

	if ([stories count] == 0) {
		NSString * path = @"http://feeds.feedburner.com/TheAppleBlog";
		[self parseXMLFileAtURL:path];
	}

	cellSize = CGSizeMake([newsTable bounds].size.width, 60);
}

This is where we tell the parser which feed to download. It calls a method, which you’ll want to paste in now:


- (void)parseXMLFileAtURL:(NSString *)URL {
	stories = [[NSMutableArray alloc] init];

	//you must then convert the path to a proper NSURL or it won't work
	NSURL *xmlURL = [NSURL URLWithString:URL];

	// here, for some reason you have to use NSClassFromString when trying to alloc NSXMLParser, otherwise you will get an object not found error
	// this may be necessary only for the toolchain
	rssParser = [[NSXMLParser alloc] initWithContentsOfURL:xmlURL];

	// Set self as the delegate of the parser so that it will receive the parser delegate methods callbacks.
	[rssParser setDelegate:self];

	// Depending on the XML document you're parsing, you may want to enable these features of NSXMLParser.
	[rssParser setShouldProcessNamespaces:NO];
	[rssParser setShouldReportNamespacePrefixes:NO];
	[rssParser setShouldResolveExternalEntities:NO];

	[rssParser parse];
}

This is a method we’ve added that creates the empty array for stories, creates a parser, and starts downloading the feed. As the parser works, this controller we’re working in will receive the various delegate methods, which you can paste in now:


- (void)parserDidStartDocument:(NSXMLParser *)parser {
	NSLog(@"found file and started parsing");
}

- (void)parser:(NSXMLParser *)parser parseErrorOccurred:(NSError *)parseError {
	NSString * errorString = [NSString stringWithFormat:@"Unable to download story feed from web site (Error code %i )", [parseError code]];
	NSLog(@"error parsing XML: %@", errorString);

	UIAlertView * errorAlert = [[UIAlertView alloc] initWithTitle:@"Error loading content" message:errorString delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
	[errorAlert show];
}

- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict{
	//NSLog(@"found this element: %@", elementName);
	currentElement = [elementName copy];

	if ([elementName isEqualToString:@"item"]) {
		// clear out our story item caches...
		item = [[NSMutableDictionary alloc] init];
		currentTitle = [[NSMutableString alloc] init];
		currentDate = [[NSMutableString alloc] init];
		currentSummary = [[NSMutableString alloc] init];
		currentLink = [[NSMutableString alloc] init];
	}
}

- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName{

	//NSLog(@"ended element: %@", elementName);
	if ([elementName isEqualToString:@"item"]) {
		// save values to an item, then store that item into the array...
		[item setObject:currentTitle forKey:@"title"];
		[item setObject:currentLink forKey:@"link"];
		[item setObject:currentSummary forKey:@"summary"];
		[item setObject:currentDate forKey:@"date"];

		[stories addObject:[item copy]];
		NSLog(@"adding story: %@", currentTitle);
	}
}

- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string{
	//NSLog(@"found characters: %@", string);
	// save the characters for the current item...
	if ([currentElement isEqualToString:@"title"]) {
		[currentTitle appendString:string];
	} else if ([currentElement isEqualToString:@"link"]) {
		[currentLink appendString:string];
	} else if ([currentElement isEqualToString:@"description"]) {
		[currentSummary appendString:string];
	} else if ([currentElement isEqualToString:@"pubDate"]) {
		[currentDate appendString:string];
	}
}

- (void)parserDidEndDocument:(NSXMLParser *)parser {

	[activityIndicator stopAnimating];
	[activityIndicator removeFromSuperview];

	NSLog(@"all done!");
	NSLog(@"stories array has %d items", [stories count]);
	[newsTable reloadData];
}

Unfortunately, the NSXMLParser is the only simple XML-parsing tool available on iPhone (some of my favorites from the Mac are missing). So, this means we have to crunch through the file in order from top to bottom. We have a series of strings that we assign values to, and then collect them into story items, which are saved one by one. Once it hits the closing “item” tag, it saves that story, clears out the fields, and starts on the next item until we reach the end of the file. Not my favorite approach, but it works.

Finishing up

We need to shut off any potential memory leaks (it’s a good habit to get into, when you don’t have garbage collection – who needs that anyway?). Drop in this change:


- (void)dealloc {
	[currentElement release];
	[rssParser release];
	[stories release];
	[item release];
	[currentTitle release];
	[currentDate release];
	[currentSummary release];
	[currentLink release];

	[super dealloc];
}

Next, open up “RootViewController.xib“, and hold down the “control” key on your keyboard, while dragging from the “RootViewController” cube icon over to the table view, and release. You should see a list of three items appear, so click on the “newsTable” item. Save and quit Interface Builder.

Build and Go

If you click “Build and Go”, you’ll see the results we have so far. If you were to run this on an actual iPhone and not in simulator, the results would be different slightly: the hardware is slower, and if you’re on EDGE, the RSS feed will take a very long time to download. But, hey, it works! One thing that doesn’t work yet: when you tap on an item in the table, nothing happens. This is default behavior, but let’s make the stories open in Safari – that’s an easy thing to do. Just change this method:


- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
	// Navigation logic

	int storyIndex = [indexPath indexAtPosition: [indexPath length] - 1];

	NSString * storyLink = [[stories objectAtIndex: storyIndex] objectForKey: @"link"];

	// clean up the link - get rid of spaces, returns, and tabs...
	storyLink = [storyLink stringByReplacingOccurrencesOfString:@" " withString:@""];
	storyLink = [storyLink stringByReplacingOccurrencesOfString:@"\n" withString:@""];
	storyLink = [storyLink stringByReplacingOccurrencesOfString:@"	" withString:@""];

	NSLog(@"link: %@", storyLink);
	// open in Safari
	[[UIApplication sharedApplication] openURL:[NSURL URLWithString:storyLink]];
}

Now, click “Build and Go” again, to see that it works.

Done for Now


You can download the finished project file here if you wish.

Check back here later, and we’ll cover some steps on how to clean up the UI, and add some navigation.

Leave a comment

Comments (165)

  • You may have just violated the NDA! The Apple police will be circling your home about now!

  • The NDA is ludicrous, and for beginners like myself, this sort of tutorial is an absolute pile of GOLD!! THANK YOU, THANK YOU, THANK YOU!!!! =D

  • I have been critical of TAB as of late, but kudos to you for telling Apple where it can shove its NDA. Well done!

  • Great tutorial, thanks a lot for putting this out, saved on my harddrive ready to be reposted in case apple watchdogs get to you.

  • Very nice! Thank’s for your tutorial, much appreciated.

  • Why would apple not want resources published that help people build applications for their phone?

  • In completely unrelated news, Apple has released iPhone 2.0.1!

  • Dude…SDK violation. Prepare for Apple’s legal team! But, great job! This is amazing. Thanks for ignoring Apple’s idiotic NDA and writing what people have been looking for since the SDK came out.

  • Damn.. now I might have to check out the price for one of those iPhone thingies. Interesting stuff.

  • Nice tutorial. Only one problem — NSXML* isn’t available on the iPhone… it’s in the Simulator SDK, though, which is why you can compile it. I suggest using TouchXML; the usage (for non-extravagant uses of NSXML*) is exactly the same, unless your XML document has namespaces, in which case it’s a simple adjustment.

  • looks to me like there are a lot of memory leaks in that code…

    • Specify line numbers if you have something… otherwise it’s not helpfull.(going only halfway.)

  • Can someone clarify jtbandes claim that NSXML is not supported on iPhone? I Googled and found a lot of stuff saying it wasn’t supported but would compile in the simulator as jtbandes claims. I did find one forum post that says it is supported on the phone itself. Would you care to comment Jason?

    To Ig: He specifically cleans up memory so what are you talking about? Care to cite an example and improve this article for everyone? Is your point to be helpful or just rude?

    Thanks very much for taking the time to write this article. I really appreciate it.

  • Great tutorial, thanks Jason.

    The only issue I had was that the links opened to the wrong website. The line:

    storyLink = [storyLink stringByReplacingOccurrencesOfString:@"n" withString:@""];

    in the last part is removing the n in http://www.feedburner.com so all links open to some spam site named http://feedburer.com/. I commented out this line and it worked fine.

  • @jtbandes: NSXMLParser is one of the few that *is* available on the iPhone OS, on the device. I’m not sure what you’re talking about, but I have a couple shipping apps that use NSXMLParser for key functions.

    @Michael N.: I made a bit of a typo. Where you see @”n”, it should actually be @”\n” (a newline character)… sorry about that. :) It’s not needed, but in some of my clients’ RSS feeds, there are odd spaces and line breaks, so that helps keep the iPhone from choking on it, so I’ve made it a bit of habit.

  • @Jason: I thought as much, so I added the “\” to my code right after I left that comment.

    Looking forward to your update to this tutorial, any chance you’ll add the ability to view the stories in the app rather than opening Safari?

  • How is this a tutorial? Just copy and paste some pre-written code into your IDE? Doesn’t really help anyone understand how to actually code for the iPhone.

  • When I first plugged my iPhone in, Xcode asked a couple of times if I wanted to use it as a development device. Now that I have the sample app running in the simulator, when I connect the phone I no longer get the prompt to let Xcode use it. I went through Preferences but I don’t see any options to make Xcode redetect the phone.

  • Great all these dudes will follow this and we will get another 400 useless apps that crash our phones!

  • I have never programmed in Objective-C but I must say the syntax looks absolutely horrendous. I have a strong CS background including a lot of C++, but I cannot understand half of the constructs at first sight. The use of () [] is uberly inconsistent. And why does it requires a dash before every method declaration? Why not use the same syntax as C/C++ as C# did? I can’t believe Mac developers are forced to write application in that awful language.

    They must feel very 1980 when they see neat programs written in a modern language.

    • Im a C# programmer myself and I originally hated obj-c. Now I find obj-c to be a simple and elegant language.

      the brackets are used for objects. and if you feel like it you can code in c. but why ? each call to property or function are fairly strait forward. Your issue was probably the same as mine. I wanted it to be too complicated and saw it as such. Its so absurdly simple that it took me a long time to grasp it. (think mac…. Think Simple)

  • Thanks for this excellent tutorial. I have a tiny bit of Objective-C programming background, but haven’t used it in about a year. I’ve been wanting to pick up iPhone programming but have been mortified to climb back up that steep Objective-C learning curve. This article was a great (re-)introduction, and I found your small descriptions of each chunk of code very useful in reorienting myself to the disorienting world of Objective-C :)

    It might be a good thing to add in the beginning that this article assumes some familiarity with Objective-C (in addition to the iPhone SDK, as you already point out). To some of the commenters points, this is *not* an Objective-C tutorial nor does it purport to be. IMHO, for a great introduction to (and in-depth coverage of) ObjC, check out Aaron Hillegass’ “Cocoa Programming for Mac OS X” — it’s not specificially about iPhone but it will get you on the right track ….

  • Nice, but I’m stuck at the part when you have to ctrl drop the box to table view.
    I’m a Super-newbie, so can somebody help me???

    • control click is mac’s version of right click. You can hold control then click and drag from control to class object. or you can use the right click….

      And remember. Drag from object to code to send data from Interface Builder (or to make interface Builder Get data from code). and Drag from code to object to Get data from Interface Builder (such as letting an IBOutlet access a control on the interface).

  • Ohw. I see no edit button so:
    If I do the ctrl drop I see only tableview and view.

  • @Geuis It does’t really matter that you can’t set it to use your iPhone, you need to register with Apple and pay the $100 to get a key (or what ever it’s called) that will allow you to both run your app on your iPhone and submit it to the App store. With out that key all you can do is test on the simulator.

    If anyone knows differently then I would love to hear from them.

  • @Michael N Yeah I was coming to that realization after finally getting the app running last night. I’m still confused though, because when I first opened Xcoode and had my phone plugged in, it asked me if I wanted to use the phone as a development device. I clicked no the first couple times, but now I can’t get that prompt to appear again. Even if I can’t deploy to the phone right now, I don’t want to be in a situation later on where I can’t deploy even after I pay the blood toll to Apple.

  • Yes, you’d need a developer account to create provisions for your device.

    But we don’t discuss that here. Definitely NDA, with good reason. ;)

    @Dan: Yes, that book is a definite recommendation for getting started. This tutorial is meant for those with experience in Objective-C, or those clever enough to work their way through it, with the assumption that it will pique your interest enough that you’ll go out and find materials to get up to speed and figure other things out. :) Personally, I learn best by taking apart existing working code and understanding it that way.

  • @Vincent (#19): Are you essentially saying that Objective-C’s syntax is horrible because it’s *shock* different to things you’ve used before? Perhaps, before slagging off a language for being ‘awful’, you should learn why it’s different, so you can make an informed opinion. I was unsure of Ruby’s syntax when I first saw it (Python being my previous favourite) but I looked into it, took the time to learn some things, and saw that many of its conventions made a lot of sense.

    Objective-C is a fantastic language – I suggest you start with http://cocoadevcentral.com/d/learn_objectivec/ to see if it’s something you could get along with.

  • @Vincent: Also, to response to your questions:

    Square brackets are used in message sending (calling methods) – [foo baz]; sends the message baz to foo (calls the method baz on the object foo. [foo fireEmployee:@"Bob" withReason:@"None needed"]; would call the fireEmployee:withReason method on foo.

    - is used infront of method declarations to denote an instance method. + denotes a class method.

  • I’ll chip in a few bucks for your legal defense if needed. Maybe you’ll get 15 minutes of fame from it. More examples like this are needed in order to help developers not familiar with Xcode overcome the initial learning curve of building an application.

    It seems like the current SDK restrictions will also prevent 3rd party books on iPhone development from being published. If you look on Amazon under “iPhone Development” there are several titles in the works, but at the moment it doesn’t seem like they could ever be legally published.

  • @Geuis – To provision your iPhone for development, connect your iPhone to your machine and fire up Xcode. From the Window menu, select “Organizer”. You should see your iPhone in the list of devices. Click on the iPhone in that list, and I suspect you’ll be able to figure out the rest from there… =)

    Cheers,
    Jon

  • Very nice tutorial. I’m very much looking forward to seeing how to implement navigation into the next view (instead of launching safari.)

    Thanks again!

  • @Vincent

    I have never programmed in Objective-C but I must say the syntax looks absolutely horrendous. I have a strong CS background including a lot of C++, but I cannot understand half of the constructs at first sight. The use of () [] is uberly inconsistent. And why does it requires a dash before every method declaration? Why not use the same syntax as C/C++ as C# did? I can’t believe Mac developers are forced to write application in that awful language.

    Man, I had to wipe a tear from my eye when I read that. You’re a funny guy, suggesting that C++ is actually readable to the uninitiated when you get beyond syntax that is just warmed over C with objects.

    You might find the language to be interesting if you would, *drum roll*, read the language spec. It’s actually a very powerful, useful language that ranks right up there with Java and C# in terms of what it can do with minimal syntax.

    And dude, you might want to avoid saying “oh that’s so 1980s” when you admit that much of your own background is C/C++. One is 1970s tech, the other is 1980s. Objective-C 2.0, on the other hand, is fairly modern stuff as C-based languages go. You would know that if you ever glanced over the language spec.

  • Ran fine for me. The only issue is that it gives a warning box:

    ‘RootViewController’ may not respond to ‘-parseXMLFileAtURL:’
    (Messages without a matching method signature will be assumed to return ‘id’ and accept ‘…’ as arguments.)

    Other than that, a nice intro. Off to http://cocoadevcentral.com/d/learn_objectivec/ to learn how to make one of 400 new crappy apps. Thanks for the encouragement, Mr Elitist.

  • Peace be upon you
    The tutorial is very nice and it goes very smoooooooth with me, Thanks a lot Jason, I hope that you give more samples,

    Thanks for your time.

    BR
    Ahmed Essam

  • So how exactly is Apple going to monitor EVERY line, in EVERY blog, every chat, and every webpage, and every email… to make sure 10000s of people that DID sign a NDA are “not speaking”, and 10000s other people, *ARE* allowed to talk freely.

    Just use a handle, instead of your real, full name.

  • @ James Frost
    I have on my side a background in many different languages including C/C++/java/C# but also exotics like lisp/prolog and scripting like javascript/ruby/perl/python.

    I picked up ObjectiveC a couple months ago when starting to program for the iphone first on jailbroken 1.X phones then on the SDK.

    Here is what is my (hopefully objective opinion).

    1) ObjectiveC is very nice to program and definitely nicer than C++ (which I do for a living) and less error prone, once you get past the syntax.
    2) the ObjectiveC syntax is in fact horendous, not because it is different but because it is inconsistent with the C based roots. And with itself… Here are example from my perspective of inconsistencies:
    Usage of (), sometimes (method definitions) they are used to indicate where types are specified for parameters or return values, sometimes (properties) they are used for optional parameters to the keyword @property and not for the type.
    Usage of named parameters in messages. Why is the first parameter special, why does it reuse the message name as its name, it would be more consistent to have the first parameter named the same way as the others.
    Usage of [] for message passing. This is inconsistent with other usages of [] in the same program (indexing), finding another way to specify message passing vs data member access would have been nice
    Usage of . with properties. Objective C objects are pointers, using . after a pointer is inconsistent with the rest.

    This being said. I think that ObjectiveC is easy to pick up for someone who has a base in any C based language (easier than C++, harder than java or C#) and the syntax quirks are just that, quirks which add maybe a day at most 2 in the learning curve, but if you can’t read the message passing syntax after reading a one page primer on ObjectiveC you probably don’t have any place programming.

  • Simple clean real tutorial.

  • I really appreciate the effort on your part for this tutorial, but this tutorial had a great deal of “Type Now, Learn Later” elements to it. Even worse is “Paste Now, Learn Later”. I didn’t know what I was doing half the time; I just followed the instructions. I did very much appreciate the parts where you explained what a View Controller was doing in plain English, and that sort of thing.

    I must say that it perplexes me that Objective-C can’t follow a standard function signature convention. Coming from C#, it’s difficult for me to tolerate even C and C++, but Objective-C is even worse, and it doesn’t help that the default curly brace format places opening braces at the end of a line of code *cringe*. I thought we’d moved beyond that.

    Anyway, I hear a lot of people defend Objective-C, but I’d be very curious to see the same defense from an Objective-C developer who tries C# for a few months and then returns.

  • @Vargonian: Having had some previous Obj C experience this code made perfect sense to me. As an excersize I am expanding on this, and it is my gateway into iPhone development.

    @Jason Terhorst: Do you mind if I use this code as a spring board (pun intended) for my first iPhone app?

  • Not bad, as these things go. I found by typing in what you’d written, I gained a better feel for actually programming in Objective-C. (The first step for me to learn any language is to copy, letter by letter, then figure out what I just wrote, then finally branch out with my own variation.)

    My only qualm with the code itself is that the functions for the XML parser are stored within the Controller, rather than doing something more MVC or Object-Oriented, such as creating a feedModel object or something, and then working with it… Then again, it’s likely if I keep exploring Apple’s sample code, I can figure out how to apply the reference material and better programming practices like MVC to iPhone development…

    I just wish Apple would listen to *******NDA.com and realize its hurting them much more in the prevalence of unstable, poor applications as well as the creation of a real developer community. Hell, just give an exemption to a few books, or offer them as encrypted files to developers only, or even set up a sanctioned forum for swapping iPhone dev tips – I mean, you can’t even talk about it on Cocoa-dev mailing lists now …

  • In case anyone is wondering, the UIActivityIndicatorView was not being created or used at all. To use it you have to instantiate it and add it to the view.

  • Very good tutorial but i can’t open link with Safari , Anyone can help me

    - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    // Navigation logic

    int storyIndex = [indexPath indexAtPosition: [indexPath length] – 1];

    NSString * storyLink = [[stories objectAtIndex: storyIndex] objectForKey: @”link”];

    // clean up the link – get rid of spaces, returns, and tabs…
    storyLink = [storyLink stringByReplacingOccurrencesOfString:@" " withString:@""];
    storyLink = [storyLink stringByReplacingOccurrencesOfString:@"\n" withString:@""];
    storyLink = [storyLink stringByReplacingOccurrencesOfString:@" " withString:@""];

    NSLog(@”link: %@”, storyLink);
    // open in Safari
    [[UIApplication sharedApplication] openURL:[NSURL URLWithString:storyLink]];
    }

  • @MikeT I Completely Agree, I may be Intruding a Little bit but, here I Go, If @Vincent Wanted Completely Readable Code base For iPhone, Try Making a Ruby on Rails Webapp (Although it Cannot Scale, Just Kidding! @Railsenvy) and Make an Simple Dedicated Web Browser for it, and Put it together as one Beautiful App!

  • Hi, folks,
    If you’re joining the party, feel free to post any questions here in the comments. Please don’t email me with questions; I don’t have time to answer them all.
    Thanks.

  • Love this tutorial, great work! Would love to know how to add a thumbnail image from the feed to the table view and how to link a video link from the XML feed to the media player framework… Got it to play a video when you click the article, but it launches in Safari… Can’t wait for an update/part two of this!

  • In the root view controller you can get the activity indicator to work with the code below, posting this to save someone else the few hours it took me to figure this out…

    Also if you get the warning mentioned in comment #32, you can fix it by moving the definition of that method ahead of the use of it in that file.

    - (void)viewDidLoad {
    // Add the following line if you want the list to be editable
    //self.navigationItem.leftBarButtonItem = self.editButtonItem;

    // make the activity indicator as the right side button
    CGRect frame = CGRectMake(0.0, 0.0, 25.0, 25.0);
    activityIndicator = [[UIActivityIndicatorView alloc] initWithFrame:frame];
    [activityIndicator startAnimating];
    [activityIndicator sizeToFit];
    activityIndicator.autoresizingMask = (UIViewAutoresizingFlexibleLeftMargin |
    UIViewAutoresizingFlexibleRightMargin |
    UIViewAutoresizingFlexibleTopMargin |
    UIViewAutoresizingFlexibleBottomMargin);

    UIBarButtonItem *loadingView = [[UIBarButtonItem alloc] initWithCustomView:activityIndicator];
    loadingView.target = self;
    self.navigationItem.rightBarButtonItem = loadingView;
    }

  • Great tutorial for someone like me who is noobish.
    Tnx

  • How do you change where the RSS feed comes from?

  • The RSS feed address is hardwired in the viewDidAppear method. Easy to change…

  • I just changed the URL to point to a Flickr Interesting RSS feed I rolled up and it was easy to view. Too bad it’s so hard to get something like that onto my iPhone since I could see myself using that little app.

  • Hey, thank you so much man…wow…I’m a total NOOB, and even I was successful on 2nd try! But can you please tell me how to change the icon in the home screen for this app? Thank you again man…

  • drop the icon in the same folder as info.plist, and edit info.plist to tell it the name of your icon

  • Whenever I try to run the app, the rss feeds do not display. Help!

  • Very nice. Thanks.

  • As to my post #52, I fixed it. A couple of questions:
    1. How do I change the font size?
    2. Is it possible to show the date?

  • @#54 -

    When I open in simulator it doesn’t display anything either, what did you determine was your problem? I’m assuming I forget something but checked my code twice and still haven’t found anything. I’m new to this so I’ll continue checking but, if anyone has any advice I’d appreciate it.

  • This is an awesome tutorial. I have been looking for a tutorial like this for the longest time. I actually found this site on http://www.iphonedevver.com which is an iPhone SDK tutorial search site.

  • Thanks a lot . you explain nicely this topic thanks a lot

  • I am new at i-phone 2.0 application developement….I am not getting at how to access CGrectangles in array!!Plz suggest me any way..Thanks.

  • How can I change the text size? Excellent tutorial, but I am finding the text too big!

  • Thank you :)

  • Correct me if I am wrong but shouldnt:

    currentElement = [elementName copy];

    be this?:

    NSMutableString *test = [[NSMutableString alloc] initWithString:elementName];
    self.currentElement = test;
    [test release];

    I might be wrong but the format would create a memory leak, while the later will not. Make sure you run your applications through Instruments.

  • When you run this application through Instruments it shows memory leaks. I have tried to fix them but I cannot get them all.

    Any ideas? Has anyone else been able to fix the leaks and share when the changes need to be?

  • This is horrible code. There are memory leaks everywhere.

  • And no, the little bit of dealloc code at the end doesn’t fix it.

  • Any idea how to modify this zip to get it to work on ppc mac? I get the following when i try and build it.
    Line Location Tool:0: No architectures to compile for (ONLY_ACTIVE_ARCH=YES, active arch=ppc, VALID_ARCHS=i386).

  • hahah
    wow i don’t get it
    well i do ~ but it doens’t work for me
    hahah

  • Very nice tutorial. I’m very much looking forward to seeing how to implement navigation into the next view (instead of launching safari.)

  • Very nice tutorial. Appreciate the work you put into it. One question though. With this parser, is there any reason why it should truncate the description of a feed? I did some digging and I think it may be a problem with RSS2.0. Can I rule this out or is a plausible reason for the problem? Thanks.

  • A much nicer/neater/standard activity indicator in the top status bar:

    UIApplication* app = [UIApplication sharedApplication];
    app.networkActivityIndicatorVisible = YES;

    and set it to NO when you’re done loading your data.

  • You can download the Stanford University’s entire iPhone Development Lecture in PDF format here http://www.cultofiphone.org/forums/showthread.php?t=342

  • Very nice job with all of this. Any ideas on how to add a ‘refresh’ button?

    I took the code and am displaying statistics — very cool way to get at XML data.

    Thanks.

  • @#69 -

    Where I can paste this code I mean which file?

    Thanks!

  • Thanks for this tutorial. It helped me a great deal to develop my initial application.

  • thanks I used this to write a program for my church sermon podcast but my question is 1 when i click on my link it opens another page in safari where i then have to choose the mp3, and if a use a rss.xml file the links dont work? http://bepsermons.libsyn.com/rss is my feed

  • Ugh, this is riddled with memory leaks.
    You’ll want to add this:

    if (currentElement) {
    [currentElement release];
    currentElement = nil;
    }

    before this:

    currentElement = [elementName copy];

    and this:

    if (stories) {
    [stories release];
    stories = nil;
    }

    before this:

    stories = [[NSMutableArray alloc] init];

    That helps a lot of it. Be sure to run this stuff through Instruments.

  • Hi,

    I am using XCode3.1 beta. In this version, while starting a new project, under iPhoneOS->Application menu, no ‘Navigation-Based Application’ item is there. Only ‘Cocoa Touch Application’, ‘Cocoa Touch List’ and ‘Cocoa Touch Toolbar’ options are there. Is there anything wrong in these steps ? Or do i have to download any sort of plugins to get ‘Navigation-Based Application’ this option ?

    please direct me. i am in stucked stage.

    thanks and regards,
    sunil

  • For an app this size, and given that it runs once, these memory leaks are really irrelevant.

  • Thanks so much for your tutorials! I think everyone in the world is learning iphone development and you are playing a key role in helping people out.

    You have saved me a tremendous amount of time, I have actually gone to sleep early now tha I have some guidance :)

    Thanks again and GREAT JOB!

    -Oscar

  • Hi,

    I have published this excellent tutorial at http://www.iPhoneKicks.com which is a community based news site purely for iPhone SDK development news. I wanted to know if you would want to implement our Digg like widget on your blog posts which relate to iPhone SDK development?

    Thanks,
    Raj

  • How do you change the RSS feed to a different URL?

  • can someone give me the entire code for RootViewController.xib

  • Ran this through instruments and found that rssParser leaks memory as well. This fixed it for me…

    - (void)parserDidEndDocument:(NSXMLParser *)parser {
    [self hideActivity];
    NSLog(@”stories array has %d items”, [stories count]);
    [newsTable reloadData];
    [rssParser release];
    }

    i also added an activity view, but to do that you have to use a new thread and a new autorelease pool…

    [NSThread detachNewThreadSelector:@selector(downloadAndParseFeed:) toTarget:self withObject:nil];

    - (void)downloadAndParseFeed:(id)anObject {

    // create an auto release pool for the thread…
    NSAutoreleasePool *autoReleasePool = [[NSAutoreleasePool alloc] init];
    //rest of code

    [self parseXMLFileAtURL:path];
    [autoReleasePool release];
    }

  • For the “Finishing up” section, can someone explain whats the magic behind the click and dragging the cube to the the tableview?

  • There seems to be leaks in the NSXMLParser when you call an NSURL directly. I have found a way around it that seems to sort all the issues out…

    Please see this post…
    http://www.iphonedevsdk.com/forum/iphone-sdk-development/4910-nsxmlparser-rssparser-causing-memory-leak.html

    Hope that helps.

  • I’d also do this, to stop it leaking when you parse the xml again to refresh, etc.
    [stories addObject:[[item copy] autorelease]];

  • REALLLLLLLY NEED TO DISABLE SMILIES ON THIS SITE. VERY ANNOYING.

  • I have a question. I just downloaded the SDK beta 3 for iPhone 2.1… When I click the applications in xCode under iPhone OS there is no object called “Navigation-Based Application”..Do I need to get this from somewhere else or reinstall?

  • The following method declaration is missing from the header file, just add this in to avoid the compile time warning

    - (void)parseXMLFileAtURL: (NSString *)URL;

  • Hi Jason,

    The tutorial is great – very clear and easy to follow.

    I’d like to try to build an RSS reader like this that can handle feeds that require HTTP authentication and SSL. Could you point me in the right direction? I’ve read arround a bit but am stuck. Am I correct in assuming NSXMLParser won’t handle authentication and I need a lower level API?

    Cheers.

    Hadley.

  • Excellent article, though I would love to have a parser that let me use XPath and with very few lines of code for developer to write in achieving the functionality.

    Problem 1:
    Has anyone worked with TouchXML, I am facing problem parcing rssfeed that has characters like & or even &
    The parser takes the url as input and doesn’t seem to parse the XML content. NSXMLParser has no such problem for the same feed URL.
    Problem 2:
    Another problem with NSXMLParse is when the foundCharacter() method finds “\n”
    even the call like
    if([currentElementValue isEqualToString:@"\n"])
    return;

    currentElementValue = [currentElementValue stringByReplacingOccurrencesOfString:@"\n" withString:@""];

    both these lines doesn’t seem to eliminate the \n character.

    Any help guys ?

  • Problem 2: IS resolved, there were trailing spaces after \n hence the replace and if condition failed.

    Problem 1: Still remains.

  • THANKS FOR THE TUT! (Disregarding all the NDA bull above)
    Being a designer, not a programmer, it helped a lot. Though I must say I followed along closely but ultimately had to download your completed version. Then compared my “followed along” version to your version and they did not quite match up with respect to where the coded was placed within the RootViewController doc. Thanks for posting finished version!

  • How do you resize the text? A couple of people have asked this but no one answered it yet?

    Also, how do you load this in a WebView in the same app and NOT open safari?

  • OK, i have tried this tutorial twice from scratch and both times I get several errors.
    Is anyone actually getting this to work?

  • Hi, I tried your code. The simulator comes up but it shows the error message “Error Loading content. Unable to download story feed from web site (error code 5).

    With other sample code (XMLPerformance, SeismicXML) I am also not able to view the xml contents.

    Can you please suggest a solution ?

  • This iPhone SDK Tutorial: Build a Simple RSS reader for the iPhone it very helpful to create a rss reader but i was wondering if you can help and tell me how to display the small summary of the feed under the title and add the date in as well. i will be very grateful if you can help me.

  • Love this tutorial, works great, I have used some of the code in a few of my apps. Thanks.

    However…it would be nice to be able to resize the text in the table view? Any ideas how to do this?

    Also, it would be nice if we could launch a Webview within the program so we don’t exit the program to safari upon clicking of the rss feed in the table view. Any ideas on how to do this?

  • Thank you! very useful!!!

  • For everyone who wants to change the text size, etc. you’ll want to replace this line:

    [cell setText:[[stories objectAtIndex: storyIndex] objectForKey: @”title”]];

    With this:

    //Story title
    CGRect contentRect = CGRectMake(10.0, 10, 260, 60);
    UILabel *textView = [[UILabel alloc] initWithFrame:contentRect];
    textView.text = [[stories objectAtIndex: storyIndex] objectForKey: @”title”];
    textView.numberOfLines = 3;
    textView.textColor = [UIColor blackColor];
    textView.font = [UIFont boldSystemFontOfSize:14];

    The demo app just writes the title into the table row, the code above creates a UILable inside the row and sets text size, dimensions, etc.

    Thanks for the demo, and I appreciate everyone’s comments on where to fix the memory leaks, I noticed those too and had no idea how to fix them…

  • And to answer the other general question going around the comments: To create a detail view you’ll have to combine this with a UINavigationController and then “push” a detail view, (as well as passing whatever data you want to show). In my case the detail view is a UIWebview that reads the content node of the xml file I’m reading. When I’m done I’ll try and post the finished project so others can hopefully learn from my experience.

    • Did you get around to implementing the UIWebview into the project? If so I am interested in checking out the code. Thanks!

  • I am trying to edit this so my own blogs posts will show up, but its not having it! Any advice?

  • George, did you change the FEED location? (look for NSString * path and change that string to your feed location) After that it’s just a matter of looking at your feed and changing what strings the code is looking for. In my case I had to change the startParsing to “entry” from whatever it was in the code.

    Hope that helps, r.

  • … shame on you dont forget

    [errorAlert release];

  • Looking closer this is some of the worst code ive ever seen. wtf replacing string data like spaces with blank instead of encoding them properly? retarded

  • I have a RSS feed that has an “&” symbol in it and it seems to get caught up in the code and nothing displays? Any ideas how to fix this?

  • Hi,
    I woul like to use this for my RSS feed on my site, but I can’t figure out in the code where to put my URL, if I place it where NSString * path = http://feeds.feedburner.com/TheAppleBlog“; is, I just get my screen on the iPhone blanc.
    Thx for the help

  • I tried the code above to shrink the text size, but as soon as I use it, the data in the table disappears. Any ideas?

  • i tried doing this tutorial, however, i get the error, cant download from site error code 5.
    and then i get an error called error 75. i have this error in my code.

    ‘RootViewController’ may not respond to ‘-parseXMLFileAtURL:’
    (Messages without a matching method signature will be assumed to return ‘id’ and accept ‘…’ as arguments.)

    i think this is the problem as its related to the download of the feed.
    any help?

    thanks

  • @ Adrian (Comment #45), if I want to put the activity indicator in the middle of the screen instead of top-right like you did, how would I do that?

    Thanks in advance!

  • If I want the articles to appear inside the app rather than actually opening in safari how do I go about doing so?

  • You’ll have to build this application within a UINavigation Controller and then “push” a new view that has a UIWebview component. If you find some tutorial on how UINavigation works you should be able to combine this with what you’ve learned. Good luck!

  • URL Encode links before passing to Safari:

    storyLink = [storyLink stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

  • Excellent article and very helpful comments as well. Perfect for a beginner level iPhone dev. Thanks a lot!

  • Very nice but i get an error code no 5 when i launch the app…any ideas???

  • Does anyone know how to make this app NOT take out the “&” for the links? I have an RSS Feed that uses an “&” in the link and once the user clicks on the news headline to read more, it points to an incorrect address b/c the code removes the “&” symbol that is need to point to the correct link in the link address. I am not talking about the RSS feed address, I am talking about the news headlines links within the RSS Feed.

  • Perfect example to learn and then build upon. Many Thanks. Matt

  • For a faster interface use a NSURLConnection to create an Asynchronous connetion and call the parse method after the NSURLConnection has downloaded the whole file, the parse is Synchronous and block your interface, so in this way you reduce that time needed to show the parsed file.

  • You will get the:

    ‘RootViewController’ may not respond to ‘-parseXMLFileAtURL:’

    warning unless you move the parseXMLFileAtURL method above the call to that method. Its an annoying warning but the app works fine they way it is written.

    Thanks for the code!

  • Matthew #107

    You need to add:
    [cell addSubview:textView];

  • What the hell is an iphone?

  • how do i open up a webview instead of safari to display my feed? If I use safari, that will force my users to exit my app. Please help!!!!

  • I’ve been reading else where that this is obviously a work around.. does this mean that apple would reject if submitted in a new app?

  • This is sweetah! Can anyone offer some assistance on calling/searching for videos and them playing them in your application? When finished with video it returns to the app. Thanks in advance. FYI: have average obj-c knowledge, call myself a educated beginner.

    • @Levi: Have you looked at the MediaPlayer framework? It offers a media picker and a movie player that do pretty much exactly what you asked for.

  • Is there a way to get this to work with URLs that begin feed: instead of http: ?

    I can only seem to get NSURL to work with http:

  • Using iPhone, I would like to create an XML file with an Image included within.

    For Example, SUkq …..

    Any direction would be appreciated.

  • “SUkqAA++++”

  • Sorry, my example is being filtered out. I want to use “b i n . b a s e 6 4″

  • One more addition to updates to improve memory management:

    in didStartElement make sure to do a check and release before the allocs, eg:

    item = [[NSMutableDictionary alloc] init];
    if (currentTitle) {
    [currentTitle release];
    currentTitle = nil;
    }
    currentTitle = [[NSMutableString alloc] init];
    if (currentDate) {
    ….

    etc. After that, and the other updates mentioned I don’t see any more leaks in a quick run through Instruments.

  • Hi, thanks for the great tutorial.

    I’ve got it to work but there’s this weird problem where the parsed RSS items appear invisible in the table view. I see an empty table, but when I click on the rows I’m taken to the Safari page. What’s going on?

  • Did you test your code in Instruments?
    As I can see this code will generate a lot of memory leaks, specially when dealing with the NSString objects.

    []s

  • hey how can I limit the number of entries?
    I just want the last 20 posts, because it would take much too long to parse all my 200 entries!

    thank you

  • Hi,
    Thanks a lot for a really helpful tutorial. I just have a question which I would really appreciate if you could answer. How do we add a webview to display the item link in the new webview and not in the safari?

    Many thanks

    Khalid

  • Why doesn’t this work with feeds beginning with feed:// instead of http://...

  • Folks, don’t use this for anything serious. It’s just to test the waters. Look into TouchXML for reliable (leak-free) XML/RSS work.

  • Tried this a few times, it loads but doesn’t display any items. Tried several diffrent RSS feeds including the one included in the code and it simply does not work. What gives?

  • I tried this a few times, it loads but doesn’t display any items. Tried several diffrent RSS feeds including the one included in the code and it simply does not work. What gives? …

  • Fixed some of the errors and now it displays fine.

  • Even though this is totally unrelated im wondering if ne one knows how to update a UItableView, while still on the same view the table view is on, after it parses information. What i did was in my parsers didEndDocument method i called [myTableView reloadData]; so at the end of the document it will call the reload data method , but its not working and ive been trying so many combinations of code in this method for the past 4 days and still no luck so ne one can help me it would be awesome

  • Can u do it without using xib file…?
    i mean directly using program……?

  • Hi from Spain,
    thank you so much, I can see now the RSS of the page in my simulator :D

    But I have a problem, this page has spanish characters like “ñ” or “á” which isn’t show correctly in the simulator. How can I do to see correctly the characters?

    (sorry if my English isn’t very good)

  • Hi,

    This is Great one! though i didn’t yet to test, but going to be soon…

    Have two questions to Mr.Jason Terhorst.
    1. Will it work this on latest SDK too? (or) To have such thing(Every day news page) with latest SDK development, is there anything else method is available instead of above code?

    2. Once we got the results on the table, tap on an item in the table will launch browser show the history? Why is that? If i want to show stories in my application view itself, what should i do? Step by step procedure please.

    thanks.

    Calve/

  • great work mate, but i keep getting an error
    warrning rootviewcontroller may not respond to ‘-parseXMLFileAtURL:’
    any thoughts

  • Do any of you actually read any previous questions asked/answered before posting a question that has to be reiterated 70 times?

  • It was great.
    Thanks man.

    Although you might want to update it, as some things have changed in the newer SDKs.

  • Great job! I really appreciate the time and effort you have put in for all of our benefit. I got it running OK on the simulator; I tried to load to my iPhone but I think I have it too full – not enough memory. I have never gotten it to load into or even bring up Safari. I don’t have a clue since this involves so little code itself!

    Keep up the good work! Don’t let the detractors discourage you; they, for the most part, seem to lack initiative, or in some cases, decency itself. Ignore them! Thanks again, Ed

  • I tried your code and up came Safari! I will study it all in the AM and see what I did wrong!

    You should be very proud: it’s over a year ago you posted this and it’s still helping many of us!

    I am proud of you, too!!!

    Thanks again,
    Ed

  • ne marche pour moi j’ai cette erreur

    RSS/Classes/RootViewController.m:186:0 /RSS/Classes/RootViewController.m:186: warning: ’setText:’ is deprecated (declared at /Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator3.1.sdk/System/Library/Frameworks/UIKit.framework/Headers/UITableViewCell.h:200)

    aidez moi please

    what i did do wrong help me please…and thank you for your gread job!

  • Hi,

    Everything works great, thanks. However, I have a problem displaying the summary.

    When I display a 3 line description under the title (I just put the summary into a UILabel) the texts come out encoded.

    For example this text: Here is a “quote”

    Will be displayed: Here is a &#8220quote&#8221

    Any ideas how to fix this?

  • Я никогда не сомневался в Ваших интеллектуальных способностях, но поймите, не все такие как Вы. :)

  • Thanks for the tutorial, it was a great way to get started. We all need more of these on the web. Great work.

  • Hi,

    I can’t get it to parse the CDATA. What can I do about that?

  • Brilliant,
    I was looking for something like this, I wish you had a video for this tutorial.
    Well done. Looking forward to see more from you.

    Cheers

  • Great tutorial, though for some reason it doesn’t seem to be working for me. Tried rebuilding myself and the flipping change of content wasn’t working, then I downloaded the source and popped that up on my server and the same thing: no change when the phone flips.

  • Hey Its working..Thank You

  • Check out http://www.TBXML.co.uk for a super-fast, lightweight XML parser!

Linkbacks (0)

Subscribe to the comments feed

Leave a Reply