Qt/Mac Cocoa Port Alpha Released

Published Monday March 3rd, 2008
26 Comments on Qt/Mac Cocoa Port Alpha Released
Posted in News, Qt

You may have remembered that in the past I’ve talked about some of the development of 64-bit applications on Mac OS X. The gist of it is that Apple changed their position on supporting 64-bit Carbon, the library we depend on for running Qt GUI applications. It became obvious early on that Apple wasn’t going to change their position on this, so it left us with two choices:

  1. Keep Qt Carbon-only and forego 64-bit support.
  2. Create a port of Qt that used Cocoa as its backend.

Naturally, since we already support 64-bit on the other platforms and since the idea of using Qt is to help insulate you from changes such as this, we decided on the latter option. It did mean that we had a bit of work ahead of us, since we had to re-write some of the internals of Qt (particularly widgets and events), but most of the other modules were already there.

I’m happy to say after a bit of work, we’ve made progress and we’re proud to offer an alpha for curious people that want to try 64-bit applications on Mac OS X 10.5. It is based off a fairly recent snapshot of 4.4.0, so it will have all the bugs and features of 4.4. There still is a lot that doesn’t work and there’s a way to go (hence the term “alpha”). On the other hand, having more people try it out will help us find bugs and will make it much better (there’s only so much we can test locally).

Here are the links for the
open source package
and the commercial package.

The official press release is here (along with an ouroboros link back to this blog post).

The place to offer feedback is on the qt4-preview-feedback mailing list. Please consider putting something about Cocoa in the subject so that it gets to the right people.

By default, the package is built in 32-bit (in case you happen to not have a 64-bit machine). To build in 64-bit pass -arch ppc64 or -arch x86_64 (if you want to build 64-bit universal, pass both). I would also recommend passing -prefix $PWD so that it is not necessary to run make install. I’m not sure make install works in this package.

Since we aren’t putting up the documentation for the alpha up (it’s pretty much the same docs as 4.4), I’m reproducing the known issues for this package here:

This document explains the current list of features in the Qt/Mac Cocoa port that are currently not working. Most of the issues will be addressed in upcoming snapshots and beta releases. We hope that all the issues should be addressed by the time the of the final 4.5.0 release.

What Works

Here are the things that we can say about the current state of the Qt/Mac Cocoa port.

  • 64-bit Support: The Qt libraries currently do build and link as 64-bit frameworks and it is possible to build and run many of the Qt examples as 64-bit.
  • HIViews are now NSViews: Every QWidget is now backed by an NSView pointer instead of an HIViewRef. QWidget::winId() will return an NSView pointer that can be used in other Cocoa technologies (e.g., Core Animation).
  • Some Native Dialogs Work: QFileDialog and QColorDialog have been ported to use NSOpen-/NSSavePanel and NSColorPanel respectively. QPrintDialog and QPageSetupDialog are not in this release, but are on their way. Currently, none of these dialogs show up as sheets pending the creation of an asynchronous API.
  • Painting, Printing, and Styles: Since printing and painting used Quartz 2D and styling used HITheme, these sub-systems work without any changes.
  • OpenGL: OpenGL is fully supported,including pixel buffers and framebuffer objects.
  • Clipboard: Using QClipboard to copy and paste data works as expected.
  • Mouse, Keyboard, and Wheel events: Mouse, keyboard, and wheel events are dispatched to the proper widget. The Qt/Mac Cocoa port respects Cocoa’s idea of a "First Responder."

Current Known Issues

The following are items that don’t currently work, but that we plan to have resolved before the final release of the Qt/Mac Cocoa port. Please do not file bugs on these.

  • Carbon Support: The current source tree for the Qt/Mac Cocoa port contains source for building Qt/Mac with Cocoa. It contains some of the source code that is used for the Carbon port, but it is currently not set up to build the Carbon Qt/Mac libraries. Please use a normal release or snapshot if you want to use Carbon.
  • Drag and Drop Support: Drag and Drop is currently not implemented and needs to be ported to Cocoa, but using the clipboard does work at this time.
  • Accessibility: Accessibility support is not implemented and needs to be ported to Cocoa.
  • Text: Most text rendering works fine for Latin-1 characters. However, rendering non-Latin-1 characters has not been tested.
  • Input Methods: Input methods also need to be ported to Cocoa.
  • Shortcuts: Shortcuts that exist outside of the menu bar may not be dispatched.
  • Tablet Support: The tablet support has not been ported from Carbon yet. However, it should still be possible to use the tablet as a mouse.
  • Phonon: Phonon uses the QuickTime backend that is only available on 32-bit. Using Phonon in 64-bit requires a QTKit-based backend and has not been done.
  • Unified Toolbar: The QMainWindow::setUnifiedTitleAndToolBarOnMac() method currently does nothing.
  • Dialogs, Tool Windows, Sheets, and Drawers: At the moment, all windows are subclasses of NSWindow. This means that window types like drawers and sheets do not work and tool windows do not get the right decorations. Modal dialogs do show up at the correct window level, but are not yet considered "panels." Many window flags are not recognized.

Things We Don’t Expect to Support

The following items that we do not plan on spending any resources on unless there is monumental outcry for their inclusion.

  • Qt3Support: At this time we have no plans for making the Qt3Support module work with the Qt/Mac Cocoa port in 64-bit mode. Following in footsteps of Apple, we would like to encourage you to consider the time of going Cocoa and 64-bit as a chance to jettison Qt 3 constructs and classes.
  • Support for versions of Mac OS X below 10.5: We are using methods and classes that are only available in 10.5 and higher. Most of these functions don’t have any equivalent on earlier versions. We recommend using the Carbon version for earlier versions of Mac OS X. We anticipate keeping the Carbon port supported at least for the lifetime of 4.5.
  • Support for -no-framework or -static: Cocoa requires that we load a nib in order to properly access the global menu bar. This nib has to reside on disk somewhere. The most logical place for it to reside is inside the QtGui framework. For this reason, building Qt as standard "dylibs" or statically is no longer supported.
Do you like this? Share it
Share on LinkedInGoogle+Share on FacebookTweet about this on Twitter

Posted in News, Qt

26 comments

Aidan says:

This is AWESOME news!

We work with large MRI scans and this will really simplify development on the Mac!
(4GB VM just doesn’t cut it anymore πŸ™‚

Thanks guys!

Philippe says:

Very happy to see that you have taken the task seriously! You’re the best!

Felix Ritter says:

I’m very glad to hear this, this is great! Having just finished a port of a big project from Qt3 to Qt4, I can imagine the pain you went through ;-). However, I would like to encourage you to consider Qt3Support of at least the basic datastructures.

This is fantastic. I was just reading about some of the cool features in Leopard like iChat Theater, but they’re often restricted to Cocoa. So having a NSView is perfect — Qt users will be able to use iChat theater with almost no programming!

Since you mention nibs above, would there be ways to interconvert between nibs and Designer? Or are you just using a small nib to access the menu and applications won’t have them?

trenton says:

To Felix: Qt3Support will probably work in 32-bit mode, but we have to port Q3FileDialog to work in 64-bit mode, and it seems like a lot of work for a little gain. Are there any “basic data structures” you were thinking about especially.

To Geoff: Apple keeps the nib format private, so it would be hard to do a conversion and expect it not to break at some point. Probably the better solution would be to get our integration good enough so that it would be possible to use QWidgets inside of Interface Builder. That’s a much longer term goal though.

Deric Horn says:

Fantastic Job Trenton!
This is a great and very important milestone! Congratulations!

I look forward to seeing continued integration with Cocoa down the road.

Jason Haslam says:

This is great news! Will text rendering still use ATSUI or will it be changed over to Cocoa/CoreText APIs? This could be a big win performance wise. Also, I’d like to add a vote of support for -no-frameworks and -static if possible. Our organization uses dylibs for debugging (because of some problem with debugging in frameworks that I don’t even remember now) and static for release. We could get by without it, but it would be nice.

trenton says:

To Deric: Thanks! We’ll see where we get to! πŸ™‚

To Jason: Text rendering is already using CoreText in the Alpha since ATSUI is 32-bit only. We are still learning the APIs (for example, we can’t seem to get the bold version of Lucida Grande at this moment), but we are sure we’ll get those solved. CoreText looks very promising. As for the non-framework version, it’s very tough since Cocoa *requires* that we load a nib (even if it is a minimal one) in order for menus to work correctly and I’ve not come up with a solution that doesn’t feel like a hack other than requiring a framework :-/ It could be why I don’t see many static Cocoa libraries.

Boyd Waters says:

WONDERFUL!

We are very pleased! We create Qt applications for processing large astronomical data sets. We can use 64-bit! Astronomers want it on Mac!

I want to echo Jason’s comment “Will text rendering still use ATSUI or will it be changed over to Cocoa/CoreText APIs?” — we’ve run into ATSUI performance problems and I had to stop development on at least one (simple) Qt application (a log-file viewer) (there’s a satisfactory log-file viewer in Mac OS X already).

I’ll put this Cocoa alpha together for the MacPorts build system so that you are sure to get many testers! πŸ™‚

Felix Ritter says:

@Trenton: We’ve a lot of data structures, such as Q3ValueList, Q3PtrList, Q3PtrDict, Q3DictIterator, etc still in use everywhere. Currently, we develop for Windows, Linux, and Mac OS X. So every major change must be tested on all platforms. Having at least a little Qt3Support for Mac 64-bit would minimize the burden of the port on the Qt side. However, I understand that it would require a much larger effort to support the Qt3Support GUI classes too. We too work with large medical datasets so 64-bit demand is high. Anyway, great to hear things are moving in the right direction.

Felix Ritter says:

@Trenton: We still use lots of Q3PtrList, Q3Dict, Q3DictIterator, etc. everywhere. Since our main applications are developed for Windows, Linux, and Mac OS X, every major change has to be tested on all platforms. Having at least some Qt3Support for 64-bit Mac would ease the burden of the 64-bit port on the Qt side. I understand though, that porting the GUI classes of Qt3Support is a much larger effort. BTW, we already removed Q3FileDialogs, never had much fun with it. Anyway, I’m glad things are moving in the right direction. We too work with large medical datasets, so 64-bit support is of high demand.

David Johnson says:

You’re only keeping the Carbon version around to the end of 4.5? Doesn’t that break Trolltech’s commitment to compatibility within a major release? Some people will have to support 10.4 Tiger, and others may need Q3Support. Will they become second class customers to Trolltech?

trenton says:

To Boyd: Wow, thanks for the macport! Good Luck! I hope that having an alpha in their tree isn’t too trying πŸ™‚

To David: We guarantee that Carbon will be there for AT LEAST through 4.5. I’m a developer and I cannot say with any authority what happens beyond that. At some point, though, we are going to have to decide how to best proceed going forward and I expect that will mean getting rid of Carbon. I have a feeling that there won’t be many Tiger users at the point the decision is made (that or the Cocoa version is back-ported).

That being said, we’ve had multiple code paths before (for example, in Qt 4.1 you could do both QuickDraw and Quartz 2D drawing, and use Appearance Manager and HITheme for drawing). Keeping all the paths working is not trivial and some would argue that we did a poor job of it.

When the Carbon version finally does make its curtain call, it’s not as though the source suddenly disappears, though. Having a “Carbon patch” to Qt doesn’t seem impossible (since that’s essentially what the Cocoa version is at the moment). Score one for open source πŸ™‚

Boyd Waters says:

Now that Qt is using Cocoa, screen drawing will be throttled by “coalesced updates”, right?

Fortunately, the Mozilla Firefox devs have been turning over some rocks, and tasting the creepy things that crawl out:
http://blog.vlad1.com/2008/02/28/finding-the-os-x-turbo-button/

(ok, it’s a gross idea, but you are Trolls, right? so it’s ok…)

And even more fortunately, Apple and Qt have merged WebKit!

trenton says:

To Felix: Well, you should be able to pull the Qt 3 container classes out and build them into your code with no problem, I can’t see anything that would stop them from working.

To Boyd: Qt used Quartz beforehand, so it had to deal with coalesced updates since 10.4. We don’t do a lot in Qt to solve this since doing lots of drawing in a little amount of time is more an application-level issue than toolkit one. In general, writing code to handle the issue of “coalesced updates” transfers very well to other platforms too.

nacho says:

Just wanted to say a very big THANK YOU. It has been a very great surprise to have a Cocoa version so early. Keep the good work guys.

Trenton, I will pay the first and the second beer round when I see you πŸ™‚

Raymond Martin says:

It is great to see Trolltech really moving ahead with Cocoa support and in various other areas.

Would you have any idea as to whether this support is going to find its way into QtJambi?

QTJambi is great, but since Apple deprecated the Cocoa-Java bridge there is a sore lack
of proper support from Java to get under the OS X hood (e.g. to use OS X services and so forth).
Using JNI to add support when QtJambi already uses it seems like just creating a mess when
a more unified and simple approach could be taken. For instance, via this new Qt-Cocoa support.

Any thoughts?

trenton says:

To nacho: Wow, great. I’ll buy the third round then πŸ™‚

To Raymond: I don’t see anything really stopping Qt Jambi from using the Cocoa version once it is finished. I don’t know how well you will be able to access the Cocoa APIs from it though. It might require some work because we only have frameworks at the moment and Jambi has used dylibs-only, but no one has investigated it yet since we are still early on. We certainly aren’t doing anything to make it NOT work at least.

Adam Higerd says:

Allow me to add my +1 to the vote for -static. I understand the necessity of having a nib file around, but the “Mac” way of doing things means that applications shouldn’t have to lug around dependencies — applications should be downloaded in a .dmg image and should be able to be run in place without an installer. Even with an installer, though, the user should never be required to do the work to satisfy dependencies. There are three solutions: link statically, put the dylibs in the bundle, or put the frameworks in the bundle. Qt’s frameworks are EXTREMELY large, easily dwarfing the compiled size of any application I could hope to ship. As far as the nib file is concerned, why not store it somewhere qmake knows how to find it, and then have the application build process copy that nib into the app’s framework instead of using the one from QtGui? Doing it that way isn’t really a “hack.”

trenton says:

To Adam:
Thanks for the feedback, we’ll keep it in mind. I’ll just state my current thoughts on this.

It is a hack because it requires the the application to have extra components that it doesn’t load explicitly (but a library does). Not to mention every application gets this little nib, which doesn’t seem right.

The Qt 4 frameworks aren’t that big (unless you build with STABS debugging, then they are huge). I’ve compiled Qt 4 apps and included the frameworks vs. linking statically and the resulting size of the binary is very comparable. I don’t remember the numbers though and it did use most of the modules, but it seemed like it was within a megabyte (and this disappeared when placed on a compressed disk image). I know back in Qt 3 with gcc 3.3 one could shave off around 3 megabytes by linking statically and using dead code stripping, but I’m not sure if you get a multi-megabyte savings anymore for non-trivial applications (especially when considering universal binaries). Seeing another datapoint would be worthwhile. πŸ™‚

As I said though, we’ll keep it in mind.

Craig Ringer says:

Can’t you include the Qt Frameworks in the .app bundle?

http://cocoadevcentral.com/articles/000042.php

That way you get the same interface for end users ( launch the app in place from the .dmg, drag it to Applications, etc ) but can retain the framework packaging.

trenton says:

To Craig,

Yes, this is what is detailed in our deployment guide (although for us you have to run install_name_tool). Morten wrote a tool to help ease the pain of the issue.

matt says:

You are not required to use a Nib. That is simply a convenience for building Cocoa applications with XCode and Interface Builder.

NSApplication *myApp = [NSApplication sharedApplication];
NSMenu *menu = [[NSMenu alloc] initWithTitle: @”Main Menu”];
[myApp setMainMenu: menu];
[myApp run];

trenton says:

Hi Matt,

Thanks for the tip. I tried this early on in the process (not with the title “Main Menu” though) and I seem to remember this not working as well as you’d expect. It required a lot of building from scratch and at the end, the menu didn’t look correct (the application menu wasn’t bold) among other things. I’m not the only one who’s tried to do it from code and didn’t succeed. Believe me, if I didn’t want have to use a nib, I would drop it in a heartbeat. It’s annoying to use in a library.

:kelko: says:

Hmm, when you use a nib for the global menubar could you do it in a way I can close every QMainWindow (with setQuitOnLastWindowClosed(false) ) and still have a menubar?
At the moment when I close the last window (the app still running) and ο£Ώ+TAB to another app and ο£Ώ+TAB back the menubar disappears and I can’t use the app anymore and have to quit it. It’s quite annoying if you want to develop the app “mac-like”.

James Turner says:

Awesome news, I was wondering about this following the 64-bit Carbon announcement, sounds like my guesstimate (huge changes in qwidget_mac.cpp and events, not too much elsewhere) wasn’t that wrong. What’s the issue with Tiger support, specifically? Can’t quite imagine what APIs are fundamental that require 10.5. Oh, and bundled-frameworks seem fine, especially if you make the install-name-tool script bundled and semi-official. How about a CONFIG option for ‘app_bundle’ that copies the frameworks and runs install_name_tool automatically?

Commenting closed.

Get started today with Qt Download now