Configure player

Close

WWDC Index does not host video files

If you have access to video files, you can configure a URL pattern to be used in a video player.

URL pattern

preview

Use any of these variables in your URL pattern, the pattern is stored in your browsers' local storage.

$id
ID of session: wwdc2004-219
$eventId
ID of event: wwdc2004
$eventContentId
ID of session without event part: 219
$eventShortId
Shortened ID of event: wwdc04
$year
Year of session: 2004
$extension
Extension of original filename: mov
$filenameAlmostEvery
Filename from "(Almost) Every..." gist: ...

WWDC04 • Session 219

Transitioning to Quartz 2D

Graphics • 1:08:38

As Quartz 2D, the powerful 2D graphics engine in Mac OS X continues to evolve, it moves further and further ahead of QuickDraw. Learn how to transition your applications from QuickDraw to Quartz 2D to take advantage of new features and capabilities. This session outlines a Quartz 2D transition plan for QuickDraw developers and explores solutions to common problems they might encounter. This session is a must for all Carbon developers.

Speakers: Haroon Sheikh, Joseph Maurer

Unlisted on Apple Developer site

Transcript

This transcript was generated using Whisper, it has known transcription errors. We are working on an improved version.

Ladies and gentlemen, please welcome Quartz Engineering Manager, Haroon Sheikh. Welcome to the last day of WWDC. It's almost over. We've got a really important session for you today. It's really going to be important if you're using QuickDraw on Mac OS X. So if you haven't heard already, let me go right to the point. We are officially deprecating QuickDraw and we are replacing it with Quartz 2D. Now, QuickDraw has served us quite well for the last 20 plus years.

It has been instrumental in the GUI revolution in the 80s. It was really innovative for its time. It introduced many interesting ideas and features such as regions, patterns. We introduced PIX with it, with the display manager. We introduced seamless multi-monitor support. And with Color QuickDraw, we actually introduced a seamless transition to color. One of the other important things with QuickDraw was that it was fast and efficient.

But unfortunately, it is no longer a competitive 2D graphics API. And our applications, our users expect a really rich graphics API on the platform. And so some of the things that are missing from it are Bezier curve support, alpha support, built-in color management. We've got color sync, but it's not built in. It's not thread safe.

Some of the assumptions that QuickDraw was built on, or some of the design goals that it was built on, are now starting to show up as limitations in your application. So the coordinate system is limited to 16-bit integers. The resolution itself is limited to 72 DPI. and going forward with resolution independence in the future, that's going to become a real bottleneck for us.

And one of the signs that it is no longer competitive is you'll notice that applications are using QuickDraw as nothing more than a blit engine because they've got their own graphics engine doing their own rendering and at the end of it they just end up using QuickDraw for blitting to the screen.

In our development of Mac OS X and bringing QuickDraw over to Mac OS X, Since Jaguar, Panther, we've noticed, you know, we've been fixing bugs inside of QuickDraw for a particular application. But just fixing that one bug would end up breaking potentially other applications. So we recognize that QuickDraw has now become fragile. And for us, maintaining binary compatibility with your applications has become quite a bit of a challenge.

So even though bug fixing is a problem for us, we can't really add some of the features that I talked about earlier on the previous slide into QuickDraw. So we really can't extend it anymore. And we've decided we're no longer going to be working on it. We may fix a bug here or there, but there's no active development on it in terms of adding new features to it. So it's no longer feature-proof, implying that we'll no longer integrate it with new features in the system. It will continue to function the way it is, as you've expected to, but it will not be integrated with the rest of the new innovative technologies.

On the Converse side, you've got Quartz 2D, where it is a very rich graphics API. It is based on an industry-proven imaging model. By design, it is actually resolution and device independent. And we've got built-in support for alpha, alpha channels on images. And for rector art, we've got transparency support and alpha there also.

It is designed to be thread safe. It has a really rich feature set. I list many of those things. And if you've been at any of the Quartz 2D sessions this year or in past WWDCs, you know what I'm talking about. And it also has a floating point coordinate system.

It integrates very well with other technologies. For example, we've got ColorSync's color management built into Quartz 2D. And this year with Core Image, you can actually take advantage of Core Image with Quartz 2D. It's directly integrated with that new technology. Quartz 2D is also now, you know, hardware accelerated through Quartz Extreme. And all of these points come up with one conclusion. This is the API that you want to be using if you want to be feature compatible.

So I just want to show you this graph. You may have seen it in the previous WWDCs. But the concept here, I just want to get one major point out of this. The numbers are not necessarily accurate, but they are there to give you a particular point. And that is, you want to be on the Quartz curve and not on the QuickDraw curve. QuickDraw is deprecated. You want to showcase your application on Mac OS X by taking advantage of Quartz. And that's really where, if you don't, your competitor probably will.

So what does it mean for you? This deprecation concept. It means that we will maintain binary compatibility, so we're not actually removing the QuickDraw library from the platform in Tiger yet. I'm not sure when we'll make that decision, but it's definitely not for Tiger. If you are building for Tiger as your build target, you'll start getting warnings.

That's just to help you to know which APIs you need to move off of. and at some future stage we will also consider removing the headers so you won't actually be able to build using the QuickDraw headers. Now what is being deprecated? It's the headers that I list here. The main important one is really QuickDraw.h.

All of the APIs in them are being deprecated. At previous WWDCs, we've actually talked about adopting Quartz in your Carbon application, and we've talked about a piecemeal or incremental approach, take pieces out of your rendering and replace QuickDraw calls with Core graphics or Quartz 2D calls. But going forward, that's no longer an optimal solution. And so this year, we're actually asking you to fully adopt Quartz 2D. And you want to leverage that in all aspects of your graphics usage, be it for display, printing, metafile generation, PDF generation.

Many applications out there are architected on Quickdraw, and some of the limitations inside of Quickdraw may also show up in your architecture. So what we would like you to do is, if that is the case, think of the new features that the Quartz provides, or Quartz 2D provides, and re-architect your application with Quartz 2D in mind. Take some time in your design cycle for the next version of your application, and really understand what you need to do, because it's not necessarily an easy transition. And to that end, we're also moving all of our internal code over to Quartz already.

Now, as I mentioned earlier, Quartz 2D is being hardware accelerated through Quartz Xtreme, but QuickDraw is not being hardware accelerated in Tiger. The main point here is if you end up using QuickDraw in your application, that window where you end up drawing to with QuickDraw, it will no longer be accelerated.

And the reason for that is QuickDraw, not being accelerated, has to draw through the CPU. And for us, what that means is you have to pull the window back and store back from the VRAM over to system memory. You start drawing into it through QuickDraw. We don't want to go ping pong back and forth, accelerate, decelerate, accelerate, decelerate. So our policy is that as soon as you end up using QuickDraw, we will decelerate you. Because just that ping ponging itself is actually going to be much more of a performance issue than it is. and any hardware acceleration that you might benefit from.

So Quartz 2D is accelerated through Quartz Extreme, and you want to enable it. It's currently not enabled in your build at WWDC. Enable it through Quartz Debug. It's a familiar tool for those who are already working with Quartz. In general, it also has all sorts of other performance features that you can use to determine what are the bottlenecks in your application. But enable it through Quartz Debug.

And there's another feature in here, which is the show window list that will list all the windows in the system. And those windows which are accelerated will be color coded as green. So you can find out whether your window is actually being accelerated or not, where it is in terms of what the window server thinks it is doing, or what the Quartz compositor has decided, whether it's on the graphics card in terms of it being accelerated or not.

Now as you start making this transition, you'll come to the conclusion that these are two different imaging models, if you haven't already. QuickDraw is fundamentally pixel-based, whereas Quartz 2D was designed to be resolution and device independent. So as a result, Quartz 2D is not going to be a superset of QuickDraw. So there are going to be features in QuickDraw, and primarily those are pixel-based manipulation utilities that are not going to be provided through QuickDraw.

So as you start making these transitions, you'll come to the conclusion that these are two different imaging models, if you haven't already. QuickDraw is fundamentally pixel-based, whereas Quartz 2D was designed to be resolution and device independent. So as you start making these transitions, you'll come to the conclusion that these are two different imaging models, if you haven't already.

In some cases, we may add similar features. For example, the transfer modes in QuickDraw. We've got PDF blend modes inside of Quartz 2D. They don't match one to one, but you could probably use some of them if necessary. You may want to also re-evaluate the usage of those APIs. A perfect example that comes out is XR drawing. Yes, we've got a transfer mode for it, but if you look at Mac OS X, many applications can get away without XR drawing.

And you want to re-evaluate and think differently in terms of how you want to use that API that you're used to, but how you could do that equivalent thing in Quartz 2D. And so in some of those cases, we've decided the OS is no longer going to be providing those APIs as a system level service.

We realize the transition is not easy, so we've done quite a bit of things for Tiger. Specifically, we've added many new APIs in Tiger in the Quartz 2D API, and those are focused primarily for people who are going to be moving over from Quartz, from QuickDraw to Quartz 2D.

A common complaint has been the documentation. So we've improved the documentation significantly. We've got the drawing with Quartz2D document. We've got the reference document. Those have been updated. Plus we've got this new document, which is the transitioning to Quartz2D. It's a new series of articles. You should have access to them already.

There'll be many more coming. It's going to mimic the contents of this session, and we'll go into more detail about some of the problems that you will run into in this transition. We've got new sample code. We'll have more sample code available, maybe even technos, depending on what problems people come up with and what the solutions are.

We've got a Quartz step mailing list. If you're not on it, it's a great list to be on because you've got other Carbon developers and other Quartz 2D developers who can help answer questions and we've also got some of the engineers on our team that are helping out with those questions also.

And right after the session, we've got the Graphics and Media Lab where you can drop by until 5:00 PM today. And we will be there to answer questions for you. So we'll do the Q&A. But after that, we can also move to the Graphics and Media Lab and focus in on specific questions that you may have. And finally, we actually need your feedback.

We've tried hard to make this transition easy or fill in some of the holes. But as you move your application over and you recognize problems in your application-- are you missing a functionality? Let us know. There's many ways that you can do that. And I've listed the mailing list, contacts that we'll list at the end. But let us know. It's a really good opportunity for you to try it out and help us ease your transition.

There are a few other technologies that are being deprecated that we're not going to be talking about in this session, but I wanted to list them here. The Display Manager and Draw Sprockets are being deprecated also. And for those two technologies, what you want to do is use the Quartz display services. Those technologies were actually built on top of the Quartz display services, so now you should actually go directly to that.

It's a better API for you to be using. And QuickDraw Text is also being deprecated. It was discussed in another session earlier this week, so we won't talk about it. And from this point, I'll actually like to bring up Joseph Maurer, our QuickDraw expert, who can actually help you see the common problems and help you move over to Quartz 2D. So, there you go. Thank you, Haroon.

They deprecated my nickname. But it's okay. I actually like it. Feels like a promotion. I still should let you know that where I come from we say Quartz. So don't laugh if my pronunciation of Quartz is not as you hear it all over the place. From now on, each time you read about, hear about, learn about Quartz, you will think of me in the way I say Quartz.

You know, I had to learn this new word this year. Deprecated. looked it up in the dictionary, comes from Latin, "deprecare." And it means to ward off by prayer. I'm not making this up. You can Google it for yourself. So can you picture Haroon and Peter Graffagnino praying to defend themselves against the evil of QuickDraw? talking about evil. You are a wonderful audience.

You fit, you are the perfect audience for this afternoon. You are, I assume you are a Carbon developer, so you can relate to the quote in the title. I assume you know QuickDraw, so I don't have to explain anything about it anymore. I assume you know enough about Quartz that I don't have to explain much about it either. And of course you want to transition your graphics programming to Quartz. Yeah? Okay. I know there is some obstacle to overcome. You need to let loose of some sentimental attachment. And I know what I'm talking about. I've been sentimentally attached for 21 years.

See, over the last weeks or so, sometimes I felt like standing out there on the corner, the Ansa Mariani, in the morning, watching all the fellow Apple employees drive by to work. And I was there with my big sign that read, hunk, if you like QuickDraw. Well, with the exception of two or three bodies from the QuickTime group, nobody honked.

So I brought my own hunking device. QuickDraw, QuickDraw. It's Friday afternoon after all, huh? I don't have a musical instrument for Quartz. Quartz doesn't need, it would have to be something big, you know, shiny and splendid. I'm thinking of a trombone. No way I could fit this in my cargo pants. Quartz has something else. Quartz has Tailwind. Tailwind is a new technology. Tailwind is a new technology. and as somebody who likes to ride a bicycle, I can tell you that Tailwind is a very good thing.

All of us know, however, that in order to take advantage of Tailwind, you need to go in the right direction. So I invite you to come along with me and we make a big turn and we turn into the right direction. We go to transition. They told me it would work. Yeah.

[Transcript missing]

Take the first three bullet items as introduction, as things we need to think about before we even get started. And then, thinking about the program here, I thought I would isolate two concepts that need more discussion in depth, region handles and copy bits.

Then I regroup some more issues and concerns. At the end, think about pictures versus PDF or performance or this color space thing and everything that's new there. And I even have examples and demos. Why don't we start with sample code? Then I regroup some more issues and concerns. At the end, think about pictures versus PDF or performance or this color space thing and everything that's new there.

And I even have examples and demos. Why don't we start with sample code? Many of you may remember from three or four years ago CarbonDraw, which was the first proof of concept. You actually can call Quartz APIs from a Carbon application. This time, it's the real thing. There is no QuickDraw at all. It can be done. You don't use XOR for drag selection and matching answer, whatever. You use overlay windows.

Hit testing, there is no point in region. We don't need it. There are other ways around it, and the sample code shows it. We have copy-pasting, PDF data, the generic color space usage, and some more. And it's available, I didn't find it today, this morning yet, but it should come up anytime real soon. And it's there to grow. I think I want to demo it now.

So it's your regular drawing application, nothing spectacular. You draw lines, move them around. Now each time you do hit testing, you use a one pixel bitmap context that you transform appropriately. You can scale the drawing. and HitTesting also works in the scaled way. What's going on behind the scenes is there is one generic transform that transforms from document coordinates in the list of shapes to the window content.

Now I'm emphasizing this because if ever you get your hands on the copy that's uploaded, this might not work. I fixed the bug just over last weekend. And I will later come back, remind me to talk about this bug. It's helpful. And of course you do set fill colors or whatever.

No, I meant full blue. And I mentioned before that it does take advantage of built-in color matching. I don't know if you can see this. If you look closely, this digital color meter tells us that the real color I'm pointing at here is not the blue that we set. It has got an additional red component in there. I don't know why. The color thing people can explain you.

But that's just a demonstration that color matching works, is there, is alive. And of course, on top of it, color matching wouldn't make much sense without calibrating to begin with and with projectors and so on. It's just something to point out. I said we have copy and paste. Before we can save as a PDF file, that's no big surprise.

[Transcript missing]

I don't know how we made it work just before. Okay. What if I open a new project? PDF we just created, now it's in preview. And I close Carbon, sketch a new window. And here I ask preview to copy this stuff. In two. Oh, here we go.

So this should have worked before. This is one of those miracles in demos. I don't know. Oh, actually I do.

[Transcript missing]

In case you want to know too, there are two different copies of preview on this machine. And the copy that works best for this demo is the one from Panther.

So now I'm back in Carbon Sketch, I can do whatever I want, like our QuickDraw rounded rectangle. Let's make it half transparent or so. And now I go back and say, I want to copy this whole page in my Carbon Sketch thing. and if this is the right copy of preview, then I can say new from clipboard and here it is. I have a new PDF that has our drawing added.

I don't know what I forgot now to show about this Carbon sketch thing. The interesting part for you should be, I'm in the following referring to it and inviting you to take the code, the source code, Copy-paste from there those things that you better copy-paste from somewhere where they already work. And then toy around and make experiences with... Getting some experience with Quartz drawing yourself. So we can go on with the slides.

Now we get into the meat. Haroon has already pointed out all the differences. I don't need to repeat all the details, but In this slide, you should start with reading the last line. The last line says, don't try to translate the usual QuickDraw idioms that we got used to over so many years into Quartz as is, because the differences are just too big.

In this slide, you should start with reading the last line. The last line says, don't try to translate the usual QuickDraw idioms that we got used to over so many years into Quartz as is, because the differences are just too big. This comes twice. It comes next to the changes of coordinate systems.

and the current transformation matrix and it comes with clipping and it would have to do with all other calls that you make in Quartz to change the behavior of the stroking and filling operations, the colors and many other settings and details. In QuickDraw, we had the model that the state was mainly preserved in the graph port. We could have accesses and then get and set the values. In Quartz, the model is different.

Everything is combined in this opaque graphic state, which you can push and pull back. You save it on the stack and you restore it from the stack. This makes for a nice bracketing thinking in all your drawing. And after the first couple hours when you get used to it, you really like it. It's a much better approach to keep your drawing code clean. And we have to come back to that more often. Now coordinates, the CTM, the current transformation matrix and transforms. This gives us an extra slide.

I remember when I encountered QuickDraw and the first time saw a coordinate system where by default the vertical coordinate went top down. I found it odd. It took me a while to get used to it. I didn't really like it. Of course, all of us, we learned very rapidly that this was the convenient way of addressing pixels in a window. It's natural.

It follows the order of the system. It's in memory and it has so many other benefits because we are used for resizing windows to resize from the bottom right and the top left. The content stays anchored to the top left. So this was the right thing. And over the years, we got completely brainwashed into believing that coordinate systems have to go vertically top down. Well, now they are again back up in Quartz by default. But... There is this general model whereby the CTM can be changed to whatever you want.

Not that you will get everything right, right away. It often requires some experimentation or some additional thinking. But it gives you the power to, for example, flip the coordinate system and shift it such that you can continue working as you did in your mental model of the QuickDraw coordinates. And HIViews, they do have their origin at the top left. They have set up the CG context that you get back in your draw control event such that you can just use this. They have had good reasons to set it up that way.

Still, it's one of those obstacles on the way to transition to Quartz, and I should point this out that you should not be surprised to spend some extra time just figuring out where the coordinates go and converting back and forth between a window position that vertically you have to count from top down in the QuickDraw model or the HIV model, and that in the default Quartz model, you have to introduce the height of the window. The current height so you can subtract it and get the distance from the bottom.

And this is a joke, math is hard. Math is not hard. It's just hard to get everything right when you use these transforms. I referred to it when I showed you the hit testing in Carbon Sketch, and I said there was this bug. I didn't notice because I hadn't tested hit testing under scaling up. Or when I tested it, it just happened to work by accident. And then I noticed that it didn't work. And it tracked it down to the following.

There is a one pixel bitmap context which I set up. And once you click in the window at some point, I move it to this point. And then I redraw the whole content of the window and check whether this point in this bitmap context has been touched. Very easy.

I set it to zero before and afterwards if it has been touched, it won't be zero anymore. Well, the problem was I applied-- and in order to draw window content, of course, I always have to concatenate this generic, affine transform that converts from the document, document, the document coordinates to the window content coordinates, depending on the position of the scroll bars and so on.

Tricky part was I got the order wrong. I applied this transform and shifted the bitmap context to where it belongs. Well, this is the wrong order. First I have to shift there and then apply the transform. It doesn't matter if you don't scale, but as soon as you scale, the transforms are not... It depends on the order. So this is just an example.

of the type of obstacle you are likely to encounter. This is a very generic slide just to tell you in order to get started. The CG context is more or less something in parallel to a graph port. We need something to draw into nearly all the Quartz APIs. Take a CG context as first parameter.

And the question is, where do we get it from in our first examples of experimentation with it? Well, you have learned over this week and for two years already that the direction for Carbon developers in the HI toolbox is to adopt the HI view architecture. And there you draw in this K event control draw event and the event record brings you the CG context ready set up, clipped with the coordinates as you like it and so on.

So that's the most convenient solution, the most convenient answer to the question. For everybody else, in the meantime... You have the window port coming back from get window port and you fill it into the QDBeginCGContext call and this gives you the CG context as you have always had. This context, each time you make this call, is a default context. It's a fresh reset context as if you created it from scratch new.

But of course, now that we promise not to use any QuickDraw in our window drawing, we do it just once at the beginning, and then it's always our context. I mentioned the bitmap context in the case of using a one pixel wide bitmap context for this hit testing business.

And we created PDF data in Carbon Sketch, so we need to create a PDF context. The equivalent in QuickDraw was to call open picture, then do some drawing that gets recorded, and say close picture to get back the picture handle. Well, in Quartz, we just draw into a PDF context.

And for printing, well, this bracket of begin-cig context and end-cig context works. David Gelbman here has done everything that needed to be done for that. But preferably, it's better to let the printing system know right away that we only use Quartz drawing. And up to Tiger, it was a little bit, I found it unintuitive how to do it. I couldn't figure it out by myself, had to go back to David and ask him. And so in Tiger, we get something that's much more clean and intuitive. And before Tiger, you go to Carbon Sketch and copy-paste it out there for your printing.

So, the first major chapter, what do we do with all those region handles? You have heard probably some references to region handles being bad in the HIToolbox presentations already. One thing is a given, there are no region handles in Quartz. Regions in QuickDraw are being used either as very general shapes that can be drawn and filled and painted and what have you, or they are used as masks.

For example, its last parameter in a copy bits call, a mask region handle. When moving to Quartz, these two different usages are being addressed by different ways. The generic shape, very naturally in Quartz, is described by its contours, so a path. And for masks, Quartz has the alpha channel. The question is, how do we put this in? I will come back to that. And the other bullet points are going to have their own slides as well, so we just flip over.

The major, the first time a QuickDraw developer encounters regions probably is to clip as a clip region, set the clip to something. And in QuickDraw, these functions, clip to the rectangle or set the clip, of course, replace whatever was there as previous clip in the port. Whereas in Quartz, the corresponding called CG context clip that takes implicitly the current path intersects with whatever the previous clip was.

The first time I learned about this from my new co-workers when I joined the group, I said, huh, I don't like this. Well, of course, it's easy to get used to it. And again, once more, CG context save G-State, then you clip to what you need, and you come back with the closing bracket restore G-State.

And so you're always in a clean situation. Still, in the first hours of experimentation with Quartz 3D... If you are like me, sometimes your drawing won't show up. The first reason is you've got the coordinates wrong. The second reason could be that you clipped and that your drawing is away from what you want to clip out.

And then, so I was wondering, how can I debug this? How can I determine if this is the case? And there is this call that I just wanted to point out. CG context get clip bounding box. This helps in most cases. Because there is no way to get the current clip back as a path. And while we're at it, here's another hint. I discovered this only during development of CarbonSketch.

I needed to clip the drawing to the portion of the window content outside of other controls. The scroll bars and this pop-up for the scale. So I said, well, nothing easier than that. You just take the path for the whole window content rectangle and then you subtract the paths that describe the contour of the scroll bars and the pop-ups.

Problem is, the CG context clip uses the winding number rule to determine what's inside and outside of the area. Which means, as the little arrows should indicate, the rectangle that gets subtracted from the area should have the opposite orientation in the contour. Now that's a little annoying when you have to write the code because you have to write at least four lines instead of just one line to add the rectangle to the path. Unfortunately then, I learned that there was the CG context even-odd clip. And so now you can just add the rectangles as they come, and the even-odd rule does the right things and you can clip as you want.

Here's another subject. If you never bothered about understanding really what happened in begin update and end update when you redraw your window in response to an update event, you don't have to listen now and come back for the next slide. The story is that Originally, in the Mac Inters toolbox, there was this concept of invalidating little regions in the area that needed updating, and by the time you got called with an update event, You didn't have to bother clipping your drawing to whatever needed to be redrawn.

It happened behind the scenes, automatically. The HI Toolbox keeps track of whatever needs to be redrawn. It keeps track of the update region. And this trick with begin update used the visual region, this region in the graph port, to achieve this. Because Quickdraw obviously has to clip to all this.

Now, if you carry this model over, just to fix the ideas, assume the window content is mirrored in a G-World. And what you are doing is you update the little areas in the G-World as the need comes up in your application. And then each time you need to refresh, every so often you just blast with a big copy of it the whole G-World onto the screen. And you rely on the benefit that automatically this big copy, every little bit of operation is clipped out to what really needs to be transferred.

If you would do this in the same way with Quartz, then you might have a bad experience, performance-wise, because this begin update mechanism, Quartz doesn't know anything about it. There is no visual region in the port and it just doesn't come in. So each time you would redraw the whole content and that's not what you want.

Well, of course, HIV use, they address this. As soon as you adopt HIV use, again, you don't have to worry about anything at all anymore in this matter. And in other cases, it's one of those examples where... We need to rethink the approach and replace existing code or the existing model by some optimizations for this purpose. Now we come to regions as masks.

Here is the Traditional QuickDraw model to create a mask. You copy bits into a one-bit off-screen, and if you're not happy with the way colors get mapped to black or white, you put in a search proc, and you get precisely the region that you want to obtain as a mask when you call bitmap to region.

That's not how you can do it in Quartz. And to begin with, masks are by design meant to be in the alpha channel. So how do you get these mask bits into the alpha channel? It all depends, of course, on what your specific application and your specific goals and needs are there.

If it's something that you can do ahead of time and then store, the proposition is just do it once and for all, keep the alpha mask up to date with what you want, and you have a picture that you can use as is, and no need for mask region handles at all anymore.

The other proposal is to tinker around with the pixels directly in a bitmap context. The bitmap context gives you the base address, gives you the row bytes, and you can basically work with it as you are used to with the pixels in a G-World, in a Pixmap. This is not really a satisfactory answer either, I know. And that's why for Tiger, the API has been extended in this perspective. And now you can call CGImage, create with mask, and CGContext, clip to mask, and in both cases the mask is a deep mask. So this should help. Hit testing, I mentioned it several times already.

Often QuickDraw would set up the region where it wants the point to compare against if it's contained or not. But the trick with drawing the content and clipping it to the point where you want to check whether this point gets drawn has been around since the beginning of QuickDraw. It was one of the first tricks that I learned back in 84.

So it's still good. And as long as in Quartz we don't have the CG path contains point for a G-matrix solution and some accompanying utility functions there to make this useful, really, and it's there starting with Tiger only, you would have to look at the way CarbonSketch does hit testing. Now would be a good time for a break. We are switching to a new chapter, but Travis is scared, so I better continue.

We are going to copy bits. I think some of you came to us long ago already when QuickDraw and Quartz were opposed and compared and when you were invited to embrace Quartz. And one of the first reactions was, what do I do with all my copy bits calls? There is no copy bits in Quartz. Really, there is CG context draw image and it will have to do. That's all we have got.

Originally, the general functionality is not there. And for good reasons, again, if you think about the fundamental differences in the imaging model. So the first comment is, maybe you don't need so many copy bits calls anymore to begin with. For one, very often the usage of copy bits out from off-screen keywords and so on was to work around the fact on System 9, on pre-System 10, that Windows were not buffered and just wanted to avoid flickering.

We wanted to composite things one by one before they could be brought to the screen. Well, now with more experience about how everything works on X, in many cases, we have still code that is not necessary. We can use the compositing feature in the Windows to our advantage and throw away much code and many keywords.

ImageRefs also, they stay around if you leave them around and if you learn about the rules of using them, they are much more convenient. You don't have to set up and juggle around with so many offscreens in general anymore. But in principle it's true, the tandem of a G-World with the copy bits in terms of a cached content to be brought to display corresponds to a CG bitmap context and a corresponding CG context draw image. There's a link in between, you need to set up a data provider for the image. It's not really as easy as it could be. It takes probably more than half an hour to really learn it, how to use it the first time.

And there are still some restrictions. We should never forget that here the source pixels of an ImageRef are immutable. You cannot change them once you have this. You can, but you might not be happy with the results. And there are some other missing conveniences, at least up to Tiger.

Now we can create an image with a sub-rectangle. And if you have been on Tuesday at the session where all the new Quartz features have been introduced, then this is just a way of repeating it and hammering it in. The image can be created directly from the bitmap context, no intermediate tinkering around with data providers anymore. And for Tiger, because of the motivation and the needs that came up with hardware acceleration, a new concept, the CG layer ref, that is particularly favorable to cache drawing that then gets brought to the screen.

The missing transfer modes, Haroon has mentioned it. We don't have a precise equivalent for the arithmetic transfer modes and everything, but there are new features, new facilities, new possibilities in the PDF blend modes, again starting with Tiger. And also, because going forward and inviting all you Carbon developers to transition to Quartz, we are going to cooperate much closer with HIToolbox and make all this blend together. And one of the functions that's there, for example, is HIView create off-screen image. In many cases, you need to have your view and keep the content as is in an image ready. So there it is.

Oh, yeah. Progressing nicely. Picts. QuickDraw had Picts. Quartz has PDF. It really doesn't make sense to hang on to the picts when you move your drawing to Quartz. And as I brought up here in the second bullet point, we need to start supporting copy and paste. Only the PDF format really captures all the details, all the finesse of Quartz drawing. There is, has been, the call QDPickDraw to CG Context. It draws a pict into a CG context, whatever the CG context is.

Well, this code has to convert, has to translate from the QuickDraw drawing model into the PDF drawing model. And that's potentially a lot of work, which means it might be a performance problem if you call this many times with many pictures and so on. In this case, the workaround we recommend is, well, just draw it into a PDF context, hang on to the PDF data, and use those from then on.

And one step further, if you have hundreds of pictures, I know it's not trivial, but consider moving them over in the same process. In particular, if you know that... As in the last line, that the picture that came out compressed from Photoshop actually is just a wrapper around JPEG data that get decompressed by QuickTime through a QuickTime opcode. Think about all the machinery that has to be put in place to get through. It really doesn't make sense anymore when you approach the Quartz API where you have CG image create with JPEG data provider right away.

So just keep them, the JPEG data themselves. Before there is this line that says some pictures don't convert well. Of course, we know they don't print well either. There are some of them are still around and you need to convert them anyway. Probably the trick is to just draw them into a PIX map and then create a new picture that's just plain pixels.

So back to the copy-paste business. I hate bringing up source code on a slide. This is just a list of some of the calls. They're all a little bit lengthy in spelling. You have to set up the PDF context to draw your content that has to go on the pasteboard into it to capture the PDF data, and then you can bring them up. And the other comment is there is this com.adobe.pdf literal. Finally, in Tiger, we get the symbolic constant for that. It's not too early in the universal types.

and pasting is a little bit longer too than this just single call. The recommendation is, that's why it's there, CarbonSketch, look at it and go through and probably you can copy paste a lot of the source code, but please start adopting copying and pasting PDF data. We need to get there.

Another chapter in the story of transition into Quartz is color spaces. You start coding with the Quartz API, don't know yet how many calls are there and which calls are there and what you have to do. You set the bitmap context and you look through the parameters that you need to provide and suddenly you need to provide a color space.

We didn't have color spaces in QuickDraw, we don't know what it is, so we look at the file color space dot h and we search for a way to get the color space to plug it in as parameter. And my first The solution was to just grab the CG Color Space Create Device RGB because it was the simplest one and it sounded plausible enough that that's what I wanted. And then comes one day David Gelfman again and says, oh, don't do that. I will show you, I will give you all the code.

That's how you have to do it to use generic RGB color. And remember when I showed you the blue pixel that actually, by the time it got to the screen, was slightly modified with some other component added in to do the right color matching? You get it for free. And because in such an application we would copy-paste content with colors or save to a PDF file, we are really interested in getting the correct colors all over the place.

So that's the model, that's the recommendation. Unfortunately, again, we had to wait until Tiger to get the real easy call that gives us this generic color space. Before, it required several lines of code, which I haven't brought up here. No point. I invite you to look at it in Carbon Sketch and to just copy-paste it out again, and then you get the generic color space for all your RGB needs.

Um, yeah, there's this last point, and we have had some discussions about it. Of course, color matching takes CPU cycles, and there are situations when you cannot afford it or when you really are hurting because of this fact. In some extreme cases, you only go to display, you only have some specific needs. We are not really perfectly well prepared for the situation, and that's why we promised a tech note sometime soon that addresses all these questions.

to bring in this new concept of color spaces. Probably I should have also pointed out that as it's written on the slide, for Tiger the behavior is bound to change the behavior of device RGB. The device RGB color space So you're going to get different behavior between Pantheon and Tiger if you already use the device RGB color space. From Tiger on, it's likely to be color matched. So in summary... There is stuff that gets left on the way during this transition. Those infamous QuickDraw transfer modes, all 173 of them, or I don't know how many.

Well, we cannot pixel by pixel reproduce everything that QuickDraw did. It just doesn't make sense. Time goes on. And as you can see on the user interface of Mac OS X, all those applications that don't use any QuickDraw, you can't live without those. It looks different. We have new ways of selecting, of drag-selecting something by using a grayish transparent overlay window, for example, if you like that.

And if not, in Carbon Sketch, I still use the marching ants frame for drag selection. With overlay windows, it's really nice how you can achieve effects which would have been extremely difficult to reproduce in QuickDraw. If you remember playing around in Carbon Sketch and creating objects and... resizing them and so on, it looks pretty good by taking advantage of overlay windows, which you could conceivably even stack for special purposes and special needs, and using transparency when you're drawing into the overlay window so you can still compare with what's underneath.

And then we have this PDF blend modes. I haven't looked closer at them myself yet. We will see what we can do. The possibilities are richer than whatever we had known in QuickDraw. The Graphport has this bottleneck Prox Concept and every QuickDraw developer was proud when he first hooked in there and achieved special effects.

and we got used to it. They are not there anymore, there are no bottlenecks in Quartz. In Tiger, we have this new feature of being able to scan and get called back for each opcode in a content stream, a PDF content stream. This is in... it's not equivalent, it's much richer.

It depends all on what you try to achieve when you're hooked in the bottlenecks. In most cases you don't need to begin with anymore in the Quartz drawing model. But if you really want to get very close control of everything that's going on drawing-wise in your application, that's the way to go. And as Haroon pointed out, some pieces, they are lost forever.

In exchange, I thought I should point out how much you win. Again, so that's a little bit of propaganda thing, but just right after the downer of what you are losing. There's so much more excitement in this new graphics model. You can do things that would have been extremely difficult to achieve them in QuickDraw.

And you can see how often we refer to Tiger with new APIs that are there to make the transition easy and comfortable. We have finally a lot of new documentation, we have the new sample code, more is to come, and I'm personally ambitious to make Carbon Sketch into something that should respond to all your questions. So bring the feedback, bring the requests, bring the criticisms. Performance, of course, has been an issue from the beginning.

If you set out and set up a Performance, of course, has been an issue from the beginning. If you set out and set up a You will find still today cases where Quartz is slower and sometimes quite substantially. On the other hand, if you measure your time in your application percentage-wise of the whole processing time, which percentage is used for drawing, for display, and which percentage is used for everything else in the system.

And if it turns out that you spend about 10% of your processor time in drawing, then you can put it in perspective. It's in many cases where you think it's, the performance is a problem, it actually isn't. And then there are cases where it is. And I will come back to that in a couple of minutes.

So the message here, which we repeat, QuickDraw is an obstacle against hardware acceleration. And we want to take advantage of it in the future as it comes. So QuickDraw really isn't a good citizen anymore on the system. And then there are some other recommendations. I don't even need to comment on them.

You know, I just copied them over from the documentation that we have about performance. And the concept of CG layers in particular bears repeating. It's something new, and we want to just emphasize it that for the future, that's really something to-- Look at. Yeah, here's the time when I come back to the performance question.

Can we flip to the demo machine, please? I think most of you have seen it already over this week, and I'm entitled to show it once more, one last time. Some of you may remember who have been here two years ago that I showed it two years ago.

These are 88,000 line segments. They come from Jean-Paul Armand, developer of CAD program. He had trouble on Mac OS X with QuickDraw because QuickDraw line drawing was so much slower than on Mac OS 9. So two years ago for Jaguar, I compared what you can do and explained what you can do to make it competitive with Mac OS 9. And I was proud of it. And nowadays, it's just pathetic if you flip to software rendering in Quartz.

You might ask, why didn't I show Quartz 2D two years ago already? Well, because two years ago it wasn't so fast. It was still slower than QuickDraw. And this is only progress that has been made within Quartz in software rendering. And you probably have seen the hardware rendering case. And it becomes, it's not even funny.

I mentioned some other things. Again, I think two years ago I had something similar to this.

[Transcript missing]

The way I set this up is I install a timer and measure the time that's used for actual drawing. And then everything else, so here in this case, drawing time in the system is 7.5%. With Quartz, what if I do QuickDraw? It's 7.7%. And of course it would fluctuate if we would repeat.

So this is nearly the same, it's practically the same. Why? Because this is just copy bits on QuickDraw, and on the Quartz side, it's just CgContext Draw Image because I set up this image ref with the pixels from the off-screen G-World. Copy bits in QuickDraw as often as it can just passes the job off to Core Graphics and it ends up resizing the same code. So no wonder they are about the same performance.

Then I tried to bump up The percentage of drawing time. Each frame I just repeat it. I repeat it to saturate the machine such that it gets more work to do. And you notice it gets already slower. It's already suffering a little bit. The priorities in scheduling kick in. And I could bring it up to about 90% and then the system refuses to let me take more CPU.

So I get 16 repetitions per frame, drawing time between 50 and 60%. If now I flip to Quartz-- 55%. The behavior is not always reproducible. What I meant to show was that in many cases, and maybe I just went too far, it turns out that Drawing time in Quartz becomes more favorable as you put more load on the machine. Well, as it happens, it's just not so spectacular anymore now in this case.

which means I don't have to explain or to comment about it. And then comes another case, again which is purely artificial. It goes back to this idea that you do a big copy bits from your off screen, but you clip out only little areas. What I'm doing here is, it's the same model as in the bull's eye before, but I'm clipping each one to the nine little rectangles. And in between each frame, I change the content of these nine little rectangles.

The idea is that you say you have some window content that reflects some hardware input in real time and you want to display how it changes. So that's how you would do it in QuickDraw. You have this off screen, you twiggle around whatever needs to be updated, you do one big copy bits call to bring it back on screen. And same thing, I wanted to see how this compares with using Quartz and QuickDraw.

And it turns out that Quartz looks a little bit unfavorable in comparison to QuickDraw. And maybe this was the case which I remembered where bumping up the repetitions suddenly made Quartz look much better. See? Quartz takes 9% drawing time by 16 repetitions. QuickDraw takes nearly twice as much.

So here we can comment about what's going on and how come that as soon as you put more load, more graphics load on the system, Quartz starts looking better. The previous example probably was just too trivial. There wasn't much to be gained. And here it turns out that internally the architecture of Quartz, the way it's designed and implemented is just so much more advanced than QuickDraw, which is tied to a design that had to match, that corresponded to hardware reality of more than 20 years ago. I think I should stop at this time. Let's go back to the slides once more, please.

I come to the conclusions. Of course, it's not trivial. Of course, it will take work. And we need to learn something new, and we need to rethink certain things. I feel it's a good thing. I feel rejuvenated since I started learning something new. Maybe this can entice some of you as well. And above all, it's really the right thing to do. Think about the tailwind. It's good karma. Trust me.

and I'm repeating what Haroon offered. We are here to help. In particular myself, who has a background in developer technical support. Long ago, I just cannot help it. So, see you in the lab afterwards. I will be there together with the other members of the group and we want to help you, bring you over to Quartz. Travis Brown is the man to talk to with everything, bring all your feedback, all your requests.

As I mentioned, we are proud of all the new documentation we have now. You will find everything down from the reference library, graphics and imaging. There is sample code and unfortunately I don't have the precise path to Carbon Sketch, but Carbon Sketch is not alone and we are working on making it richer and we have the Quartz dev mailing list.