Object-C – Singleton

Singleton is a design pattern that guarantees that only a single instance of a class exists at any time. Singleton classes are good for Models and Datasources. The singleton is a great partner with a UITableView as the datasource for the tableview.

In the header file declare a class method that will return the shared instance. The shared instance is the single instance of this class that will exist. This method is also responsible for creating the new instance the first time the method is invoked.

+(id)sharedManager;

Define this method in the implementation file.

+(id)sharedManager {
    static Things *sharedThings = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedThings = [[self alloc] init];
    });
    return sharedThings;
}

In the sharedManager method declare the variable sharedThings as static. A static variable remembers its value across invocations of a function. That is, the value is set the first time the function is called, and that value is “remembered” the next time the function is called. Normally you would expect that the variable would be forgotten on each subsequent invocation.

The dispatch_once guarantees that the block is contains is only executed once. In the example sharedThings should only be created once, the first time sharedManager is invoked.

The last step is to return the sharedThings instance.

Cocoa – UITableView

These are a  few notes on creating the UITableView. Understand at the time of writing this, I’m a total beginner, so take everything here with a grain salt, and an once of skepticism. The purpose of writing this is to settle subject in my own brain.

As part of the MVC pattern UITableView is a View, so a table view knows how to draw itself. A table view typically needs a view Controller to manage it. A table view always needs a data source. The data source supplies, the number of section, rows, and the content for each row. Typically a table view needs a Delegate. The Delegate handles events generated by the table view.

An instance of the UITableViewController class can handle the role of Controller, Data Source, and Delegate. The UITableViewController, as a view controller, manages a view and this view is always a UITableView.

Any class that manages a UITableView must be a UITableViewDelegate. The data source for the UITableView must be a UITableViewDataSource. These are often the same class, I’m guessing  they don’t have to be.

@interface ViewController : UIViewController <UITableViewDelegate, UITableViewDataSource>

@end

This is the UITableView Protocol

To display the UITableView these requirements must be met.

UITableViewDataSource

This protocol requires two methods be implemented:

-(NSInteger)tableView:numberOfRowsInSection
-(UITableViewCell *)tableView:cellForRowAtIndexPath

These two methods tell the UITableView how many cells to work with, and give you the opportunity to populate and configure the UITableViewCells.

Giving the table view the number of rows in a section allows it to get data via the index of that row. Without having to contain the actual data. Essentially tableView:numberOfRowsInSection tells the table view how many cells you will need to work with. When comes time to display a cell, the table view calls on tableView:cellForRowAtIndexPath passing the index of the cell, this function returns the cell; and within this function you populate and configure the cell.

-(NSInteger)tableView:numberOfRowsInSection

This method is relatively simple. It returns the number of cells in the table view. If you were using an array you might implement it in this way:

-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return [array count];
}

– (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

The cell For Row method is more complex. Here is where table cells are created, populated, and configured. The table creates cells only as needed. It only creates enough actual cells to fill the screen. As cells scroll up the page they are recycled and repopulated with new data, with the tableview keeping track of which index is currently visible. This process makes the system much more memory efficient, since the computer holds only a limited number of cells in memory. Imagine your iTunes library with 500, or 1000, or more songs. The table view is really only working with enough cells to fill the screen, maybe 10. If the computer to generate 1000 or more table cells, it would slow down, and become unresponsive. Using this system, the table view is recycling a limited number cells like an escalator, changing the content as the cell moves off the top of the view and reappears at the bottom of the view.

You might implement this method as:

-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    static NSString *simpleTableIndenitfier = @"SimpleTableCell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:simpleTableIndenitfier];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:simpleTableIndenitfier];
    }
    
    cell.textLabel.text = [recipes objectAtIndex:indexPath.row];
    return cell;
}

Here the dequeueReusableCellWithIdenifier asks for an available cell from the table, which is stored in cell. If cell is nil, no cell was available, so a new cell is generated. In this case the cell is generated using the UITableViewCell alloc. Then initialized with initWithStyle. Here we tell initWithStyle to use one of the default cell styles UITableViewCellStyleDefault.

– (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView

This method tells the table view how many sections you will using. Be sure to set this to at least 1. The default implementation of this methods is set 0.

Storyboard and outlets

To connect a tableview created in storyboard to it’s view controller’s outlets, Control drag from the tableView to the view controller and choose dataSource. Repeat the process for delegate. You want the Outlets dataSource and delegate to read ViewController.

Apple HIG – Branding

I see many apps that look like web sites. These often feel the need to brand themselves with a logo and company name in the title bar. Or they present the company logo in a splash screen.

An app is not a web site. Apps are small focussed pieces of software. They live on a mobile device, and in that environment they act in a more personal and intimate role. The icon alone should brand the app. Making the conscious decision to launch an app you know what you are looking at.

Here’s a quote from the HIG:

Incorporate a brand’s assets in a refined, unobtrusive way. People use your app to get things done or be entertained; they don’t want to feel as if they’re being forced to watch an advertisement. For the best user experience, you want to quietly remind users of the brand identity through your choice of font, color, and imagery.

Human Interface Design Guidelines

Apple published a book called the Human Interface Design Guidelines. This covers everything about how to design computer interfaces. I had a print copy some years ago. You can now read it online. It covers everything from color to working with text in different languages.

Apple has also written an IOS version. Here is a great quote from it.

Deference. The user interface helps users understand and interact with the content, but never competes with it.
Clarity. Text is legible at every size, icons are precise and lucid, adornments are subtle and appropriate, and a sharpened focus on functionality motivates the design.
Depth. Visual layers and realistic motion impart vitality and heighten users’ delight and understanding.

Native or HTML5?

Native or HTML5?

Starting a new project, you’re likely to explore what would be the correct platform as a first step. Javascript has a lot of buzz right now. There seems to be a movement to do everything in the Javascript language. At the moment you can Write your app with JS, script your server with Node.js, query your data base in JS using MongoDB. Wow, sounds like you can do it all in JS! This is neat but, I feel it’s important to not lose sight of the forest through the trees. In any project it’s really about choosing the right tool for the job.

If we’re doing everything in JS does that mean the browser is the new OS? I don’t think so. There’s a bit of the emperors new clothes in this type of thinking. The thing about JS and apps in the browser is they just don’t live up the promise in many cases. Or, maybe I should say that there is to much promise. JS has a lot of hiccups and performance issues. Writing a program across HTML, CSS, and JS has a lack of elegance, and feels crude and verbose at times. Just because you can do something doesn’t mean you should. Again it’s about choosing the right tool. The big draw of JS for everything is that it leverages a common tool set, on a common platform. This can save time and money which is good, but if you are making an inferior product is it worth it?

I don’t want to sound like I have some axe to grind. I’ve had a lot of fun with JS, and if it’s the right tool for the job I’m more than happy to use it. My point is HTML5 has so much hype people are treating it like it can do no wrong, like its the wunderkind that can do anything. I just want to get real here. JS can do anything, and I suppose that’s a really a great thing. But, just like people, JS is good at somethings and not good at other things. I’m a firm believer that anyone can do anything if they put their mind to it, I’m not saying that everyone can break world records.

There’s a lot to like about writing code in one place using a common set of tools and deploying to every platform. But if the app provides weak and compromised user experience do you want to put your name on it? Look at Facebook. They had an HTML5 app, and the user experience and performance was weak. The way I see it, they essentially shoehorned a web site into an “app”. They obviously bought into the promise of HTML5.

“The biggest mistake we’ve made as a company was betting on HTML5 over native”

M Zuckerberg

It’s fun to think you can recreate all of the nifty transitions and animation of a native app with JS in a browser. But, you’re not really doing your job unless you apply a critical eye and are willing to say that something is falling short of expectation. Kudos to Facebook for owning up to a problem that was theirs.

Is the browser the new OS? Computers are getting faster, and JS can do more in the browser than ever before. But I don’t think this makes JS the be all end all. There will always be something you can do native that will be out of reach from the browser. Either for security, performance or other reasons. The world may spend more time in a browser than all other apps combined but, I don’t want to edit images in Safari, and I don’t think this is where the world is going.