Mike Rundle of flyosity.com recently posted an article, Making Rounded Rectangles Look Great, on designing rounded rectangles, some design techniques, etc. I recommend you to check out the post and download the PSDs for great inspiration!
I’ve recently worked extensively with re-engineering and re-designing the UX and UI for an online retailer, which involved a lot of paper, Photoshop and CSS (or Sass).
I thought it would be cool to create the buttons from Mike Rundle’s article in pure CSS, so I went ahead and did it. Before checking out the CSS buttons, be sure to check out Mike Rundle’s examples and PSDs for a comparison.
I tried as much as possible to stick with the same colours and transparencies as Mike Rundle’s examples, although there may be slight differences, depending your display and browser.
I’ve also added :hover and :active states to all the buttons, so they’re a bit more exciting. Unfortunately CSS doesn’t provide a simple way to create a masked gradient at an angle, so the Convex example is probably the least similar one. But it still looks great and I wanted to stick with all CSS – could have been achieved with an image mask or simple overlay.
You can check out the result on a separate page. Feel free to grab this .zip containing all the project files: Rectangles.zip.
Accessibility on iOS provides visually impaired iOS users the ability to use an awesome touch screen platform to its full extent. It’s your job as an iOS developer to ensure your app works wonderfully with Accessibility on iOS.
When considering adding features or optimizing your app for Accessibility, don’t assume we’re just talking users who are completely blind. And despite being all iOS being full touch screen devices, there are lots of visually impaired users outthere, ranging from users who are blind, hard at seeing or colour blind, for example.
Apps, such as Mail, numerous Twitter clients and more include the possibility of changing text on the screen to a larger font size. Matt Rix‘ Trainyard includes an option for players who are colour blind. These are just a few examples of improving apps for Accessibility.
Also consider interaction. While a scroll requires just a flick with one finger for regular use, having VoiceOver enabled scrolling is done with a three finger swipe, and moves the UIScrollView (and any NSObjects that inherit from UIScrollView) a page at a time. So while a pull-to-refresh is awesome, for user with VoiceOver enabled, it might not be as apparent or ease to use.
In this post, I will focus a bit on optimizing your app for VoiceOver. Before continuing with this post, check the video below where a blind user shows off VoiceOver and demonstrates how to use it.
I also recommend enabling VoiceOver on your own device and playing around with it for a while, just to get familiar with it. One thing is to know about it and use it with the Accessibility debugger turned on in Simulator, another thing is to experience it for yourself!
While most of UIKit works fairly well out of the box with VoiceOver, there are plenty of things you can do to improve how your app works with VoiceOver. If you’re doing any custom UI (especially drawing) VoiceOver will most likely not work, or it may speak out the names of the object. So if you call a custom UIButton “createNewTaskButton,” that’s what it will say. Instead, it should probably say “Create New Task”.
Consider your own app(s) and what use visually impaired users may have of it. I made a transit app, so it was only natural to optimize it for visually impaired users and add custom and improved VoiceOver support. With VoiceOver enabled, users can tap the time until the next transit vehicle arrives and the device speaks out in plain English “Next TTC vehicles arrives in 5 minutes and 32 seconds. Tap again to hear updated time.” If I had not customized it, it would have just said “5:32.”
Underneath are subsequent vehicle arrival times. As you can see from the Simulator screenshot, without VoiceOver optimization, the device would just say “20 min bullet 25 min bullet 26 min.” With Voice Over optimization, it says “Subsequent TTC vehicles arrive in 15 minutes (pause) 20 minutes (pause) and 25 minutes. Tap again to hear updated times” Notice the (pause) and look at the screenshot. VoiceOver speaks pretty fast, so if you would like a bit of a pause, just insert a period, and it will pause a bit between the words. This is a great way to split up important information.
Also notice how it will say “and” for the last arrival time. If there are more or less times, it would only say it for the last item. Remember attention to detail in these cases. If someone was to tell you the information for what you touched on the screen, how would you best understand it? There’s a huge different between spoken language and UI. Keep this in mind!
For the buttons with which users can change a route, the label would look like this “506 • Carlton.” In this case, the literal VoiceOver sentence would be “506 bullet Carlton.” So I went ahead and customized this to “506 Carlton,” so it wouldn’t speak the “bullet” part of it. For the custom UIButton where the user can add or delete a route/stop selection to their Favourites, I added “This is a favourite. Double tap to remove from your favourites” and if the selection is not a favourite it would say “Not a favourite. Double tap to add to your favourites.”
If you’re doing any custom drawing, for example as I have done in the example on the right, you will need to pay extra attention to VoiceOver optimizations.
For flat, drawn views, VoiceOver cannot access any of the text or other information on screen. In this example, I draw each cell, so there are no UILabels or UIImageViews for VoiceOver to recognize and speak.
I therefore set the accessibilityLabel property on each cell which then provides VoiceOver with information about what to say. As you can see from the example, according to Accessibility Inspector, VoiceOver will say the route number and name, and because the item is a current selection, I also made sure VoiceOver lets the user know about this by saying “Current selection” after the route number and name.
For non-VoiceOver users, the checkmark is a great visual marker for the item being a current selection. But for VoiceOver users, this would have not been the case. Especially since it’s a custom drawn view, VoiceOver has no clue about the checkmark. In your Accessibility optimization, not only consider what VoiceOver would say, but also consider the UI and what VoiceOver can see, or should see that is related to the item the user it touching.The user may not know about a certain UI object or visual marker without VoiceOver telling them.
Accessibility Inspector in iOS Simulator is a great tool to help optimize your app for full VoiceOver support. Tapping the X button disables the Inspector and hides most of its UI. This enables you to see the app without VoiceOver enabled to quickly get to the content you’re currently debugging for VoiceOver, or since VoiceOver scrolling requires three fingers, it will allow you to scroll when you disable it temporarily.
While Accessibility Inspector shows what VoiceOver will say, you should again test on an actual device with VoiceOver enabled. As mentioned, one thing is how something looks and “sounds” when it’s written, another is how it sounds when VoiceOver speaks it.
So these were a few of the consideration I made for one of my apps in optimizing it for full VoiceOver support. For more on the subject, I urge you to read Apple’s Accessibility Programming Guide for iOS, which gives a more detailed overview of the possibilities as well as more in depth examples and usage guides.
Furthermore, Matt Gemmell has written a great post on it as well with more details on Accessibility properties, among other things, and it’s totally worth checking out.
I picked Core Location since I had learned some good insight at WWDC and also worked with the framework thoroughly through building my app Next TTC.
The presentation went well and was well-received, and I am now posting it here for everyone else to enjoy. I have left my notes in the presentation, but I am not sure how much help that will be. I suggest you view the presentation in Play mode, just so the animations help understand the content a bit better.
For this week’s #idevblogaday post, I’ve written a small utility app that’s freely available for download on github.
ColorKit is a tiny iOS app (iPhone) which allows for quick and easy color-sampling for a UINavigationBar + UIToolBar. It allows developer to easily assess the appearance of tintColor on the device.
Last week, I talked about adding textures and depth in your app, in particular to a UINavigationBar. While this effect is great when used appropriately, UINavigationBar’s tintColor property is extremely handy and useful to give your app a unique look with one line of code.
Finding the right colour for your app can be a bit of a hassle, especially due to differences in colour appearance depending on which monitor or device you’re using. Furthermore, UINavigationBar and UIToolbar are coloured with a gradient and has a glossy shine, so knowing exactly which RGB value to use is often impossible.
ColorKit builds and runs right on your iPhone and makes it extremely easy to quickly play around with various RGB settings to find the perfect colour for your app.
Inside the app is a UIImageView which allows you to add a screenshot from your app to better see how the colours may look with your UI.
Pro-tip: Do not use bright colours. Play around with the values to create more “faded” colour. Brighter colour wash out the title text and generally look horrible.
I was expecting this blog post to be about something completely different, but I’m still out of the country and have come down with a bad cold, so it’ll be a bit of a short and simple.
I’ve decided just to a few coding tips, I have come across and though might be useful for other devs, especially if you haven’t worked much with UIKit before in your development, or perhaps just these areas below. (At the bottom of this post is an Xcode project file which includes examples of the tips below).
Tip #1: Check for URL scheme and open correct app from your own You’ll probably run into having to link to another app, for example your company’s Twitter account. Instead of just linking to the Twitter website, you can do a quick check in code and open the Twitter app instead. You can also do it with other Twitter client apps as well, however, not all have URL schemes setup (that I could find), and most users will probably be using the official one anyway. Regardless, the code is good to do the same check for other apps, or if Twitter.app doesn’t exists on the user’s device, you can try another Twitter client app, or use a UIAlertView to ask the user what else they’d like to use (depending on which ones are possible to open using the URL scheme).
Basically, all you have to do is ask whether UIApplication responds to the URL:
Tip #2: Getting a free UINavigationController in your UIViewController I have seen some apps that use a UIToolbar as a navigation bar, and this just doesn’t work. If you compare the two, they’re actually a bit different, and this really shows when put in the wrong place.
If you’ve got a UIViewController, turning it into a UINavigationController is really easy:
Tip #3: Getting a free UIToolbar in your UINavigationController This one I only just recently found out (thanks to @auibrian). UINavigationController actually comes with a UIToolbar. It’s property is set to hidden:YES by default, so all you have to do is override this property when you load the view.
[self.navigationController setToolbarHidden:NO];
Note: I have seen some weird behaviour when pushing view controllers onto the screen (buttons not getting a pushing animation, just appearing in the toolbar in place). Also, you will need to hide the toolbar if you’re popping or pushing to a view controller that you do not want to show the toolbar (because with pushing you’re reusing the same navigation controller). In my opinion it’s not a very good way, I wish the view controllers were more separate for this.
Tip #4: Use shadowColor and shadowOffset appropriately when faking text indention
One thing that bugs me are improper use of a UILabel’s shadowColor and shadowOffset. When using these, one has to pay attention to the colour of the background as well as the text colour. In the below example (when we’re going for the look where text looks carved into the display, used by Apple across the entire UI), we’ll see that when using darker text, use a lighter colour for the shadow and a positive value for the offset.
When displaying lighter coloured text, use a darker shadow colour and a negative value for the offset, which in both cases create the proper indented or “carved” effect.
Using the wrong combination doesn’t create this effect and makes the text appear raised from the rest of your UI, which is most likely not what you should be going for in most cases ;)
I’ve made a small Xcode project you can download here, which has the code examples from tips 1, 2 and 3 and I suppose #4 as well, since navigationItem.title is using text indention.
Again, apologies for a bit of a short and simple post due to being under the weather and traveling.
iPhone 4 will make your UI look stunning. Everything in UIKit has been scaled up already so it will require only a bit of work on your end to make the rest of your app look amazing on iPhone 4. If you only code and don’t touch Photoshop, you’re in luck. However, if you’re a UI designer or have the skills to do your own UI, hopefully you did your original artwork in a nice high resolution – if not, you have a bit of work cut out for you with updating all the UI elements to 2x the resolution.
Updating your app’s UI to be compatible with iPhone 4′s Retina Display is amazingly simple. Since the scale works in points, not pixels, you will have to do very little work on the layout itself. Apple Engineers have made it really simple to use new graphics for all your UI on iPhone 4, at the same time as being compatible (and not using 2x memory) on older, lower resolution, lower memory devices.
All you have to do is add the same image file at 2x the pixels to your app’s resources and name it the same it’s lower resolutions sibling with the following suffix: “@2x”.
For example, in your Resources folder, you will now need to have two image files, one for older devices called myImage.png and one for iPhone 4 called myImage@2x.png, which is twice the resolution.
This way, when you call [UIImage imageNamed:@"myImage.png"]; (or contentsOfFile:) iPhone 4 will automatically grab the filename with a @2x suffix, and lower resolution images will grab the lower resolution copy. You don’t have to check for the device loading the image and write any additional code to grab the correct image. Genius!
If you have seen an iPhone app on the iPad in 2x scale, that’s pretty much how your app is going to look on the iPhone 4. Perhaps not so drastic, but there will be a noticeable difference from app not optimized for iPhone 4 and “Retina Apps” as Apple calls them.
Thoughts on @2x on iPad…
I didn’t hear anything at WWDC regarding this, but my thought is that they’ll integrate this into the iPad for the next major OS release. Basically, it will be able to do the same and grab the higher resolution image appropriately for iPhone apps running at 2x scale.
Happy Photoshopping to UI designers and happy relaxing programmers!
UPDATE JULY 7, 2010:
I have discovered a bug in Apple’s code that deals with grabbing the correct image on iPhone 4. If you are using imageWithContentsOfFile: the code will in fact not automatically grab the @2x if running on iPhone 4. I have submitted a bug report to Apple, and they’ve informed me they are now aware of the issue and the Engineers are currently working to fix the bug. So for now, stick with imageNamed: for all your images.
I am implementing Push Notifications in one of my apps. Doing so may be a bit tricky in terms of debugging since you cannot actually debug incoming Push Notifications appropriately while the app is running, so I wanted to share this tip. Also, I am writing this post on my iPad on an airplane, so pretty excited about that :)
Xcode allows you to debug applications that are running locally on your device. You can even set breakpoints in your code and print out any information you may need from the console in order to debug your app and fix whatever issue you’re experiencing, should you not be able to fix it via “live” debugging.
This feature is especially useful if you’re doing Push Notifications (a great way to easily communicate information to your user with their permission, such as notifications, reminders, marketing (be careful with this one), etc.).
With Push Notifications, your app receives data from Apple Push Notification servers in a dictionary in the UIApplication delegate application:didFinishLaunchingWithOptions: that you’ll need to parse and do in your app whatever is appropriate for the implementation you’ve chosen (launching with specific views in front, etc.). Since your app cannot be running while receiving Push Notifications (it actually does receive notifications while running, but you’re required to deal with that through another delegate method), you’ll need to use the “debug executables” with “Wait for next launch/push notifications” ticked. Once you run the debugger and launch your app (for example directly via a Push Notifications UIAlertView) you can set breakpoints anywhere in your code and use the console to print out (po) any objects you may wish to inspect.
As your app launches immediately when you debug, it’s a problem if you’re debugging Push Notification (which, by the way, does not work in Simulator). So here’s the hidden treasure in Xcode: In the Groups & Folder pane, find Executables, expand and select your app executable. Hit command+option+i to “Get Info” and select the Debugging tab. From here, tick “Wait for next launch/push notification”.
Now, when you Run & Debug your app it will not launch, but instead wait until you tap the app icon to launch it or the app is launched via a Push Notification UIAlertView (this of course requires you have not set the “action-loc-key” to null in your Push Notification JSON dictionary).
Once your app launches via a Push Notification, it will stop at the breakpoint you set and you can now print out any information you need to debug your app, such as the NSDictionary your app receives, whether the appropriate view will be displayed and any other issue you may have.
UIView animation is a simple and nice way to add to your user experience. I just wanted to point out a few suggestions when using UIView animations.
Duration (speed):
If you choose to use animation to compliment some of the stuff already happening in UIKit, either at the same time or before/after, it makes a big difference how fast your animations are. Pretty much all the UIKit animations I have come across have a duration of 0.3f and so should yours. Of course, it’s doesn’t always work 100% but for the most part, 0.3f is what you should aim for. It’s quick so your user don’t wait for something to finish animating before continuing with the next input action, and it’s not too fast so that the user doesn’t have a chance to see where the object came from or what happened.
If you have an animation happening while the keyboard animates up or down, use an animationDuration of 0.3f. Same with pushing and popping the navigationController. Annotations in MKMapView also drop at a duration of 0.3f.
0.3f is the way to go.
A simple UIView animation can be added with the following code:
The above example is from an app I’m doing, where the segmentControl is enabled and I increase its visibility in the toolBar at the same rate as a pin drops in the map within the same screen.
When to use animation:
A few objects come with free animation (also at a duration of 0.3f, of course). For example, when adding a UIBarButton to your UINavigationBar, consider setting these with animation. If you replace a UIBarButton with another, they’ll even animate in and out nicely during the change. When adding a pin to a map, why not drop it onto the map with an animation, instead of it suddenly appearing on a map from nowhere?
Another good advice is to do animation (whether your own or with objects that include animations) to bring attention to an object. For example, if you have a pushed view, consider what you can “add” after the view has appeared through animating your objects in viewDidAppear.
Create a better UX with animation
Consider all the ways you can use UIView animation blocks in your app to enhance the user experience. It’s a great way to create a more fluid and pleasant experience for your users. A user’s inputs and actions will feel less rough and more smooth and soft to the touch. Don’t go overboard with animations. Too many will become annoying and it’s important to use animations only where appropriate.
The best advice is probably to have a look at many of the built in apps designed by Apple as well as the many free animations that a part of UIKit objects (how UIBarButtons animate in and out when you push a UIViewController stack, how a modal view appears from the bottom, etc.).
Ever noticed an app where the UIActionSheet’s bottom button doesn’t want to respond to your taps, unless you hit exactly in the top of the button? If you have a UITabBarController and want to display a UIActionSheet, you have to be careful with what view you show the UIActionSheet in.
If a UIActionSheet is shown in “self” or “self.view” and you got a UITabBarController behind it less than half of the last button will respond to taps:
I have received some feedback regarding this post that I thought I would share:
One developer implemented this feature in a UIAlertView pop-up, asking users nicely if they’re enjoying the app and whether they would like to be taken to the App Store to review the app. This UIAlertView happens after the 10th app launch, so you’re already dealing with people who have used your app enough that they must be liking it. It’s a $0.99 app by the way.
In just two short hours after implementing this, he had received 6 new app store reviews, all with positive feedback along with 4 or 5 stars, nothing less!
What can we learn from this?
1. People are, by nature, lazy. Consider the steps required to actually reviews an app that you like: You have to actively find it again in the App Store, scroll down and go to the review page. Then tap the button to submit your own review, login, etc. Unless someone’s super excited or very pissed off about your app, you will only see a small percentage of people taking their time to go through all those steps to review and rate your app. By asking users, who’ve been using your app more than just a few times nicely for a review, then linking *directly* to the App Store, they’re already skipping many of the above steps and rating and reviewing your app becomes a quick activity related to an app they’re enjoying.
2. Reviews are generally positive. Ratings on the other hand tend to be more black and white. Either people hate your app, delete it and quickly give it 1 star. I doubt a lot of people give apps 4-5 stars when they delete an app. They’re deleting it for a reason; either they didn’t like it, or it just wasn’t what they needed/expected. If they like the app, chances are they’d never delete it, and you wouldn’t be getting those great 4-5 star ratings (refer to #1). I have seen reviews that have pointed out several wrongs about apps, but they’re still adding a 4-5 star rating with the review. It may seem there’s a difference in people’s mind about a review and a rating. I think a lot of users think of reviews as a way of communicating to the developer that there’s an issue with the app, or they want this or that added, but they still use and love the app regardless (giving it a high rating).
3. You’re asking the right users. When deleting an app, Apple has implemented a horrible UIAlertView asking the same people who just got rid of your app to rate it. I think we all agree this is ridiculous (refer to #2). With a UIAlertView inside your app for 10+ launches linking into the reviews of your app in the App Store, you can pretty much assume these people are enjoying the app, especially if they agree to review it. If they’re don’t like it that much or don’t have time, it’s just a simple tap to dismiss the UIAlertView.
ORIGINAL:
Today @coffeeandiphone we briefly discussed ratings/reviews for apps, and one person mentioned he’d like to show some of the users who have used his app more than X amount of times an alert where he’d ask them to review his app in the app store.
So here’s a link that will take people directly to the review section of your app in the App Store. Note, though, they won’t be able to go “Back” to the actual page for your app in the App Store (when on a device), so they can’t really see that they’re on the review page for your app. Therefore, you probably want to make it veryclear where your linking to and before sending them out of your app, into the App Store.
See where is says “?id=341136260″ ? That’s the only thing you need to change. Just insert your own app ID there and you’re good to go. Don’t get confused by “type=Purple+Software&mt=8″, because if you change that, it won’t work for some reason. I am not quite sure why it has to say Purple Software, but I don’t really care as long as it works :)
Combine it with something like this (“Fighting Back Against The App Store’s Negative Rating Bias”) and you’re good to go!
Edit: I can’t remember where I got this info from, but credit goes to whoever/wherever, of course.