WWDC2001 Session 132

Transcript

Kind: captions Language: en good morning everyone I'm Travis Brown and the imaging technology manager for Mac os10 and I want to welcome everyone to session one 32 which is graphics and imaging tips and tricks what we're gonna be talking about in today's session or two things the first is something we think is a great opportunity for carbon developers and that is to better define for you the interaction between courts 2d and quick-draw and we think there's a great opportunity for carbon applications to look at using some of Mac OS tens very powerful graphic graphic technologies to deliver things such as PDF support you know anti-aliased graphics all sorts of interesting possibilities for features for your users secondly what we'll do is we'll concentrate on performance issues with courts in general courts has a piece that we've talked about a little bit during this WWC called the courts compositor which essentially abstracts you from the screen unlike Mac OS 9 and earlier where you had direct access to the screen you don't have that in 10 and therefore there's a little knowledge we need to communicate with you to it with regards to how to optimize your application in this environment where your pixels are essentially being buffered by the quartz compositor so I'd like to get started because we have a lot of information for you today so let me introduce David gelfman he'll continue the presentation from here hi I'm David Gilman can you hear me okay I'm David Gilman I work in the graphics to imaging group primarily on printing but that sort of takes me off into some other area so I get to do a little bit of work in quick-draw a little bit of work in the courts 2d system so as I was lying awake in bed last night thinking about this talk and sort of anticipating it you might say I thought about the first developer conference that I came to in 1987 and at that conference Apple had just recently introduced the Mac 2 and was new technology was color quick-draw and Apple had sort of hidden in the background some new stuff they were gonna show us it was something called multi finder so anybody remember that so yeah so to me it's really exciting to be here talking about something besides quick-draw input most part core graphics quartz 2d as we call it and here's the agenda for today we're gonna start talking about how you can use quartz do 2d in your carbon-based application on Mac os10 the cocoa people for the most part get it free it's easy to use it it's you know they have cover routines for a lot of the functions you might use but we're going to talk about how you can use it in your carbon application that sort of leads us to talking some about printing on Mac OS 10 specifically we're going to focus a lot on the carbon printing graph board on Mac OS 10 it's a different kind of graph port than you've seen before on Mac OS and I think you'll see that we've done some interesting things there then my colleague Ralph Brunner is going to follow up and talk about performance tuning of your application when you use ports or just when you use anything in carbon and cocoa so just as a way of sort of getting started as you've hopefully seen during the conference quartz has very powerful 2d capabilities the imaging model of the quartz 2d system is consistent with the PostScript imaging model which is a very powerful mature imaging model for those of you that have been using PostScript generation yourself where you been using postscript picture comments we think that you're going to want to move over and start using quartz 2d instead of generating your own PostScript it's going to have some pretty significant improvements for your application that is on all the imaging devices when you go to print you're going to see really high quality rather than the quick-draw drawing that you were doing when you were printing to raster devices in the past when you're using quartz 2d you're going to see the really high quality now this talk is going to assume that you have some familiarity with quartz 2d we're not going to talk all about the imaging model I am going to touch on some things that are relevant specifically for people they're probably coming from a quick-draw base background and this is just a reminder kourt's 2d and quartz the system is a Mac listen Mac os10 only technology it's not something that's in carbon lib so I'm going to start by getting a little demo so if we can get the demo machine up over here so the first thing I have here is just some really simple drawing that we've done some of this is drawing with quick draw some of it's drawn with quartz 2d yeah and I've got the little pixie application here which is just a sort of a fat bits equivalent where we can magnify the screen we can come over here and look at hopefully people can tell which is the which are the lines that are drawn with quartz 2d and which of the lines that are drawing with quick draw the quick draw line the you know the ends of the lines have that square pin that hangs down you can look with the pixi application if you look over on the right-hand side here where we can see how jagged that line is if we move over and we look at the next line over here of course we're looking at a line that was rendered by quartz 2d if we look at the end of that line you can see it's a nice butt end cap it's antialiased along the line I don't you know as you're far away you probably can't see the difference in quality but of course if you're looking at a screen and you see that anti aliased line it really looks a lot better a lot sharper and then of course just to just for fun I did a little bash line that something is trivial to do using quartz to D now this middle portion here I have a couple of ovals and I think as you get far away it's a little harder to tell but I'll look at it here with pixie and you can see now this is actually not an oval that I've drawn using quick draw what I've done here is I've made an oval mask region that I use to clip or as a clip region that I use to clip some drawing I just have a big rectangle that I'm clipping through an oval of course you get essentially the same result if you do the oval itself but if you look at the edges here you can see how jagged it is if we look over here what I've done is I've set a clip that's the same oval using quartz 2d and I've just drawn the same rectangle and you can see it's nice and antialiased along here and again on screen you see this jagged behavior with quick-draw and of course it looks nice and smooth now one of the reasons I did this is a clip rather than just drawing an oval when you go to print if you've done clipping what we do is we're going to take the if you've done clipping with quick-draw we're going to take that region clip that you've supplied and we're going to turn that into a path the courts 2d path and when we do that well regions are device-dependent they're resolution specific so to do that what we're going to do is we're going to make a little path that's a bunch of jagged lines just like that and that's what you're going to see now if you draw using courts 2d what you're going to see at print time is you're going to see a nice smooth clip so of course you know you wouldn't really draw an oval this way but this is just to give you an idea of what kinds of things you can do with courts 2d and how that actually translates into your real imaging the last thing here I've got some text here on the left-hand side I've drawn text with quick-draw and on the right hand side I've done context with courts 2d one of the things that especially small point sizes it's a little hard with pixee to see I hope you can see it when you display it the difference of course the text with courts to D is antialiased nice clean-looking text one thing that's really nice is the weight of the text as you get go through the point sizes with a sort of waterfall text the weights nice and consistent looks real smooth when you look with quick-draw you tend to see sort of the chunky gradations as the text increases in point size on this page what I have is a couple different things first of all I mean I've already shown you we've mixing courts 2d drawing with quick-draw and a window here but I just we've got a picture here that I'm drawing with quick-draw using draw picture and I've also taken some text at using atsui text drawing and we can apply the usual courts 2d transformations to the coordinate system get different effects I haven't done anything particularly fancy but it's really trivial to rotate text you want one of supplies other special effects you can do that one thing I put on here because I want to emphasize something I think is really important we'll talk a little bit about in just a second about the details of how to do it but this zebra picture here is a PDF file that I've just drawn on my page here and the zebra that's rotated I've done the same way is just PDF that I'm drawing I've rotated the coordinate system before I've drawn it using courts 2d but I don't want to emphasize this really easy to support PDF in the system it's just essentially like drawing a picture very easy to do and you know even if you're not thinking of adopting some of the other things that we're doing with courts 2d consider seriously adding PDF support to your application I did a little thing in here for fun excuse me which is I applied a clip now to the drawing before right before I actually do that last zebra so I drew a text character but before I actually do the text character I set the text rendering mode in courts 2d to be a clip then after I did that I drew the zebra I just drew the PDF it's really easy to get these kinds of effects ok so let's go back over to the slides can we go back over to the slides please thank you okay so I told you how easy PDF import is I'm going to show you how easy it is now of course this little example is importing from a file I've assumed that you already have an FS ref that points to a file if you don't have an FS ref but do you have an FF spec there's an easy way to get an FS ref okay from the FS ref you can create a URL CF URL this is part of corefoundation once you have a you a CF URL you can make a call that's part of core graphics part of the courts 2d cg PDF document create with URL you get what's called a PDF document from that that's the doc that I have here from that we can get the media box which is essentially the bounding box of the graphic here get the bounding box for that and in this case I'm just going to draw with that bounding box into my context which is the CTX parameter it's the courts 2d context draw the document that's it that's to draw the first page of a document you can also find out the number of pages in the document so on and there's other bounding boxes that you can get besides the media box but that's it now if you say oh I don't have my data as a file on disk or a URL really because you can really have URLs here of course if you were in the courts to the discussion you would heard about data providers where you can have there's a generalize mechanism so you can provide the data for the PDF document so this was just the simple one for a file so again straightforward use of courts 2d drawing even for a quick draw based application okay so now how do I get started I'm really hyped about doing this let's get to it okay so the first thing of course is you need to have what's called a CG context in order to draw into all of the courts drawing routines to expect that you're going to draw into CG context it's an explicit parameter that you provide to the drawing routines there's no set port like there is in quick draw you're going to pass in the context to all the drawing that you do so the CG context is something like you might think of as a courts drawing port instead of a quick draw draw report now one thing that's really important to realize is that a CG context has a graphic state that's associated with it the quick draw graph board does also it has the usual things the pen size the font the font size the background pattern the foreground pattern you know all of that stuff well there's similar kinds of things that are part of the graphic state of a CG context such as there's a separate fill color and a separate stroke color there's a separate fill color and Stroke excuse me separate fill color space and stroke color space there's a clip there's a line with those kinds of things all those parameters are on the cg context and now when you're drawing when you get one of these things from quick draw or if you're using quick draw at the same time that you're using a cg context that you got for for a graph port you should realize that those graphic states are completely independent there's no sharing of the graphic state if you go and you set a color on the quick draw port that's not reflected in your cg context so when you go to use courts 2d you're going to set the parameters in the courts 2d context for your drawing okay so let's start just I think some real basics and like I said I'm not going to talk a lot about how you use courts 2d but I think these are relevant things for developers coming from a quick-draw background the first thing is that the coordinate system is based on the PostScript PDF coordinate systems it was a fundamental decision by Apple to follow the PDF imaging model this is the coordinate system in the PDF imaging model standard Cartesian coordinates X goes to the right across the screen or across the page Y goes up and the origin is in lower left corner of the window or of the port rather or of the page okay so this is what it looks like this is the relationship between the coordinate systems the quick dark coordinate system the courts 2d coordinates this is sort of the standard relationship when you get a CG graphics context report the quick draw coordinate system as always top left corner courts 2d bottom-left corner y going up now the relationship between the origins is initially at least if you haven't changed the port origin the relationship between the origins is based on the port crack type that's the height of the port okay so there's a couple issues if you're used to drawing with quick draw apps are used to that quick draw coordinate system where it's in the top left corner of the port the vent coordinates are returned in the quick tile coordinate system in some apps when they switch over to using the the courts 2d imaging system they sort of want to keep all along keep using that top left corner with the coordinate system flipped okay well there's a couple ideas one is you can actually transform your coordinates on the fly yourself if you want to the relationship between the quick draw coordinate system and the kourt's 2d coordinate system I showed you on the picture before you can calculate the port bounce height you can compute from a given quick draw Y you can compute a a Y for that would be suitable for courts 2d coordinate system drawing so you can do that yourself now there's some disadvantage of just doing this kind of transformation and one of them is that as you start rotating and scaling the courts 2d score system something you can't do with quick-draw now this kind of transformation gets a little messy because now your coordinate system is transformed so just some other ideas here's what I called approach B which was using courts itself to do coordinate transforms for you now when you draw with the courts to coordinate system you're drawing in what's called user space and that's malleable by the application you can scale it translate it rotate skew it do whatever and courts 2ds always doing transforms on user space coordinates that are supplied by your application when you draw into device space or into the space of the actual device you're drawing on via the printer be it on screen whatever now you can piggyback off of those transformations that course 2d is already doing for you by simply making your own matrix that you can cat to what's called the CTM the current transformation matrix from user space in the device space you can piggyback off those transformations and here's what that's what I'm doing here so I make up a transform there's in CG affine transform H there's a whole bunch of stuff about transforms you can read about and you can make a translation transform in this case I'm translating by the port downs height that's that that's the thing that connects the quick thar origin to the core graphics to the courts 2d origin and then in addition I'm going to do a further transform on that transform by scaling it by flipping it so I made Y minus y so at that point if I actually take that transform that I built up this QT transform that I built up and I can cap that to the coordinate system that's already part of my context here represented by my context parameter here now I have a flip coordinate system and I have the origin of my quartz coordinate system in the top left corner of the port okay well it's all great start drawing your graphics you do your line art you do your ovals you do whatever well wait a minute when I go and I start drawing text using out Sooey I find that it's I got a little problem here which is my text is flipped because we flipped the coordinate system and when you draw text with that soui into a into a CG context they're expecting upright coordinate systems and that's learned okay well it's a tips and trick so here's maybe something you can consider you could actually modify the approach a little bit it's a little bit of a pain but what you can do is before you draw your text you unfit a system so normally you're going to draw into a flip coordinate system but before you go drawing text you're going to flip it the only thing you have to do is unhook the coordinate system at that point you want to use minus y coordinates instead of Y coordinates because now we're gonna you've got the origin in the top left corner and Y goes down so we'll be using minus y coordinates but that's what's involved there okay now let me just emphasize the only reason you would need to consider using some of these approaches is if you want the courts 2d coordinate system when you go to draw to match the quick-draw coordinate system they're familiar with if you're comfortable drawing with an upright coordinate system go for it don't bother with all of this one other thing to say is in CG affine transform dot H in the header file there are some additional transforms that let you take points and transfer them through the matrix to get a new point that's transformed so if you'd rather do your coordinate transformations using CG by transforming the coordinates not by transforming the coordinate system that's part of the CG context you can do that yourself also let's talk just for a second about text drawing hopefully you've had an opportunity to go to some of the text drawing carbon text drawing sessions here at the conference we discourage use of the low-level quartz API for drawing text it's really not suitable for international text international text I mean if you've seen some of these demos and the kinds of things that people need to be able to do with international text all of that is layered on top of the courts 2d coordinates just the courts 2d imaging system but they are really providing the facilities for drawing international text so the recommendation is look at and use Atsui and MLT e for drawing text into a CG context and they've talked a little bit about how to do that in that in those sessions just to give you an idea of how straightforward it is if you're already familiar with using that so we draw text drawing you know that you're going to use a layout for drawing your text all you need to do is add a tag to that layout that's what I'm doing here in this sample code adding a tag to the layout then I actually draw the text the way otherwise whatever the tag that I'm adding just says that I'm adding a CG context and I pass a pointer to that context so I'm supplying the context to that Sooey now all of the coordinate system transformations and so on the color all of those things are used from the CG context assuming for example the color you haven't made as part of your layout okay that would override the color that would be in the CG context okay so I've given you a bit of an idea about some of the issues maybe of drawing with a CG context how do you get well there's a routine create CG context report what that does is you give it a port it gives you a CG context for them you can start drawing into that CG context there's a couple other helper routines that you may need to use one of them I can't say these without looking at them sorry sync CG context origin with port what that does is when you call that it resets the current transformation matrix on the context of the default that removes any scaling or anything that you might have provided it then resets the CG context origin so that it has that relationship between the port origin and the CG context origin so for example if you've done a set origin in in quick draw now you want to and you want to tell the CG context that you're using associated with that port that you've done that that's when you call this routine then there's also a clip CG context to region where you supply a clipping region and that will reset the clip on the CG context to that that you're supplying here ok so when would you do these things window resizing so you've made your window bigger or smaller you're gonna have to reset the clip because the VIS region on the window or the clipping region rather on the window it's gotten larger you want to sync that up you want to tell the CG context that you've got a bigger clip and then if you're scrolling or you for other reasons you change the port origin now you need to synchronize your CG context with the port origin okay all right well I'm mostly a printing guy so I've got to talk about printing what about printing so I've sort of divided up the kinds of applications these again or carbon applications I divided them up into three categories the first category is our favorite kind of application on Mac os10 that's an application that when imaging during printing the only thing that you're drawing into the printing port so to speak or the only thing you're trying to image is something or all the content is drawn using only quartz 2d so that's the first type of application so all them all the contents image with quartz 2d now you say well you know maybe I'd like to do that but I have all this legacy data that's I've got these pic files and I got to use draw a picture well we recognize that that's an issue and so what we're adding to Mac os10 coming soon is a routine that allows you to take a quick draw picture and draw that into a CG context and I have a little demo that sort of like doing that and you'll get a chance to see that now we want to hear from you about what other kinds of quick-draw content other things you're drawing into a graph board that hey right now you don't know how to draw into a CG context because if that's what's preventing you from moving over to courts we want to know what that is and we want to fix that and by the way you know you probably can do it we just need to give you some ideas about how to do it and maybe we can add some more convenience things in the future okay so that's the first type of application your application soon to be only imaging using courts 2d when printing alright second type of application is what I'll call a quick tour only out it's the vast majority of Carbon applications today it's what you're doing online when you were printing you were drawing with car quick draw in something in some fashion and then the third type is in a type that we want to talk about also which are applications that are going to mix their drawing so they draw with both quick draw imaging and courts 2d imaging at printing ok and that might be an application for example you say well I don't really want to move over to courts 2d but man I like this PDF import I really want to do that or maybe you want to do almost everything with course 2d but there's still a little bit of crypto stuff that you haven't quite gotten weaned off of ok so I'm going to talk about printing issues with these three types of applications in that order now before I do so I need to say a little bit I mean I know everybody knows about the printing architecture on Mac os10 and I'm boring everybody but it just helps me to remind myself how it works so printing architecture on Mac OS 10 it's really completely different than it is on Mac OS 8 9 we've totally rewritten the backend of printing the front-end of printing it's all totally different the api's are similar very similar for carbon apps but we've really rewritten the underlying printing system so a couple things that are important to know about it the printing system completely leverages quartz 2d when actually both imaging print time at spool time that it's built into the printing system all the printing that you do generates a PDF spool file is an intermediate representation for the graphics that you draw in your application it's the same printing port both for raster printing and for PostScript printing you don't have to worry about driver X and driver Y it's the same graph port has the same characteristics both of those regardless of what the back-end printing device is we're going to split out a PDF now the good thing about this I think all your customers are going to like all our customers are going to like is you're going to get high quality imaging on all printing devices ok so again I'm talking about an application it only does courts 2d imaging during printing now these are carbon applications and by default the printing systems set up so that when you actually start printing your document we're expecting to hand you a quick tour graph board because carbon quick draw that people think of them together that's the default graphics context that you get at the time that you go to draw is quick draw so before you actually start printing you need to tell the imaging system that you're going to use what we core graphics courts 2d those are the same thing so what I have here is we need to create a CF array that has one element in it and that one element is a CF string that we've predefined called KPM graphics context core graphics ok you're going to draw with core graphics courts 2d when you're imaging at print ton that's all you're going to do so before you actually call this routine p.m. session began document which is beginning the printing process before you do that you need to set up this array you need to call a routine that tells the printing system that's the format and that's the type of graphics context that you're going to draw with so you're gonna say p.m. session set document format generation with the print session you got when you created your print session and then you pass in you want to do format PDF which by the way is the default but you're reinforcing that and you're gonna pass in this graphics context array then you release that array because we hang on to it you release it this is a classic way of using corefoundation ok so now you've told the printing system that you're going to use courts 2d at image so how do you get your graphics context that's associated with the the printing system at print time well you ask the printing system this is just what you would do if you weren't using core graphics it's a little bit different because now you're saying okay I want the core graphics context from the get graphics context p.m. session get graphics context okay now you have a context of CG context that you can draw into using court student you can't draw any quick draw if you only draw into that courts 2d graphics context alright one thing that's different about the graphics context and the coordinate system this different than you might be familiar with with carbon printing that the the origin of the coordinate system is the lower left corner of the sheet okay now when you're doing carbon printing you probably familiar with the fact that the origin of the coordinate system is the top-left corner of the image buleria of the page so this is a significant difference not only is at the bottom left corner it's not the bottom-left corner of the image area it's the bottom left corner of the sheet okay now that's for your applications drawing only using courts 2d so what about your application that's drawing using only quick draw or some quick draw let's start with the only quick draw now as I said the spool file that we generate during printing is this PDF spool file now quick draw applications they don't know how to generate PDF so what we do during the printing system is we translate the quick tile imaging that you do into the port into the core graphics courts 2d drawing and we're going to generate that spool file for you now how do you actually get your graph port you do it the same way as you do you don't need to set call it you don't need to set this up before you start your printing but add after each page p.m. session begin page call after that you're going to go and you're going to get your graphics context which is going to be a quick draw port and you're gonna image into that now let's talk about that port because that port is completely unlike any graph port you've seen before it's something like a hybrid quick draw raster driver printing port and a postscript like graph board so I jumped ahead a little bit of second ago because we need to have PDF spool file of course applications that draw with quartz 2d drawing can produce that natively by just using quartz 2d directly however during print time we need to translate any quick-draw drawing that you do into quartz 2d drawing and therefore generate PDF from now this is true both for quick-draw pure quick-draw applications and also applications that mix both quick-draw and quartz 2d we have to translate the quartz the quick-draw portion into quartz 2d drawing here's that here's what that looks like you do your quick tile imaging calls we replace the quick-draw port bottlenecks with bottlenecks that translate that quick-draw drawing into quartz 2d drawing so that's that second box that blue box that's the translator that turns into quartz to the imaging calls and as you know we're hope you know by now the quartz 2d imaging system can produce from those draw those drawing calls a PDF file ok well the process of doing this translation is very similar to doing this kind of thing that we've done with Poe script printing with the laser writer driver for years the quartz 2d imaging model is essentially the PostScript imaging model what we've done is we borrowed techniques that we've used with the laser 8 driver to do this translation from quick-draw into the quartz 2d imaging model we've tried to get results that are consistent with the laser at r8 driver wherever possible because that's something that's very familiar to people we think that's a win for you and for customers all right so I'm going to talk about not only similarities with the laser r8 driver but also differences and again let me just say what we're talking about is the translation on Mac OS 10 from the quick-draw drawing that your application does into the printing graph port into quartz 2d drawing into PDF ok so we use that same general approach like we did for laser writer 8 we're using the same line layout algorithms that we use for laser writer 8 line layout algorithms are used because frequently in quick-draw the metrics are different in your quick-draw fonts and so on than they are in both PostScript for laser router 8 and in PDF so if you're using integer font widths for example well going to turn those into fractional usage of fractional widths on phones we do layout in order to adjust the differences with regard to images we have the same quick draw transfer mode support that we have in laser router 8 for one bit images we support all the transfer modes except the XOR transfer modes which we can't support for deep pix Maps anything deeper than one bit we support the source copy mode we don't support into the other transfer modes however coming soon we're gonna have support for the quick-draw transparent transfer mode transparent transfer mode is where the background color in the graph port is used as a transparent color so any pixels in your image that have the same color as the background color in the graph port they're transparent when you draw your image ok more similarities to the laser 8 driver we do pattern substitution so if your application draws with patterns which by the way you actually always are because the port has a pattern in there that's using for all your drawing when you do line art what we do is we map some of the patterns into great grayscale colors or Greg levels I hope this is clear what's happening here in the slide it's certainly clearer in the front of the room maybe than the back but on the top I've got several different patterns let's see what that looks like dot patterns and what we do is for certain combinations of the dot patterns we map those into gray levels so you can see a much smoother appearance in the drawing and by the way of course if there is a real pattern like there is in this brick pattern we're going to we're going to generate that pattern ok some other similarities with laser router eight we also support many of the picture comments that are supported during printing on Mac OS 8 9 so some of them are the text alignment picture comments text rotation and flipping polygon smoothing where you can draw with cubic Bezier graphics rotation where you can have different kinds of quick tile graphics and before you draw your graphics you can tell the imaging system to rotate you can't do this on screen but the printing system knows how to deal with that

  • lines fractional with lines so

something other than a normal pen sizes with fractions of a pen and also color sync support so on Mac OS 8 9 you could tag your data with picture comments that provided color sync profiles and we respect those and we'll use those color setting profiles to draw the graphics as calibrated route the calibrated color if you use those picture comments I have some examples of a couple of these things in the little demo I'm going to do so differences from laser 8 well I think the big one that probably many people run into is that PostScript picture comments are not supported when you're printing in this print graph board there's no way to take these PostScript picture comments and turn them into PDF without having a post crypt interpreting we don't have a postscript interpreter in the PDF printing system so the PostScript picture comments that you would generate are ignored they're dropped on the floor we don't do anything with them instead in this bit in this manner we act something more like a quick-draw driver what you might be familiar with on Mac OS 89 where the portion if you say PostScript begin and then you draw with some quick-draw and you draw some Posca picture comments and you say PostScript in a raster driver on Mac OS 8 9 uses the quick-draw drawing at that point and that's what we do here on Mac OS 10 because we're not a postscript driver we use the quick door representation so that also means for example if you have an EPS preview that you're doing you don't just want to say PostScript begin and omit a whole bunch of postal code and end you want to draw that preview image also and we will use that preview image instead of the EPS data ok well that's one of the big differences there's also another difference in something we think is better and hopefully going to help you that is we've added for the first time to Poe script type of driver we've added support for quick tour regions that is you can have a quick tour region that you click with that you fill that you frame arbitrary regions are supported now of course their device dependent and you might be unhappy with some of the results you get and that's of course of one of the reasons why we're pushing you toward using courts duty but we are supporting it so that's a good thing another thing is that we've basically fixed a bug which is that now when you draw with your patterns patterns quick draw patterns respect the port origin laser router a driver didn't respect the port origin when doing patterns we fixed that so let's say you had your ducks like this you had your ducks all lined up and you were drawing with the origin at the corner of the graphic with the laser eight driver we're gonna use the original zero zero port origin with the printing system on Mac OS 10 we're going to respect the port origin so you'll get your ducks in the right place okay let's move over to the demo machine so I'm gonna so I have a couple of images that I want to show you this is a little application and I wrote it's essentially leveraging this draw picture into CG context routine that I told you was coming soon in Mac OS 10 on the left hand side here I have a picture that I found on actually I don't know where I found this picture picture that came to me and this is drawn using draw picture on the right hand side in this window the same pictures drawing drawn using core graphics using quartz 2d it's essentially drawing through a port which has this bottle extra place as they would be during printing so I hope you can see some of these some of the features of this first of all we do pattern substitution let me use the mouse here to maybe point a little bit over here we this is a normal quick draw pattern that gets substituted with the gray level here all the text here all the Texas anti-aliased all of the graphics int aliased this is the quick draw version of course over here is the courts 2d drawing what else do we have here that might be an interest just anyway of course the goal here is at print time we want to get the best quality we can and we think translating this into coarse 2d is going to give you better quality even when you're using quick-draw so I've got a couple others oh one thing that's sort of fun want to mention one thing I added this little app is Oh a little save as PDF because this window on the right hand side here is drawn using courts 2d if I create a PDF context rather than getting the context for the window and I do that same drawing into that PDF context I get a PDF file so I'm gonna make it really easy to get PDF out from your applications here's another drawing oops it's a highway map that we got again here's the quick draw version of that and one of the there's a couple things that are shown here you can also see if I can bring this up here you can also see a pattern substitution going on here here's the quick-draw pattern over here is a nice smooth grayscale the lines of the map here are drawn using polygons but at print time the polygon picture comments are being used so we interpret those picture comments and now you get nice smooth lines not only an EI list but smoothed out because they're drawn as busy as all the text is anti-alias so if you look at the text in here over here text looks a lot better and oh and look here's some rotated text here it really is this text this is a bit image of course that's done is the quick draw representation but here it's really turned into drawing with it font okay I got one more so I mentioned about color see the left-hand side I've got a pic that's an image it's actually using this particular ones extreme example it's using the color sink picture comments and I'm drawing this with draw picture there is a draw a matched picture that will let the imaging system handle that with quick draw but I'm just using draw picture here and over here on the right I'm not using draw picture I'm using or rendering using courts 2d and it picks up the color sync picture comments and draws in the calibrated color space somebody's clapping good I like that okay well one of the things this is sort of tip you know like to add a few tips and tricks since that's the way we were advertised and one of them I think you might be interested in this is the PDF that we're generating for one of those graphics that I had and when you start to look you know if you're if you're familiar with PDF then you might be interested in looking at if you're not familiar might be interesting a little bit of the about the PDF that we generate however for performance reasons and file size wise file size reasons we're generating PDF that has many of the streams in the PDF file compressed it's using the flate encoding so here's the data that represents the the PDF data that's generated by the printing system and it's compressed well for developers we thought okay maybe it would be helpful to you if you want to look at that data to not have it be compressed and I wrote a little app here that's a printing preferences app that you know talked about a couple of the Preferences that are on here so by default the printing system is going to compress the PDF data as its generating the spool file and you can turn that off with this little application if you uncheck it and save that then when you go to print your PDF if you go to look at the PDF you'll see it's not compressed any longer you can actually look at it in clear text just another couple things about this particular application if you were in Paul Dan Voltz talked yesterday you learn that the printing system can generate something that's called a job copy for the PostScript data that's being sent to the output device so for debugging purposes it's not a save to save the PostScript functionality that a user would use but I know we in the printing team and I think a lot of developers appreciate the ability to see what PostScript is being sent to the printer as part of the printing path especially if you're generating your own PostScript in some situations or you just want to understand what's going on you can turn this on you can choose a location by default us and slash tab that location needs to be writable by all just because of the way the printing system is run you can set a new printing new location for these the files that get generated or based on the job name so you really do get distinct files for each print job and you can go and find them and look at them if you do need to now this last thing is a job status log printing status log rather and this is basically the data that's coming back from the PostScript printer module that gets logged if you turn this feature on and it goes into the temp directory so this would be a very specialized developer that would need this you want to see what's coming back from the printer from the PostScript job onto the PostScript printer module but you can also turn that on okay so I uncheck this and I'm gonna save that and I'm gonna quit this and I'm gonna go and I'm going to print and now this is something I do and I think other people might find this interesting also which is it's very easy to get the PDF from the printing system you just say print preview there's the PDF oh well I like to look at the all the time so what you can do here this is this project builder open drag that here it is open it there it is okay now remember I checked on comprar don't compress the PDF stream so here is the PDF stream from that printing okay so for those that are familiar with PDF file we're just drawing an image here we're setting up a coordinate system drawing an image but it's very easy to get that so let me just see if there's anything else I want to talk about I think that's it so go back to slides thank you okay so we've talked about what happens when you draw with quick draw and print let's talk about if your drawing with quick draw and courts 2d and doing courts 2d imaging during printing so I think the most important thing and the number of developers have run into is that this routine that I talked about create CG context report if the port that you have is the port you got from the printing system this routine fails you get an error you can't get a CG context from that port now the reason is is as I've talked about the printing system itself that's translating quickdraw graphics into core graphics drawing into courts 2d drawing the printing system share has a CG context associated with this translation that it's doing now if you start drawing into that yourself there's some synchronization problems that we have because we you know the printing system thinks that it owns that CG context and it can change the color and it can change the clip and it can do all the stuff in it if you start going in and doing those things we can't do our job so to work properly doing this we need to have careful state management of quick draw and courts 2d drawing at print time ok now we're working really hard to resolve these issues let's talk about what it's going to look like well we need to enforce some kind of modality into this to separate the drawing that you might do into this CG context from the drawing that the quick draw to courts 2d translator would do it print time so we've added some routines or we are adding routines to Mac os10 in the future these are not in Mac OS 10 version 10 point oh point X and the routines are QT begin CG context and QT NCT context now these routines unlike the get context report these routines work both for screen drawing and for printing so if you're only doing screen drawing you can keep using this CG context create context report but if you're doing printing you want to use these new routines now in order to enforce the fact that we have this modality where you're doing your cg drawing and then you're doing your quick draw drawing and then you're doing your core graphics drawing and then you're doing the record quick draw drawing in order to enforce this when you actually call these routines on a port we take the bottlenecks in the port the imaging bottlenecks and the port and we make them non drawing bottlenecks okay so both on-screen and printing quick draw drawing that goes on in between the Qt begin CG context and qtn CG context that quick draw drawing is going to be ignored one other thing is you're when you call CG in excuse me qtn CG context that's CG context that you got from the beginning routine goes away you have to get a new one next time you want to do your drawing with courts 2d okay it sounds hard it's not here's the way it looks so you start you don't have a context for the you don't have a context to draw into you have a port you call QT begin CG context passing the port you pass in a point of your context you get a context back so now you go and you do some core drawing using courts 2d so in this case I'm just using the CG context draw a PDF document similar to what I did before and drawing a PDF document so you're done drawing your PDF document you're done for now drawing your courts 2d content and you now we're going to draw some quick talk content of whatever sort you call qtn CG context you pass in the port you pass in the pointer to the context that you had that you got from the beginning routine now that value that you get back from this routine that context is null you can't draw out of that context any more if you have another way of hanging on to that you're gonna be really surprised when you try and draw into that okay so now you do your copy bits or whatever other quick draw imaging that you need to do and it's time to do some more core graphics drawing some more drawing with quartz 2d you go you get your context again now when you go to get the context again it's important to know the graphic state the G state on that context is it is reset to an initial graphics initial G state so it doesn't remember whatever transformations you might have done between the last time you use to begin and CG context okay so you get it get it again you do some more courts 2d imaging and so on okay now we want you to start moving over to this style if you're using the courts 2d system and so in order to facilitate that we've written some code that you can link into your application you can start getting start using this style rather than using the create context report again this is this printing issue okay so these routines work both the the real routines that are going to be in the future version of Mac OS 10 work both on-screen at print time this linkable code does not enable printing but it lets you move your use of core graphics of courts 2d over to the style of mixing both quick-draw and core graphics so again if you're only drawing with quick-draw or if you're only drawing with courts 2d this does not apply so we have some linkable code does not enable printing it doesn't install these bottlenecks that dummy out the quick-draw drawing in between but it lets you get going okay well tips and tricks I got it I hope I gave you a little bit of a tip or a trick with the demo but let's talk about some printing tips first thing number one most important don't expect that when you say PostScript begin draw some picture comments post gripped in there that's going to generate PostScript you need to do something really special Paul Dan bolt talked about how to do that if in the praying session so you need to do something really special if you want to generate your own PostScript by default the printing system doesn't generate PostScript well let you generate PostScript okay so in addition don't expect that you can use PostScript begin in PostScript pen to hide quick draw draw Lots applications do this on Mac OS 8 9 they say ah well it's the laser rider driver you know so it's not going to you know pay attention to the quick-draw drawing that I'm doing in between post creep again and hey we recognize that quick-draw and we're going to image it okay so the next one here is if you're someone who likes to actually go in and call the bottlenecks the quick-draw bottlenecks directly make sure you check that graph board make sure that those bottlenecks are nil or don't exist already in the graph board before you go off and call standard bits or standard text or whatever because if there's support bottlenecks you want to chain any calling that you make any calls that you would normally make in the standard bits or standard text or whatever you want to call the port bottlenecks okay and the last thing there is no pixmap mapping backing up the imaging that you're doing at print time so don't think you can say oh though I've got some bits there and I can scroll call scroll bits you'll crash you just get garbage probably on Mac OS 8 knowing you crash on Mac OS 10 okay now there's some documentation we have out there on the Mac OS 10 printing graph port it's already been written it's already been out there for probably I don't know maybe even 10 years but close to it and that's the documentation that's in Appendix B using picture comments for printing pretty much what it says in there is true mod modified by some of the things I've said here there's some picture comments in there that say yeah these are going away you don't want to be using these hey these went away you don't want to be using those okay now coming soon we're working on a tech note that's specifically about the Mac OS 10 printing graph board it's going to contain the material that I have in this talk expanded ok so let me just give you a summary so far we hope you see that there's both my talk and obviously talks earlier in the week with far more impressive things in them you can really do some cool stuff with quartz 2d and Carbon on Mac OS 10 in carbon ok the printing graph port it's not like a graph board you saw before it recognizes all these picture comments but it's not a postcard graph port it's not a quick-draw graph it's this sort of hybrid and just emphasize again applications can mix courts 2d and quick-draw drawing content on screen and at print time the mixing is going to take the form of these new routines that I've described okay that's the summary what I've given you so far what about making it all go fast and to talk about that my colleague Ralph Bruner on the graphics team okay so I will talk about course performance tuning and in the next 15 minutes you will learn something about how to improve your graphic speed or to do about memory usage and most importantly how to find performance problems okay first like to say something about how the architecture in Mac OS 10 works the graphics architecture on Mac OS 10 there is a process running in the background called the windows server and that process is responsible responsible for managing screen real estate so when an application creates a window it will go and send a message to the window server and say well I need a window that size that's that's what and the window server will go and allocate a buffer for that window map it into shared memory with that application and any application can go and draw into these bits well when the application is down drawing it sends again a message to the windows server and says okay now here are the new bits I want to put them on screen and the minnow server will do that now the important concept here is that the window has a backing store so all your all your content is buffered and that has some implications for how you do graphics first of all what it gives that to you is the window server is able to mix the content of your application with the content of any other application so that enables things like the drop shadows you see Genie effects scalable dark and things like that now you have to be aware that whenever you do a manipulation of your window that is no longer as lightweight as it was under OS 9 because pretty much everything you do with windows that affects the window geometry is actually a message that goes over to a different process and tells it what to do one other implication is that window buffers use a bit of memory so the last thing you want to do is allocate a lot of windows which are not on screen but just eat up some memory so two tips here one is primarily for cocoa applications it's a bad idea to go allocate the window at a certain size and immediately resize it to a different size because that essentially means the window server will allocate some memory then it will get a request well toast it away I really want to change my mind up on something else and that is fairly common when you have a default size in your nib file and then set it to the window size that the user said it last time to so if you can avoid that that is a nice performance game something from the carbon side of the world some Carbon applications online and use an off-screen G world to buffer the window content so on 10 this is counterproductive because you already have a buffer so you just double the memory size for the window and you do an additional copy so if you can avoid that that helps too another thing for cocoa applications in interface builder we have this little flag that says you can make the window one shot well one shot windows are have the property that when they go off screen the buffer is automatically discarded and when it comes on screen again the application gets a redraw message and to rebuild the content so whenever possible if you should use that most times it's far cheaper to redraw the content of the window than swapping it back in from a small file okay let's talk about drawing well the key message about drawing is in today's world graphic speed is essentially a function of memory bandwidth it's the number of pixels you touch it doesn't really matter anymore what you're actually doing with each of these pixels so the first thing you want to avoid is multiple drawing like you draw your window with you fill it with a pin stripe pattern and then you put a big white rectangle on top of it to have a background for your text so if you can avoid the pinstripe drawing at the first place that is a nice performance game and the other thing that ties in with the architecture of the window server reminds me before is avoid unnecessary flashing so whenever you're done with the drawing something that message gets sent to the window server to sell well put to tell it well put this stuff on screen now it's fairly common a fairly common bug that you flush too often you have essentially your drawing is half done and then somewhere in your code have a flash happens and what that means is unfinished drawing appears on screen and then right after that the complete drawing shows up causing flickering so you want to avoid try to avoid that as much as possible now one nice thing about Windows Server is all updates you do are synced to the CRT beam so you really get totally smooth graphics if you play in animation you get the exact 25 Hertz of your monitor or whatever and that's the reason why dragging the window around on OS 10 is really smooth however this can backfire for you if you flush too much that mechanism will actually ensure that the unfinished drawing stays on screen for long enough for the user to notice so it might be good to good idea to look at that so in today's world or as 10 point oh point X when the buffers live in main memory but however it is a good idea not to rely on that there may be changes coming to move windows the window buffers on the graphics card or maybe they get compressed or any other performance optimizations we might think of so relying on that the fact that the window buffer is in my memory today is not such a future proof proof strategy so what you want to avoid is touching the window bits directly whenever possible use quick-draw QuickTime quartz 3d to produce your content so this here on the slides essentially getting the port for your window and then the pics base address that's whenever possible you should avoid that well there are definitely cases where you have to so I can't imagine if you write an emulator for something then you probably want to produce your own bits so if you do we'd like to hear from you maybe we may come up with some API to enable that without breaking the programs optimizations you're going to do in the future okay word about the velocity engine understand we have a certain number of functions inside the graphic system that are optimized for the g4 and this gives in some cases really significant speed ups in fact whenever we go and vectorize one of these routines we usually get more than 2x out of it and in some extreme cases we saw something like 17x speedups well for you for your drawing to actually make use of that there's essentially one hints to give here which is whenever you produce your own bitmaps like you create the CG bitmap context or you create a cricketer or gee world and then hand that to the graphic system make the robots a multiple of 16 which is the vector length on g4 chip that will enable more optimizations to kick in and as a side effect of that because there are routines that are significantly faster do test your software on the g3 as well not just your chief or developer machine if you have interactive graphics going on which is really nice on g4 it might be that you may be that you're actually triggering one of these optimization and it's dark slow or g3 so it's worth verifying that okay now I'm going to do a demo about how to find performance issues on your system I get rid of this so in your developer folder there is a little application called quartz debug it says this colorful window here and enables you need to activate some switches inside the window server that will give you some debugging hints simple text here okay the first switch here is flash screen updates which means which tells the window server whenever it puts something on screen flash the area briefly in yellow to brick make it very visible where updates are happening so for example if I switch over to simple text here you see there's some flickering going on and when I move the window around you see there are certain areas that get updated now I'm using simple text here because simple text has an interesting performance bug so when I've type here you see it redraws the entire window for every character type so this mechanism makes it blatantly visible where your performance problem are and why your key repeat rate is really slow so this helps a lot in finding these kinds of problems because to be at the window of the window contents are buffered it's not much hard to see you no longer see flickering on screen usually if the flash is in the right place so this is the mechanism to counteract that effect and tell you what's going on another switch here is all flush drawing which essentially activates whenever a primitive is drawn either to quick draw or to court CD we flush immediately this is like the immediate mode drawing you'll see on OS 9 so if you combine that with the flash screen updates then you actually see every single primitive and you see there's a lot of flickering going on the menu gets redrawn and stuff like that so this makes your system really really slow as you can see but it helps you to detect some things like duplicate drawing if an area flashes twice then you know well okay there is probably something going wrong here okay so if I switch back you see yes the fireworks still going on okay another thing that allows you to that quartz debug allows you to do is look at the window list in the system so let's get rid of this it's probably bit small but these are all the windows the windows overseas and there is the things like well size on screen size in memory position and the name of the app that produces that produced that window so for example the top three here say quartz debug app there is one window which is 22 pixels high and test the width of the entire screen which is the menu bar on the top there is another window down here which is 300 by 200 something which is this nice little picture here and there's a third window interestingly which is 19 by 19 pixels now this is AB gate caching that little checkbox here so which is internally implemented as an off-screen window so look at your application using the show window list feature here and find out if there are windows that are off-screen and if they're big try to get rid of them because you don't really want to end them and them to end up in the swap file ok that's it for the demo if you can go back to the slides that's please thanks okay now I'd like to invite Travis brown back up before we get to the Q&A I just want to take a quick time to go over the last item on our roadmap at WWC relating to graphics and we have at two o'clock in room j-1 the graphics feedback for them this is a very important forum for you to come and tell us feedback on mac OS x graphics technologies it's a good opportunity to you know query us on to why certain elements the architecture implemented differently from what you experienced in our mac os9 additionally provide your feedback and features and things you would like to see in the system if you need my contact information I'm Travis brown at apple.com I can be reached if you have questions about any of the 2d graphics technologies in Mac OS 10 feel free to send me emails you