Why Leopard is taking so long

As we learnt yesterday, the release of Leopard will be delayed until October (i.e. 4 months after the end of “Spring” when it was originally slated to ship). Along with this news, developers also received a further development build of Leopard, 9A410, which, according to AppleInsider, ships with a list of almost three-dozen known issues, which are listed here. For the purposes of this post, I’m going to ignore the one or more “top secret” features that are supposed to appear in the final Leopard release and talk about why I think Leopard is taking so long, based on what we know (with a sprinkling of what we think we know)…

What Leopard will bring

Unless Leopard goes the way of Vista and drops support for any of the massive headline features, there will be a huge number of technically-challenging changes in Leopard that push Mac OS X even further ahead of its competitors. So let’s have a look at some of the major ones…

Objective-C 2.0

Welcome to Cocoa 2.0. Objective-C is receiving an overhaul in Leopard. This is not a minor undertaking by any stretch of the imagination. The greatest change is the introduction of garbage-collection, which frees developers from the tedium of manual memory management. Also being added to Obj-C is fast iteration (allowing, for example, traversal of an NSArray without first obtaining an NSEnumerator). Basically, this will reduce this code:
NSEnumerator *enumerator = [myArray objectEnumerator];
NSString stringFromArray;
while (stringFromArray = [enumerator nextObject]) {
NSLog(@"Array content: %@", stringFromArray);
}

to this:
for (NSString *stringFromArray in myArray) {
NSLog(@"Array content: %@", stringFromArray);
}

Nice. Rather brilliantly, Obj-C 2.0 will also introduce “declared properties”, which removes the need to explicity declare methods to access and set properties of your objects. Instead, one simply declares the name of the property and whether it is read-only or also supports writing. Accessing these properties will also be made extremely simple. This:
NSString *name = [myObject getName];
will become, with an appropriate change of the accessor method name, the considerably more readable:
NSString *name = myObject.name;
These changes are very welcome and if, for some reason, you’d rather not use them in your app, they are all opt-in — the Obj-C 2.0 compiler is backwards compatible with Obj-C. So how could this cause a delay in Leopard? I would (perhaps naïvely) imagine that Apple has opted-in to the Obj-C 2.0 runtime for at least some of its programs. We know, for example, that XCode 3.0 takes advantage of garbage-collection. I imagine that, upon rewriting a program to utilise garbage-collection, there is a lot to potentially go wrong, as old memory management code is removed and handed over to the garbage-collector. It’s also possible, although virtually inconceivable at this stage in development, that a problem was detected in the garbage-collector.

Pervasive 64-bit

This is another huge change. 64-bit programs run just fine in Tiger — as long as they’re confined to the UNIX layer. Any UI work had to be either CLI only or through a 32-bit wrapper GUI that communicated with the 64-bit backend. This has all changed in Leopard, which brings LP64 (64-bit Longs and Pointers) support to all application frameworks (except for QuickDraw, Sound Manager and the low-level Quicktime APIs, all of which have been deprecated). Not only this, but there is no 64-bit “mode” in Mac OS X as everything is completely backwards compatible. Programs, frameworks, scripts and even drivers may intermingle with one another, utilising either 32- or 64-bit registers on either PowerPC or Intel processors. Quite an achievement, especially 32-bit driver compatibility, which is something that Windows 64-bit hasn’t yet managed to master.

Why might the addition of pervasive 64-bit frameworks have slowed down Leopard development? Well, adding 64-bit support to all the application frameworks while maintaining backwards compatibility isn’t quite as straightforward as substituting all your ints for longs. Apple has been rather cunning about this whole affair and introduced NSInteger and NSUInteger (U for unsigned) and done the following:
#if __LP64__
typedef long NSInteger;
typedef unsigned long NSUInteger;
#else
typedef int NSInteger;
typedef unsigned int NSUInteger;
#endif

Then they’ve gone through and replaced all unsigned ints with NSUInteger and all ints with NSInteger. Incidentally, they’ve also switched floats to doubles when running in 64-bit which, in the true spirit of “64-bitness”, greatly increases floating point accuracy. This switch is a very good thing, as Cocoa relies on floats for pretty much all of its graphical calculations (distances, colours, etc.). This is all pretty smart, but despite this, there’s still a huge amount of work to do in making sure that all the frameworks are good-to-go and optimised for the appropriate architecture. As a quick example… if you were using this:
NSLog(@"This used to be an int: %d", myInteger);
would you really want to change it to this:
NSLog(@"This is now a long: %ld", myLong)
or just leave it as it was? Take this fairly easy decision and multiply it by the number of times you think integers are used in all of Apple’s application frameworks. I would wager that’s quite a few times. Then there are the considerations about using 64-bit values in applications in more persistent places like Core Data where, more often than not, you don’t really need to store values in 64-bit data types and to do so would just be a waste.

Window Server (resolution independence and Spaces)

Another fairly massive change in Leopard is the introduction of a fully resolution-independent graphics engine. This is no small achievement — Apple isn’t expecting developers to be ready for this until 2008. Resolution independence has become necessary as the resolution of displays has increased considerably since the days of 72 dpi screens and will only continue to increase. Resolution independence removes any assumptions about the resolution of the display. If Tiger were running on two different 17″ monitors, with resolutions of 72 dpi and 144dpi, the interface on the 144 dpi screen would be half the size of that on the 72 dpi screen. This is not the desired effect — it would be preferable for the interfaces to be the same size, but revealing more detail on the 144 dpi screen.

Therein lies one of the difficulties with resolution independence — revealing more detail. In many cases, this is detail that just isn’t there at the moment, as applications tend to use fixed-size bitmap images (just look inside the iLife app bundles for evidence of this). In terms of why this is taking so long, I’d say it’s self-evident: new artwork is required for every icon and custom button in the whole operating system. In each case, Apple may have decided to use vector images or a series of NSBitmapImageReps at different sizes (1x and 4x if they’re taking their own advice).

But there’s not only this massive task to contend with, there’s a lot of altered code as well. As a slightly esoteric example, NSOpenGLView has had to be updated, as OpenGL draws everything in pixels, so the view has to perform an inverse transform on the bounds of the view to convert from pixels to points (which is the coordinate system of the view).

Then there’s Spaces, allowing for multiple desktops, which certainly relies upon Core Animation, but I imagine implementing Spaces also resulted in a non-trivial change to the window server, especially considering the ability to drag windows from desktop-to-desktop from an Exposé-like “show all desktops” view:

Spaces also allows for applications to be “bound” to a desktop, and the Dock (…or LaunchServices or both) is aware of these bindings, such that it will switch to the correct desktop when switching to a different application.

QuickTime and QTKit

QuickTime is receiving a massive overhaul in Leopard as well and QTKit is being pushed forward from its current, rather limited implementation in Tiger. Apple’s also introducing the QTKit capture APIs, which look very sophisticated, allowing simultaneous video capture from multiple USB and FireWire cameras and also simultaneous recording out to multiple devices. More significantly than this, the QuickTime low-level engine is receiving a complete revamp. The goals Apple set themselves for QuickTime in Leopard involved making all QuickTime code parallelisable and 64-bit clean with no remaining QuickDraw code and a code reorganisation to comply with the MVC. Again, this is a huge amount of work, especially as the old QT engine will remain in place (as well as the new one) for compatibility reasons.

Also, although it’s not quite as major, the QT browser plug-in is being given the option to render synchronously in the browser’s paint-loop. This is especially interesting considering the introduction of “alpha” H.264 — H.264-encoded video with an alpha-mask (apparently this is an optional part of the H.264 codec). As another brief aside, QuickTime is also adding support for the display of CEA-608 closed captioning text.

Text handling

Very little information has been released on this front, but the CoreText framework is being made public and Allan Odgaard (developer of TextMate) is excited. This is a big deal. I imagine that CoreText will consolidate some of the powerful features of NSTextStorage, NSLayoutManager, NSTextContainer, NSTextView and make understanding all of this:

a lot easier. This might not seem like a big deal, but there’s a lot of buzz surrounding this new API and, as such, I imagine Apple will be using it in a lot of places, again taking time to make sure it’s perfect (and yes, I know it’s been tested for a long time in Tiger, but expanding it OS-wide still isn’t easy).

Spotlight

Spotlight’s getting a bit of a revamp as well, allowing searching of networked machines, the use of boolean operators in searches, linking in to the system-wide dictionary to look up search terms and linking in to web search. Spotlight is also now being leveraged by the help system, revealing menu items based on the user’s query in the Help menu.

I don’t know how much under-the hood work is going on in Spotlight for Leopard but, on a side note, Uniform Type Identifiers are being made ubiquitous throughout Cocoa with the introduction of LSItemContentTypes and associated methods. NSWorkspace, NSDocumentController, NSPasteboard, NSOpenPanel and NSSavePanel (amongst others) are being overhauled to support this with new methods being added to NSWorkspace and NSDocumentController. Also, just to produce some example code for all of these changes, Apple has (finally) updated TextEdit to support NSDocument.

Core Animation

The introduction of this framework relies on three technologies already present in Tiger: Quartz, OpenGL, and Core Image. Core Animation is a “layer-based animation system” (formerly code-named Layer Kit), which allows for developers to rapidly add animation effects to their interfaces. It is utilised by Spaces and Time Machine as well as any application that is taking advantage of the new Image Kit or NSGrid views in Leopard. NSGrid views automatically add implicit Core Animation-fuelled animations when reordering, filtering, adding or removing items.

Layers in Core Animation support a variety of attributes and modes, including geometry (allowing 3D transforms), fills, sublayers, borders, CI filters, shadows, opacity, compositing and masking. This, as you can probably imagine, allows for some very complex scenes to be built and animated such as Apple’s now famous “city of album covers” animation. I’m not sure just how long implementing this kind of framework would take, but I’d guess that it wasn’t that easy.

Time Machine

Time Machine is Apple’s new automated backup solution. Conceptually, this is implemented by backing up read-only HFS+ snapshots of the entire file system at a frequency set by the user. So if you want to retrieve a file that was deleted yesterday, Time Machine is able to “point” the application from which the file was deleted to the file system snapshot from the day before yesterday.

Obviously this is only how it works conceptually — only the first backup is actually complete. After this, there is a low-priority back-up daemon that registers to observe file system events. As files change, the daemon notes the changes and coalesces them into one snapshot per day. For files that haven’t changed between snapshots, these snapshots use hardlinks to link to those files in the original backup (or the previous snapshot). This maybe isn’t quite as sophisticated as switching everything over to ZFS, which supports snapshots natively, but I still think there’s a lot of work in there.

And then there’s a whole lot more, including:

  • PDFKit, which makes provision for adding, removing and reordering pages to PDFs with no code.
  • Upgrade to CUPS 1.2, adding a massive number of new features, including a new web interface for printer administration.
  • The implementation of ZFS (although I’m not sure of the extent of the implementation)
  • Calendar Store is being added to allow developer access to view and edit user’s iCal events (and To-Do items).
  • Multithreaded OpenGL engine and an upgrade OpenGL 2.1 and OpenGL ES 2.0.
  • Support for animated desktops using Quartz Composer (which will also support custom patches in Leopard).
  • Core image enhancements, including automatic UI generation for CI filters (!) and RAW processing.
  • The introduction of Image Kit, including the new Image Browser view (presumable built on the new NSGrid class), the picture-taker panel with support for CI filters, a revamped slideshow view built atop Core Animation, built-in support for image rotation, cropping, scaling, image effects (like those currently in iPhoto) and saving out to multiple formats, etc…
  • Massive enhancements to XCode and Interface Builder, such as in-line error messages in the editor and the ability to edit NSToolbars directly in the .nib file. There’s the introduction of XRay, which looks like an incredible tool for monitoring the performance of applications and finding any bottlenecks. And finally, Dashcode will be bundled with Leopard for rapid development of Dashboard widgets.

With a few exceptions, I’ve thus far completely ignored any updates to user-level applications and focussed on the under-the-hood changes in Leopard. I’m not going to go through the changes to applications at this time, but from a combination of Apple’s website and various leaked development-build screenshots, we know that iCal, Mail, iChat, PhotoBooth, Preview, Terminal, Automator, Safari and DVD Player have all undergone very significant upgrades. This has presumably taken quite some time as well…

Additionally, there are many changes to system-wide user-level features, such as the introduction of more sophisticated parental controls, greatly enhanced VoiceOver (with Alex the new voice designed for rapid screen-reading), a revamped Sharing preference pane and (somewhat inconsequentially) a whole slew of new screensavers.

And that, ladies and gentlemen, is just a small part of the reason why Leopard is taking so long…

Google Desktop for Mac

Google has just announced Google Desktop for Mac. Being from Google, it is in beta (even though the version number is, bizarrely, 1.0.0.155). Also, the Mac version certainly does not have feature parity with the Windows version. Notable features that are missing include the Sidebar, any Google Gadget support, advanced search, the ability to lock down searches and the “Floating Deskbar”. So it’s not really in same league as the Window’s version at this point in time. Perhaps the lack of “Gadget” support indicates that Google thinks Spotlight is crap, but Dashboard is pretty good, so didn’t bother competing on that front. Who knows?

So what does the whole thing do? Well, when you first download it, you’re actually downloading a 1 Mb installer (“Google Updater”) that doesn’t just want to install Google Desktop, but also tries it on with Google Earth, Google Notifier and, presumably, if I’d let it run its course, Picasa Uploader. I think this is particularly obnoxious behaviour from Google. The worst part is that I already have Google Earth installed but, because it’s in /Applications/Google/ rather than just /Applications/, Updater didn’t detect it and tried to download it again. At this point, I tried to quit the installer and was presented with this rather horrifying dialog:
Google Updater
So, let me get this straight. I have two options 1) Watch you (Google, that is) continue installing a program I already have or 2) Let you do it secretly. What a choice — it’s a tough one.

So after this pretty abysmal start, things picked up a little (aside from the ever-present Beta label and lack of feautres). After installation, I was presented with a rather helpful dialog, explaining that all I had to do to use Google Desktop was to press the command (⌘) key twice:
Google Desktop Welcome
After confirming that I had indeed “Got it!”, I was presented with the main head-up interface to Google Desktop, which is beautiful in its simplicity:
Main “head-up” interface
Pretty nice. Certainly as simple as the Spotlight interface. The Preferences link at the top right takes you to a pane in System Preferences — fair enough. It is, after all, a system-wide service and can run as a “faceless” process in the background. As you can see in the bottom right of the above image, Desktop was at the time hard at work indexing my hard drive (a process that took around an hour in my case for ~100,000 files). Rather nicely, it’s possible to perform a search while indexing is in progress, although obviously the results are incomplete…

At this point, I just waited until it had finished indexing before actually starting to use it. Once it had finished indexing, I ran a quick ps auxc | grep Google out of curiosity to see what was going on behind the scenes. To my surprise, this revealed 8 processes, as shown here:
Google processes
Now, I don’t actually know what all of these are doing, but there seems to be an almost comical level of redundancy between the processes. For example, what are all these doing: GoogleUpdateInstaller, Google Update Helper, GoogleUpdateDownloader and GoogleUpdateChecker? Weird. Also, what’s the difference between a Daemon and an Agent? Though I’m probably just being ignorant not knowing the answer to that one…

So far, so interesting. Now, in terms of features, the obvious comparison is between Google Desktop and Spotlight. On this front, Google Desktop looks fairly promising. My feeling (i.e. without any formal testing) is that Desktop is marginally faster than Spotlight (on my 17-inch MacBook Pro 2.33 GHz). It also has the option to present more information than the Spotlight menu does in the form of file-paths or “snippets” from mail messages, HTML files etc. However, Desktop does seem to ignore Spotlight’s preferences for the order in which search results appear (and presents no equivalent option in the preferences). When I search for “iPhoto”, for example, the first hit with Spotlight is iPhoto.app, whereas with Desktop, the first hit is the iPhoto Getting Started Guide — not really something I want to open on a regular basis.

Another feature of Desktop is its integration with your web browser. Once you’ve restarted Safari, you can access the Google Desktop homepage from a multiplicity of places: the Desktop menu bar item, its Dock icon or by heading to google.com and clicking on a new item above the search box: Desktop. All of these take you to 127.0.0.1:9115, which looks like this:
Google Desktop homepage
As you probably already know, this allows you to search for local content through the web browser. Through this interface, I’d say Desktop surpasses Spotlight in some regards, but not others. For example, it allows for searching of web history and will show you a small graphical preview of each page in the results. Also, cached email messages can be viewed within the browser with no need to switch to Mail, which is pretty nice. But Spotlight wins in terms of filtering down your results. Desktop gives you the option to show everything or just any of the following types: email, web history, files, media or “others”. Then it gives you the option to sort by either date or relevance and whether you would like a partial or exact match of the search term. These options are fairly limited compared with Spotlight, which presents the following options:
Spotlight interface
Desktop also allows for searching of Gmail accounts, which is neat (although it takes an age to index the messages) and, crucially, allows a Google search to be launched by pressing ⌘ ⌘ “Search term” Up-arrow Return. This can be done from any app and is definitely a bonus of installing Desktop, especially if you don’t already have Quicksilver configured to do something similar.

So all-in-all, Google Desktop is pretty average. It’s in beta (although admittedly I haven’t had any issues with it thus far), it doesn’t offer feature parity with the Window’s version, it isn’t better than Spotlight in all regards and the installer is horrible. But, on the plus side, it does offer a couple of nice new features, notably Gmail search, system-wide Google search and web history search with graphical previews. I’ll be leaving it installed for the moment, especially as it’s a pretty “passive” program — it runs in the background and hasn’t taken over any of my keyboard shortcuts, so why not? I think Spotlight in Leopard is introducing system-wide web searching, and Quick Look will give us rich graphical previews of every file but, for the moment, I think Google Desktop will make some contribution to my daily Mac-using life.

Improving the Dock (a little bit)

As Bruce Tognazinni rightly points out, “Apple Sales is in love with the Dock”. He points out many (specifically 9) problems with the OS X Dock but, contrary to his original stance, believes that the Dock should be kept in place, but supplemented with “serious, information-dense tools”. I do agree with the Tog, but at least there is the consolation that at least a few third parties stepped in to help out.

Anyway, I was thinking about how Apple could possibly add functionality to the Dock, but at the same time keep Apple Sales happy and leave the Dock with its current simplicity and aesthetic appeal. And here are a couple of my ideas (excuse the abysmal Photoshopping):


This shows a sub-menu of the window menu item in Safari’s Dock menu. I’ve always thought of tabs as sub-windows and I think it’s a shame they’re not treated as such by Exposé and the Dock. Programs that currently use tabs include pretty much every web browser, Adium, TextMate, iTerm, Preview1 and Pathfinder.

Pre-release screenshots of Leopard show that both iChat and Terminal will join this ensemble in the coming months. So maybe it would make sense for Apple to have a bit of a think about tabs and produce some crazy mash up of NSTabView and NSWindow, such that each instance of “NSTabViewWindow” could advertise its tabs to Exposé and the Dock. I don’t know – I’m not a programmer. But I am a user, and I think this would be a sweet bit of functionality for OS X to gain.

A similar menu could appear when a user right-clicked a tabbed, minimised window. Possibly even showing a graphical representation of the contents of each tab, which leads me neatly on to my next idea…


I think this one’s pretty self-explanatory. This window selection interface would appear upon mousing over the Dock icon of a running program, revealing all of its available windows in a ⌘-tab-style interface. Clicking on one would bring it to the front, un-hiding the application if necessary.

So that’s all the images for now. However, I would also like to add two extra features to the Dock that I didn’t feel required a illustration:

1. Allow minimised windows to be closed through their contextual menus (in programs other than the Finder!)
2. Allow for persistent app-specific contextual menu items (e.g. it would be nice if the list of Pref panes in System Preference’s context menu were still there even when System Preferences wasn’t open)

I’m sure there are many many other enhancements (including spring loaded folders – apparently coming in Leopard) that could be made, but I reckon these would be a great start.

1Kind of. If you open multiple images in Preview at the same time, they are “quasi-tabbed” in the drawer at the side of the Preview window.