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: wwdc2002-601
$eventId
ID of event: wwdc2002
$eventContentId
ID of session without event part: 601
$eventShortId
Shortened ID of event: wwdc02
$year
Year of session: 2002
$extension
Extension of original filename: mov
$filenameAlmostEvery
Filename from "(Almost) Every..." gist: ...

WWDC02 • Session 601

An Introduction to Building QuickTime-Savvy Apps

QuickTime • 1:13:14

Your best introduction to QuickTime, this session explains a plethora of QuickTime technologies and provides instructions on how to incorporate them into your application. All aspects of movies are covered, including open, play, capture, edit, import, export, effects, extensibility, components, and interactivity. Also covered are Cocoa support, Mac OS X, cross-platform development, data handlers, QTVR, compression, codecs, ref movies, Internet solutions, still images, audio, and streaming.

Speakers: Ian Ritchie, Brad Ford, Jon Summers, Tom Dowdy, Sam Bushell, Tim Monroe, Greg Chapman, Adrian Baerlocher

Unlisted on Apple Developer site

Transcript

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

Good morning, everybody. Welcome out to the QuickTime Session 601, How to Make Your Applications QuickTime-Savvy. My name is Ian Riitchie. I'm part of the QuickTime engineering team. I have the pleasure of engineering some of the engineers on this team. Now, today we're going to present some ideas to use some techniques.

To help you leverage the power of QuickTime, and now you may wonder, well, why QuickTime? We were told that some people that will be attending this show will be new to the OS, will be new to QuickTime, and that we should give a roadmap, sort of an intro session of...

[Transcript missing]

There's thousands of titles out there and you wonder, well, why was it so popular? And he talked about extensibility. Let me go a little bit more into the extensibility side of it.

If you have a video card that's unique to your company and you want it to work with the rest of QuickTime, will you write a VDIG? And a It'll be able to play your VDIG then, we'll talk to the card, capture the video, give it to the sequence grabber, that will then work with Final Cut, that'll work with sample apps that we've gotten, Adobe Premiere.

And as you've seen, QuickTime has a lot of video compression and decompression technology in it. We didn't write all these. Other people out there would specialize on their code, write really great algorithms, and then wrap it in a codec and ship it as part of the QuickTime technology.

Either we would license it or you'd be part of the third-party component program. And users out there would be able to use your software. What we've done is we've set it up so that you can specialize on what you're really good at, and everybody else takes advantage of it.

Today what we'd like to show you is How you can, if you do these few calls, a little bit of code in your applications, you'll be able to take advantage of a lot of work that we've done, leveraging. There's a martial arts technique that follows along this. What is it called? Where you use your opponent's energy against it? Judo. Yeah, so we could call it QuickTime Judo.

The situation is completely cross-office. Our product is not machine-hard updates with you. Our competitors are jacks and ways to devour our remaining workmanship. We have no protein. Our shareholders have a hand in this, and I am in for it. All engineers go. and you just say the company.

It must have been a disaster to have any new features. We need multimedia integration. Movie playback, capture, still image, import, and export, and interactivity. As the hot schools get on, it's expected that YouTube will strike for code. And we should. I hope to have you covered. It is not possible.

As my panel, I gain instant access to a vast number of movies and still image formats. I must learn the ways of QuickTime if I can fulfill the master's task in time. and beginning to see more clearly already. Off the tables, inverse discrete cosine transforms. I won't be able to do battle with such audible moments. How I've mastered foreign video concepts in two weeks. I must read with great speed and probably sleep. I'd like to bring on Brad Ford and Jon Summers to give you guys an intro to Movies 101. Thank you.

Good morning, and welcome out to Movies 101, which is the polite, politically correct title. I like to refer to it as QuickTime Boot Camp. We've been given the arduous task of explaining to you the minimal calls you need to know, the basics, to get a QuickTime-savvy app running. Now, who will this be pertinent to? Like Ian alluded to, we have, hopefully, a lot of new people to the platform and a lot of new people to QuickTime, QuickTime newbies.

For those of you who have not programmed in QuickTime before, all of this information will be pertinent. We probably also have some veterans out there, people who have been programming QuickTime for five or ten years. All of this information is pertinent. Don't go to sleep, because we are going to interlace brand new QuickTime 6 API calls that you should be aware of and you'll be interested in knowing.

So let's start with a very high level overview of what a movie is. Suspend reality for a moment and forget everything that you know about a movie. Because in QuickTime's world, a movie has nothing to do with $8 seats or popcorn. A QuickTime movie is more like a card catalog drawer. You've seen card catalogs before. They're the things over in the corner at the libraries that no one uses because there's a computer next to them that does the same thing.

But 10 or 15 years ago, people used to use a card catalog. And the idea behind it is you have thousands of books and you don't know where to find anything unless you have an organizing abstraction that tells you where to find things. That's what a QuickTime movie is. It's no more than a catalog. So think of a drawer. It's got index cards in it.

Each one of these index cards points to a book. So you can think of the books as being the actual data that you would want to look up. And the index cards are tracks in a QuickTime movie. QuickTime supports a bunch of different types of tracks: video, audio, MIDI, sprites. And all of these tracks you can think of as being a separate index card that points to books that will show you where to get the actual data.

So a QuickTime movie is actually a catalogue of media resources. It contains a list of tracks which tell us what the media is, where the media can be located, and when to play the media. You'll notice that a QuickTime movie is not a QuickTime movie file. The media data references, the media data samples do not necessarily... need to live in the same media storage unit as the actual QuickTime movie.

Okay, let's give a quick demo on Demo Machine 1 that illustrates this point. Okay, so I hope you like this analogy of the card catalog and the index cards because you're going to hear it over and over and over, so get used to it if you hate it.

I've brought up one of the old QuickTime stupid movies. This is a tradition every year to have a stupid movie, and it's a lot cheaper than trying to get a Spider-Man trailer or something like that, so here we go. This is an actual QuickTime movie that actually plays. ♪ Well, I'm done programming it for today. I think I'll relax with some QuickTime TV. I've got kickboxing.

I've got some. Okay, let's look at a little bit of information about this movie. First thing we'll notice is that, okay, 64.4 megabytes on disk. That's really big for just a catalog, so the light should go off in your head. This isn't just the catalog. This is the card catalog drawer and the books all wrapped up into one big file.

This is also known as a self-contained movie, where you get the media data and the catalog in the same file. You don't have to do it this way, but this is the most portable way of doing it. So if you're going to download something from the Internet, this is the way you'll usually find them. The catalog and the books all in one big file.

But we can play around with this. So, for instance, in QuickTime Player, I'm able to perform some editing functions. I'm just going to go ahead and grab the whole movie, select all, I'm going to copy it, And then I'm gonna make a new movie and paste it in.

And so this is now untitled one, and I'm going to say save. Notice I get two things I can do with it. I can either save normally, allowing dependencies. What that means is it just gives you the catalog. Copies down the information from the card catalog index card and writes that little bit out to a new file. If you make the movie self-contained, notice it's going to be 64 megabytes again, because it's going to write all the data out.

If I had made an edit list, if I had taken little chunks, think of them as little sections of the books, you know, page 100 to 114, it would do the same thing. It would just take the little chunks that it needed from the sample media, write it out to a new file. Let's save it normally, allowing dependencies. So I gave it the beautiful title of Untitled One. Way to go, Brad. And let's play a little bit of it.

and the rest of the team. Amazingly, it plays. But let's investigate a little bit. 48K. So now it's just the catalog. Just the information that you need and it's pointing to the books that are in file one. Okay, just to show you that there are no tricks up my sleeve, I am going to close that.

I'm going to delete the Seating for Dummies movie and I'm going to try to open Untitled and is going to yell at me. Well, first it's going to search for a long time, and then it's going to yell at me. But you get the idea. The books are no longer there. We now have a card catalog that points nowhere. So let's go back to the slides.

Okay, where does movie data come from? Now let's talk a little bit about the books themselves. A QuickTime library is a lot more flexible than a library that you would go to in real life because the books don't have to be stored in the library. The data that you would want to bring into your movie or call from your movie can be located any number of places. We'll talk about four of them. Local storage. It can be stored in a disk file, not necessarily a .mov file.

QuickTime can import a lot of other file formats in place. What that means is it doesn't need to turn them into a QuickTime movie first. For instance, an MPEG file, MPEG-2, MPEG-4. These files can all be opened in place without writing some QuickTime specific data to them. So you can get it from a disk file.

You can get it from a remote source URL, such as an HTTP server or an RTSP streaming server. You can also get a movie that's in memory. If it's already been loaded, you have a handle to it, you have a pointer to it, you can reference that media in your catalog as well.

And here's the real selling point for me. Different pieces can come from different places. So you can have one part of it coming from an RTSP streaming server. You can have a flash track coming from an HTTP streaming server. You can have a voiceover coming from a local file on disk, all in the same movie, because these are all just separate files.

So you can have a movie that's already been loaded, you have a handle to it, you have a pointer to it, you have a reference to that media in your catalog as well. And here's the real selling point for me. You can get it from a disk file or an RTSP streaming server. You can get it from a disk file as well.

And here's the real selling point for me. You can have a movie that's already been loaded, you have a flash track coming from an RTSP streaming server. You can have a flash track coming from an RTSP streaming server. And here's the real selling point for me. You can have a movie that's already been loaded, you have a flash So we'll take a high-level view of what we'll need to do to become QuickTime 6 savvy. Working with movies, the first thing we need to do is initialize the QuickTime toolbox with Enter Movies.

We're going to show you how you can open movies from any location. Once you've opened the movie, then you need to give QuickTime, which is a toolbox for dealing with time-based media, you need to give it processing time. So we'll talk about that. Then, for movie playback and editing, we'll show you the importance of attaching a movie controller to the movie. When you've done your edits, then we'll show you how you need to save your movie.

Note that applications should not call exit to movies when they're closing the application. Exit to movies really should be called if you are writing a component and that component has called Enter Movies, you should balance that call with an exit to movies. So take out that exit to movies. in your applications.

Now, just to show you that QuickTime, a QuickTime movie is actually a catalogue of media and does not play the media in the... In the order that the media is actually in the media storage, we'll go back a few slides and we'll talk about where does QuickTime media come from? There are a couple of locations here, local storage, remote, and from memory. But that's not all the places that QuickTime movies can come from.

And in order to specify that location, we have a data reference. This is an abstract location specifier. QuickTime developers are used to the file manager-based calls, such as Open Movie File. Now with the abstracted family of calls using a data reference, you can now specify movie locations from anywhere. A data reference is a handle to a data structure.

The DataRefType specifies the accessor component that is required to read the Data source. Therefore, a data reference specifies location, and a data ref type specifies the accessor, and that... That returns an instance of a data handler component which knows where the data is stored and how to read the data. For example, local file storage, a data reference is... is a handle to a structure of an alias record. This alias handle plus the data ref type alias Allows us to use an alias data handler to return the data from the file.

Now that we have specified the location of the movie, how do we open the movie? We open the movie with new movie from data ref. This is a general form of the file manager based new movie from file. Notice that we, new movie from data ref takes a data ref and a data ref type and returns a movie catalog. Note that we do not need to call open movie file, close movie file. New movie from data ref opens the movie storage, loads the movie catalog, then closes the movie storage for us.

Now we'll have a demo on Demo 1 to actually show how you can actually write your own data handler. This is a demonstration of how to get QuickTime movies which are stored inside a database. Right. This is an interesting plug on the things you can do with... Can we have Demo 1, please? Okay, this is sort of an interesting plug on what you can do with QuickTime when we haven't even foreseen this possibility. You should not be afraid of data references. Data references are your friends.

You can continue to think of them as aliases to files if all you're working on are file-based things. But they buy you a lot of things that you wouldn't get otherwise. So you should use data references and use these newer APIs. One such instance is this very cool thing called FrontBase.

FrontBase is a relational database server put out by a company called FrontBase, and it's very QuickTime savvy. They've done some very cool things with QuickTime movies. Most databases, if they are storing a lot of files, you'll have references to them in a database. You know, where the file is, the name of it, the duration of the movie. But what FrontBase is doing is storing the whole movie in the database. So once you put it in the database, you can't pull it out anymore.

It's not a .mov file. It's in the database as this one big blob. So let's go ahead and start up the server. And we'll click on this and show you... and more. So, I've made a table in here called Streamable Movie, and it has two fields in this table. There's a file name field and a movie content field.

One of them is the name that I gave to the movie, and one of them is the actual movie, which I uploaded into the database. Now, once it's there, there's no way to pull it out because it's not a file on disk anymore, an MOV file. It's not an HTTP streaming server. It's nothing of the sort. It's from a database.

So what did the front base people do? They wrote their own data handler that grabs movies from their database as requested. Let's try that. Here's a little Cocoa application that just demos how they do this. There's no other way to get these movies out of the database except by using the data ref and the data handler.

Wow, that guy can play. So, Jon, what's happening under the hood here? So what's happening is... We've used New Movie from DataRef with a data reference which tells location in the database of this movie. That is the file name, the name of the movie. Also we have used a DataRef type which specifies the front-base custom data handler. These two, this combination gives us a data handler of the custom data handler, of FrontBase's custom data handler.

Once we have the movie catalog from new movie from DataRef, we have a slight problem. The data references inside the movie catalog refer back to the original movie file that was imported into the database. So before we can work with the movie, we have to go through all the media handlers and reset the data reference to use the front-based custom data action handler.

Now, as QuickTime requests data to display, the data handler goes to the database and actually makes byte range calls into that data blob. So, as you can see... So, for instance, you can... It's not just downloading the whole thing as a blob. We have random access to it. The data handler goes out and it finds the new frames that are requested when I scrub around or go to a new position. It's not quite as fast as Instant On, but still pretty good. All right, so let's go back to slides.

Okay. Now the ever-important topic of movie controllers. Movie controllers are a hugely functional object. What we're going for here is maximum efficiency. When you want to build a QuickTime-savvy application and you want to get a lot of work done with a minimal amount of code, use movie controllers. This is not market speak. This is not me trying to push something on you because I like movie controllers. If you want to get a lot of work done, attach a movie controller to your movie. You'll get the most bang for the buck doing so.

So movie controllers. Once you've opened your movie, for instance using New Movie from DataRef, you attach a new movie controller to it using New Movie Controller, and then you can run your event loop. There's a special call called MCIsPlayerEvent. If you're used to the old wait next event based application loop, then you're used to having some big switch statement where you handle events. Well, all you have to do is plug in MCIsPlayerEvent before you handle the event yourself.

What MCIsPlayerEvent does is it will send you a message that says it gives QuickTime a chance to look at the event before you process it, and QuickTime will say to you, "Yeah, I know that guy. That's my event." Or it'll say, "I have no idea what this is. You handle it yourself." And so it gives you a lot of automatic processing of events. When you're finished, here's another little important thing. Dispose of your movie controller first. If you've attached it to your movie, don't dispose of the movie first. That will be bad.

Okay, a lot of developers have expressed to me, you know, that they're afraid to use a movie controller because they don't want that stock look. They don't want their application to look like everybody else's application. Well, a movie controller is not the same thing as a movie controller bar.

I think the movie controller bar is fantastic because it puts a lot of functionality into 16 pixels. But if you don't want to use it, you don't have to. You can still use a movie controller without showing the bar. You can make it invisible and still use all of the functionality in this great object, this delegate object.

Okay, now I'm going to give you four compelling reasons to use movie controllers. First one, at the risk of sounding redundant, they simplify control. They are, after all, controllers. There is a wonderful call called MCDoAction. In a library as large as QuickTime, where you have, you know, well over 2,000 function calls, it's nice to know that there is one call that you can use that does, I believe, 77 different things.

So with MCDoAction, you give it your movie controller, then you put in an action, be it action pre-roll and play, action go to time, set keys enabled, whatever. And then the third parameter becomes your context-specific information, your parameter that you need for that one. For instance, if you want to play your movie using a movie controller, you use MCAction pre-roll and play and then give it at a fixed rate to play at.

Okay, here's probably the most compelling reason to use movie controllers. Some things will not work without them. If you want to do interactivity, it's not an option. You have to use movie controllers because there's no other way to do it. You have to use the movie controllers to get those events to do intermovie communication and work with sprites. With QuickTime VR, you sort of implicitly need a controller because you don't play a VR movie, you sort of play with a VR movie.

So without a controller, it wouldn't really make sense. Streaming you can do without a movie controller, but it's really hard, and you have to do a lot of code by yourself that's taken care of automatically with a movie controller. So I would advise you to use a movie controller if you're going to use streaming.

The second thing you can do with them, so you can control, you can also query your movie. You can get movie information using your movie controller object, like MCGetCurrentTime. There's also one called MCGetControllerInfo. This is mostly used for adjusting menus. So let's say you have an edit menu that you need to adjust on the fly based on whether or not your movie is playing.

You can use MCGetControllerInfo, pass in any flags, whatever the, you know, you have a long that's flags, and it gives back to you these flags and you can compare them with whatever you want. For instance, MCInfo is playing, or is looping, or has sound. These will tell you what you want to know about your movie and you can adjust your menus based on what it gives you back.

The third reason that you would want to use controllers is that there's a very simple mechanism for providing callbacks. This is customization. So if you don't like the custom way QuickTime does something, you can change it by intercepting an event before it gets handled by QuickTime and change it around.

One simple example that I can think of is, for instance, in QuickTime, in a QuickTime movie, if you click on the portion of the movie where it's being shown, it stops. A lot of people don't like that. They want it to just keep playing no matter if people click on the movie or not. Well, if you set up an action filter, like, for instance, my action filter callback, then it will intercept these events before they get to QuickTime.

And you could intercept, say, MC action movie click, and you could make it into a null event and it would then discard it. And it would say, "Yes, I handled the event. Keep on doing whatever you were doing." The last one is tasking with movie controllers. If you've worked with QuickTime a little bit, you know that it needs time to process the movie information that it's working on.

You can use a lower level call such as TaskMovie, but you don't have to use those if you're using a movie controller because you can use MCIsPlayerEvent. If you use that call, it will task movie for you. It will make that call and it will give your movie sufficient processing time. There's also a new API in QuickTime 6 that gives more efficient processing time to QuickTime and it lets you know how often to call QuickTime, but I'm not going to steal the thunder of people who are going to talk about that later, so more on that later.

One of the other great things that attaching a movie controller to a movie gives you is you immediately get a nice professional support that you can actually now support movie editing. As you can see, if you turn movie editing on with MC-enabled editing, then there's a mapping from high-level edit commands, menu edit commands, to MC functions. Not only do you get cut, copy, paste, but you also get undo.

Adding media samples is a simple matter of calling beginMediaEdits in order to prepare the movie storage for write. QuickTime opens the movie storage for write. You add media samples, you add compressed media samples along with descriptions of what the media is and the duration of the media. Then, when you've finished your editing, you close the media for write. Then it's important to call insertMedia into track. This is very much like updating your card catalog index to actually point to the books. And this then associates the media with the track.

New movie from scratch. We can create a new movie with create movie storage using our old friend, the data reference and data ref type. This returns an empty movie catalog. Then we can add tracks and media. Then we add the movie catalog into the storage. Then, when we're finished, we use close movie storage to close. You'll notice these calls are new in QuickTime 6. This is because QuickTime has always had a file manager-based way of finding movies, movie location. Now, with data references, We now have the movie storage API, which is a more generic way of accessing movie data locations.

Then, when you've finished editing, you want to save your movie. You can update the catalog, which is just to synchronize the in-memory model of the movie back to the movie storage. We can also flatten a movie with Flatten Movie Data to Data Ref, which actually then trims the media data so that only the data that is referenced by the catalog is in a self-contained media storage. Then we can also export... We can export a QuickTime movie to a native media format, such as you might have an AFF file, AIFF file, which you can then bring into QuickTime. QuickTime can import that.

It will create a temporary catalog. You can edit that movie. Then you can save that back out as the native media file format. There you have it. Congratulations, Movies 101 graduates. You now know all the basics that you need to know to get a basic QuickTime-Savvy application. Thanks.

and the success is finally mine. Behold, I can open and play a DB movie file. Yes, Jon-Sa, but can you open dozens of video and audio formats with a single set of API calls? No, you cannot. I, on the other hand, have discovered the way of the data handler. Aye, data handlers. Excellent. Let's bring up Tom Dowdy to tell us a little bit about video processing.

Thanks Ian. Jon and Brad talked about where do you-- creating a movie from scratch or modifying a movie by adding samples to it. One of the common questions we get is where else could you get these samples from? QuickTime has built-in support for capture, compression, import, and export that abstract away from your application the details of particular types of video input, output, compression formats, etc.

Capture is a very important part of QuickTime, and the structure that you need to understand in order to perform capture is called the sequence grabber. The sequence grabber provides an abstraction from your application that allows you to capture any number of media types, audio and video being the most common, but it does support an unlimited number of types that can be captured simultaneously. The quintessential source code for showing how to use the Sequence Criber, it's really a little bit too much to go into detail here, is called HackTV, it's available on Apple's website.

Video compression is another important area of QuickTime. Your application can perform video processing on the video before it's been compressed, but after it has been captured. You can process a live video and store it. You can take an existing movie, process it, and store it back into a new movie. Or you can perform video processing while movies are being played back. If you're interested in doing processing on videos, such as perhaps alpha overlays, displaying a video bug, doing effects or crossfades between videos, session 602, which follows this session, gives more information about this.

Another important aspect of QuickTime is the ability to open multiple file types or save out different file types. The movie import and export components within QuickTime Allow your application to perform this importing and exporting without knowing the specific details of each particular file type. This means that when new file types are added by QuickTime, your application gains immediate support for them. For example, when we added MPEG-4, even though it's a very different file type, applications that are using the normal QuickTime calls for opening files and exporting files immediately gain the ability to import and export those files into the MPEG-4 format.

In addition, there's facilities within QuickTime for outputting a movie directly to an analog video source. This is sometimes called print-to-video. Also, all of these import and export functions have built-in user interfaces within QuickTime your application can call on, so you don't have to have specific dialogues that you construct for configuring the user's options. But, if you're an application that's perhaps command-line oriented or does batch processing, the same settings are also available for you to set via an API. Again, if you're interested in import, export, and print-to-video, session 602, which follows this session, has a lot more detail.

Ian? Hi. Make sure you go to that session this afternoon. It's going to be really great. Now let's bring up Sam Bushell, or just before that. Let's see what our friends are up to. Video capture and processing. Thank you, QuickTime team, for again illuminating my understanding. Integrative effects and video acquisition is as easy as snapping my fingers. The concept is comparably simple. I write fewer lines of code. QuickTime performs the dirty work while I receive all the credit. Ha ha, QuickTime has filled me with much self-confidence. Perhaps QuickTime will also bring me much more success with the ladies. Okay. Sam Bushell.

Good morning. Yes, my name is Sam Bushell. I'm here to tell you a little bit about a basic introduction to QuickTime still image support. QuickTime still image support consists of two classes of component, graphics importers, which are used for drawing still image files, and graphics exporters, which are used for creating still image files. Both of these component types are designed with the philosophy of making them easy to start using and then to have extra calls that you can make as an opt-in to get to more powerful features and functionality.

What I'm going to go through here is a brief introduction to how to call or how to start calling both of these kinds of components. And then I'll briefly touch on some of the more advanced features that are available. And then I'll show you a brief demo of some sample code that I personally recommend to have a look at.

So, to draw still image files, first you need to get a graphics importer component. There are a bunch of APIs. There's one that's FS-based, but in order to gain FSRef support, you should consider using data references that you've made from an alias handle, as we discussed, and passing in the alias type.

When you pass, once you've called this, Image Compression Manager will search for a graphics importer that's appropriate for the file that you've pointed it at. It'll search based on the file type, if there is one, the file name suffix, if there is one, the MIME type, if one is known by the data reference, or can be inferred from other information that the data handler knows how to deal with. And it'll even look at some of the data inside the file if necessary.

If it fails, it will return an error and the graphics input will be zero. At this point, you can find out more information about the data reference. You can find out about the image file. You can ask for information about the dimensions, the color space, metadata, and so forth. But in this simple example, I'm going to pretend that we already know where we want to draw the image. And so we'll set the location for it to draw with the graphics import setDeskDirectCall.

After that, we're ready. We can just draw it on the screen, and next time we... Next time it's appropriate for that to appear on the screen, it'll appear. You can draw again and again if you need. You could change the location. You can ask for more information. You can hang on to the graphics importer component while you need it, but when you're done with it, you should close the component and release the storage that it's held around. With this simple piece of code, it doesn't actually know about a particular file format. The data reference type is not the type of the file, as some people initially think. It's the type of the data reference.

So for an alias handle, data ref type is alias. So this piece of code can work for a whole bunch of different image file formats based on the available graphics importers. These are the formats that you'd be able to use in QuickTime 5. As you would have seen this morning, we've added a JPEG 2000 to this list for QuickTime 6.

Other things that graphics importers can do. What we showed there was how to... Specify a rectangle for drawing the image in upright. But you can also choose to pass a transformation matrix that can give you more accurate positioning. You can even rotate or put the image in perspective.

I should point out that in QuickTime 6, we've done a bunch of good work to improve the quality that you can achieve with rotation and perspective, which you can read more about in our documentation. But that's really neat. Graphics importers support a variety of transfer modes, such as quick-draw transfer modes and also some other ones, such as alpha composition.

They support arbitrary clipping to a region. They'll let you read metadata out. An important kind of metadata that's coming up on the scene is exif metadata in exif files. Who here has a digital camera that they purchased in the last five years? That's a large number of people.

If your camera makes JPEG files, those JPEG files are almost certainly actually exif files. Exif doesn't define how to do compression so much as it defines how to lay out metadata in the file. And there are particular kinds of camera-oriented metadata, such as flash, exposure time, those kinds of things are stored in the metadata for exif files. Graphics importers can also support multiple images in some files. The relationship between those different images varies. For a Photoshop file, there's different layers.

For a TIFF file, there might be pages. For a PDF, there might be pages. Exif files have the main image and then a thumbnail. Graphics importers are also extensible by third parties. There's a company called Escape in Greece, for example, which sell a graphics importer component for DICOM images, which are used in medical imaging. For creating still image files, the API is still very similar. You have to choose which graphics importer, graphics exporter you want based on the chalk.

You have to choose what choice of file type you want to create. You open the component directly. Then you tell it where the image comes from. It might come from a G world or from a picture or from another graphics importer. You tell it where the output should go to, which might be a handle, a file, or a data reference.

You tell it to perform the export, and it might actually tell you if you'd like to know how much data was created, and then when you're done, you close the component. With that amount of code, you can write a bunch of different file formats. This list keeps growing as third parties extend it, and we're extending it with JPEG 2000 and so forth. Other things that graphics exporters can do, they can provide a user dialog for the user interface to access format-specific features. They can store metadata in the file. They can write thumbnails. And they're also extensible by third parties.

So I'd like to show you a quick demo of some sample code that's up on the QuickTime website, on the Apple site. This is called Improve Your Image. It's over on Demo 1, which I should wake up. So I didn't have to write anything fancy here. I did change some of the images so that it's some more interesting things, because I like to show pictures that I take on holiday in Australia. So let's come back.

and many more. So let's have a look at a couple of lines of code to draw a picture. Can you see the kangaroo? Well, scaling the image is very easy just by changing the rectangle, but with a very small amount of further code, you could just rotate it or put the image into a non-app-on transformation such as perspective. This kind of transformation is particularly improved. It used to be point sampling in QuickTime 5 and before.

Now it might be bilinear interpolation or bicubic interpolation, perhaps with anti-aliasing. Looks really good. QuickTime can also perform alpha composition for you. Here's a picture of a beach and a picture of an old mascot of ours. With a normal transfer mode, you see a white box around the image.

With the transparent transfer mode, we do a key color, but that gives you halos and maybe takes out pieces of your image. But this image actually has an alpha channel. The important point here is that alpha composition is a very important component of the image. Alpha composition is an orthogonal feature from the transformation matrix. So we can actually rotate the image and still have it composed on the image on the background.

Briefly, because I'm running out of time, let me show you some... Support for layered images in Photoshop. Here's a slightly doctored image of a wallaby using an iMac. I'm going to go through the different layers in the file. Individually, there's a background, there's the shadow underneath the iMac, there's the iMac itself, and then there's the wallaby brought back in. And now I'm going to use QuickTime to draw them without erasing in between. And this time we see the background, the shadow, the iMac.

And this is more or less the same image as we saw in the first place, but composed by making QuickTime calls to the graphics importers. So that's all I have time to demonstrate, but I recommend having a look at this sample code if you want to find interesting things that you can do very easily with graphics importers. Thank you very much. I might have to step back.

We can bring up the slide machine, please. Thank you very much, Sam. Yeah, and that sample code, go out. We'll have a link at the, or a slide at the end of this that'll tell you where to go and get lots of the sample code that we've covered today.

But hopefully you're getting the impression that, hey, I do a little bit of work and I get a big payoff. That's where we're trying to go. Let's see how our friends are doing. With sufficient cunning and lightning-swift reading, I may succeed in devising an image-savvy framework. But I must make haste.

[Transcript missing]

Understanding, JPEG, TIFF, GIF, Photoshop. QuickTime handles them all for me automatically. Import and export are mine for the taking. Thank you, oh wise red-headed sage. Now I'd like to bring Tim Monroe up here to discuss interactivity with us. Thank you, Tim Monroe. Thank you. In addition to the linear media formats that we've seen and still image formats, QuickTime also supports what we call interactive movies. What's special about these is they don't just play frames over time. Instead, they respond to the user events such as mouse input or keyboard events. With a well-made interactive movie, these events can trigger various actions that give you dynamic feedback.

And QuickTime supports two basic interactive types, namely QuickTime VR tracks and flash tracks. In addition to those intrinsically interactive types, there are two other media types that we can add dynamic behaviors to, what I call scriptable. These are text tracks and sprite tracks. And as we've seen, QuickTime is an extensible architecture, so if you're really into this interactive stuff, you can add your own. So, if you're really into this interactive stuff, you can add your own. So, if you're really into this interactive stuff, you can add your own media types.

Some examples here would be 3D media, for instance. Let's take an easy demo of some interactive movies. Can we have the demo machine up? Where did they go? Here's a simple example of a QuickTime VR panorama. As you can see, I'm sort of standing out there in the desert. And by clicking and dragging the mouse, I can move around within the panorama.

So I, as the user, have control over what I'm seeing at any particular time. I can also use the keyboard to zoom in and zoom out. And as you can see, when I move my cursor over this area of the movie, it turns into an arrow. If I click that, I go to a new node. So here we have a multi-node panorama.

Another type of QuickTime VR movie is what we call an object movie. This is sort of where I'm controlling the object. I can move it around. Again, I can zoom in, zoom out. So I'm in control here. Another media type, as I mentioned, was Flash. Here's an off-the-shelf Flash movie. Again, the passage of time is irrelevant here. I'm in control as I move the cursor over various objects here. I can then drag them around and create a nice little eggplant.

We can get Flash movies that have more dynamism in them. Here's one where I've got sort of this pulsating square. I can use controls here to move it around. I can make it larger. I can move it to a random location. And so forth. and one note, two more examples. This is a sprite track, so I've got a graphic image.

As you can see, the one penguin is changing its location over time. When it gets to the bottom, it jumps back up. If I click on that penguin, he'll blink his eyes, and the other penguin will start moving. And also, you can see that sort of hidden down here are some controls. I can move the penguin back to his start, move him to the end, and so forth.

Again, I'm in control. What I do to the movie is what makes it go. Here's another example, and this one I really like. This is just a graphic image using one of the effects to give a ripple effect to it. And again, if I click there, I get a nice little ripple as if I had thrown a stone in at the penguin. OK, back to slides, please.

What's distinctive about interactive movies? As Brad mentioned earlier, when I'm working with an interactive movie, I have to have a movie controller. Also, objects within the movie, such as the, uh, The Penguin That I Clicked On can send actions to other objects in the movie, or indeed, I can send actions to other movies that I have open. That's a very powerful capability that we call intermovie communication. And can I have the demo machine back? Let's take a quick look at one of those. Here I'm going to open two movies.

We have our ripple penguin again. You can see he's still responding to my clicks. Over here I have a similar looking penguin. He doesn't have any rippling, but when I click him, the other penguin has disappeared. So a message is being sent from the one movie to the other movie saying, please toggle your visibility state, and I can make him disappear as I like. Back to slides, please.

Okay, another nice feature which is not really interactive, but which seems to go along with interactivity, are skinned movies. A skinned movie is a movie window with a custom window shape. So that's really what's involved with a skinned movie. When we do that, we don't get our standard window frame. We don't get a title bar. We don't get any of those nice Aqua buttons. We don't get anything to drag it around by. So we've got to define those behaviors.

The nice thing about a skin movie is it allows you, the content creator, to specify the entire look and feel of that movie. You're not stuck in this rectangular box anymore. You can do more interesting things. Now, because you're not getting a controller bar, you may need to supply some controls for the user to be able to manipulate the movie. And I think we're ready for a demo, so let's take a demo of a few simple skins.

Here's a couple done by Totally Hip. Here we have a movie window that is submarine-shaped, and inside of here is a video. This is actually a flash track that is providing the rest of the graphic elements here. You'll notice the little propeller down here is turning around, and this movie has a cool feature that if I click here, the escape button, it will close the window. Let's take one more example.

Here's a fairly complicated Flash skin. It's got some things up here. I can select various. Let's try some still images. Got some nice 3D models here. There's the hip bot. This movie is kind of cool because it can go out and query the environment. You can see it knows that I'm running on a Macintosh. It knows that my haircut is punk, whatever that is. And it knows that I'm running on QuickTime 6 here. OK, back to slides.

[Transcript missing]

You amaze me with your technical wizardry. Master, is the level of carnage satisfactory? Yes, it is most gratifying.

[Transcript missing]

Okay, you'll notice that I haven't shown you any code to figure out, so you can incorporate interactivity into your application. The reason for that is that if you've written your application right, these kinds of interactive movies will play automatically. There's really nothing special you need to do. Now, there is some stuff that you can do extra to make your application a little more interactive savvy, and I'll talk about that later in session 604 today.

Now, I want to shift gears a little bit and talk about writing cross-platform QuickTime applications. So, you've got some code that opens, plays QuickTime movies. What do you need to do to make sure that it's portable to other systems? In particular, what I'm thinking is perhaps you have an application that runs on Macintosh, and you'd like to be able to port it to Windows so that it runs there and greatly increases your sales.

QuickTime in Windows is a very good story. Since QuickTime 3, we've had identical programming APIs on the two platforms. The idea being that you can code once and deliver this on both Macintosh and Windows. In order to do this, we've had to make what we call Macintosh data types, such as handles, pointers, off-screen G-worlds, available on Windows as well as on Macintosh. So, for instance, the few lines of code that I've got here, I could put into my application. I'm allocating a buffer, and then later I'm getting rid of the buffer. That code works as well on Windows as it does on Macintosh.

This magic is provided by this thing called the QuickTime Media Layer. And essentially what they did was take a whole lot of the Macintosh operating system and shove it into a library that works on Windows. And I've listed here a few of the various managers that you can call on Windows because you might need those to do your QuickTime programming.

Very important point. A lot of people like to say that QTML is not a porting layer. Well, that's a little bit of a lie. QuickTime, QTML is not a general purpose porting layer. So you can't think, oh, I've got an application that runs on Macintosh, I'll just use this QTML to get it to work under Windows. In general, that won't work.

What QTML is, is a special purpose porting layer. It's designed to allow you to take your QuickTime code and move it to Windows easily and quickly. So you can write the code once, deliver it on multiple platforms. Now I want to talk about a few porting issues that you'll run into, because of course nothing is ever as easy as we say it is.

and there are four in particular. Let's talk about namespace conflicts. Turns out that Macintosh had some various functions, for instance, show window that you use to show a window. When the people in Redmond did their APIs, they thought, what do we call it when we want to show a window? How about show window? Well, so we've got show window on two platforms.

When you try and compile your Mac code that calls show window for Windows, you'll get a compiler error. What do you do? Just stick Mac on the front of it and everything will work out perfectly. So a certain number of Mac APIs, this list is not exhaustive, have been renamed to make them available on Windows as well as on Macintosh.

Indian issues. Macintosh was originally a Big Indian platform. This shows up in that data in a QuickTime movie file is stored in Big Indian format. Big Indian means that the most significant byte of multi-byte data is stored lowest in memory. Windows runs on little Indian platforms. That is to say, where the most significant byte is stored highest in memory.

Now in general, you don't need to worry about the endianness of any multibyte data. If I have some parameters that I pass to a QuickTime function, or if I call a QuickTime function to get some data back, it's going to be in native endian format. That is to say, in the format that is appropriate for the host processor.

Occasionally, however, you do need to worry about the format of multibyte data. Typically, this happens when QuickTime gives you a chunk of data that it doesn't know the structure of. One good example here is with movie user data. Here I have some lines of code that show how you get what's called movie user data from a movie file.

And in this particular case, I'm asking it for the piece of user data of type WLOC. This is added to a movie to let you know where to put the window on the screen. Now, QuickTime does not know the structure of that data. So when you get it back, you need to swap the bytes of that to make sure that it is in native Indian format. And you can see that I'm using a macro Indian S16, B to N. That is to say, big to native.

Now, byte swapping is only an issue for multibyte data, but not for C or Pascal strings, even though they're multibyte. They're treated as arrays of single byte characters. It's necessary only when you're transferring data between RAM and some external container, such as a file. And the best advice here is simply use the macros that you find in the header file, Indian.h.

The QuickTime Media Layer supports the Resource Manager, so if you have data such as user interface data or any type of data stored in a resource, you can use QTML on Windows to read that data. The gotcha here is that on Macintosh, when you open an application, the application's resource fork is automatically opened for you. On Windows, that's not true. You need to go through some code like this to make your resources available to you when you're running under Windows.

Once again, QuickTime tries hard to give you back the information that you want in a native Indian format so that you don't need to worry about these issues. If you have a custom resource, however, where QuickTime doesn't know the structure, all it's going to do is give you back the chunk of data that's in the resource. You will then, if you're running under Windows, need to make sure that that data is in a format that you can handle.

So there's a couple of ways you can handle that issue. A very simple way is to install what's called a resource flipper, and this is a callback procedure that the resource manager will call when you ask it to read that kind of data. It will then call your function, you do your flipping, and it gives you back that. Alternatively, you can just get back the raw block of data, and you know the structure of that data because it's your custom resource, so you can just flip whatever fields you need at the time you need them.

One last thing is QuickTime puts up a lot of dialogues as part of its user interface. This is really cool because you get all this UI for free. Under Windows, you need to jump through a hoop because you can't handle these in the standard Macintosh way. So what you'll need to do is either install what's called a modeless dialogue callback procedure, or, alternatively, if you have a fairly complex dialogue, you should consider just re-implementing it using the standard Windows APIs. Amen.

Let me say just a few words about Carbon. If you have some code that was pre-Carbon, you want to move it under Carbon. The thing here to worry about, of course, is that a lot of the data structures are no longer transparent. They're opaque, so you need to use accessor functions to get at them, such as if I want to get a menu ID pre-Carbon, I could just dereference the menu handle and look at the menu ID field. Under Carbon, I can't do that. They've given me an accessor function. That accessor function is not available under QTML, so you can define your own macro here to handle that. And I'm done. Thank you very much. Thank you, Tim Monroe.

The master will be so pleased with me. I have implemented my code in a cross-platform manner. My code runs on Atari, as well as vintage Commodore machines. Tim Monroe has taught me the way of Indian flipping. With my newfound knowledge, I can write my code once for both Windows and Macintosh. QuickTime Judo flows strongly through my veins. Let's bring up Greg Chapman. He will discuss some issues and enhancements that we made around tasking QuickTime. Greg.

You can hear me? Yes. There's always the question that we always get asked, how often should I call QuickTime to give it time? And I'm sure there are several people in the room here who have asked that question before, and you never really get a very satisfactory answer. Inside Mac QuickTime says you should task QuickTime regularly and as often as possible. Okay, there's a lot of folklore about this.

The problem is that if you task it too little, you'll be okay on some movies, but on more CPU-intensive movies, you'll have a problem. Some of the folklore is things like, well, if the movie's not playing, then I don't need to task it. So I can see what the movie rate is. If it's zero, I don't need to task it.

Wrong. Big time wrong. You saw a lot of movies that Tim Monroe showed you that were not playing, but there was a lot of stuff going on. You need to continue to task QuickTime when the movie's playing. A lot of people think you need to task it once per every frame in the video track. This is also incorrect. That's a little bit overkill in general. But QuickTime 6 helps you, because there's got to be a better way.

New in QuickTime 6, we have an API that you can use to find out when QuickTime needs to be tasked next. So you call it each time. If you're a WaitNext event-based app, you call it every time before you call WaitNext event. You say, you know, how many ticks should I pass to WaitNext event so that I'll wake up again, pass a null event to QuickTime. If you're a Carbon Event Loop timer-based app, you can call it to schedule a timer that you use to task QuickTime. We have working sample code available. There will be a URL at the end of the session.

but again you shouldn't even have to do this i mean this is this is You shouldn't have to do this. So on Mac OS X, we have some higher level abstractions. For Cocoa, we have NSMovieView. Now, this got smarter with QuickTime 6. NSMovieView has handled the tasking of QuickTime for you in the past. Now it knows about this new API, it uses it, and you'll only use the CPU that you need to play this particular movie. For Carbon, we have a brand new thing in QuickTime 6 called the Carbon Movie Control.

This is really cool. It's a first-class Carbon control. Put it in a window. It'll manage the playback manipulation of your QuickTime movies. It always creates a movie controller, but of course that can be hidden. So you don't even need to deal with the movie controller if you don't want to.

Carbon movie control will do that for you. It handles all the events, mouse and keyboard events. It can participate in the edit menu and in edit command handling if you want it to. And of course, you can install event handlers as well to customize the behavior of the control.

and Assuming you've created a window and you've done a new movie from DataRef, and you've You say, create movie control. Pass it the window you want to put it in, you pass it the movie you want it to control, and it hands you back a Carbon control. You run your application event loop, and that's it. Nothing further in your app you need to do unless, of course, you want to customize the behavior. We have working sample code. Check this out. Let's go to demo one.

This app is a very simple app. It doesn't even have file open. When it comes up, it brings up Nav Services, says what movie do you want to open. and others. We're going to stretch this window out. Like I said, it's not a very smart app. He just created a movie control, a Carbon movie control, and started his app event loop. So you've got full-on playback. Jump around.

to do. It's all there. Now that was fairly straightforward, but let's see what happens. If you pass in, I don't know if you noticed in the create movie controller call, there was a flags where it was being passed in zero. Well, if you pass in one flag that says "oh, and I want to edit too," that's the only difference between these two apps, and you Same thing, but I have full-on editing. Hang on, let's just go here. We'll select this.

[Transcript missing]

No code in the app doing this. This is just a control in a window. The control is handling all of that for you. Okay, back to slides.

Now we're going to bring up Ian again. Sorry. Thank you, Greg. Greg wrote the tasking mechanism we have in QuickTime 6, and it saved a lot of CPU usage. The QuickTime player uses it. Also, he mentioned in Cocoa, we are committed in QuickTime to increasing the support in Cocoa. I'm wondering how many people out here use Cocoa? Oh, very good. How many people are planning on using Cocoa? Adrian Baerlocher, let's introduce him. He's an engineer on our team, started about a year ago.

He'll tell you about the QuickTime Broadcaster that he's been working on. Good morning. So QuickTime Broadcaster is a new application we're working on for broadcasting live events using Mac OS X and a camera. It's a Cocoa application that uses many components of QuickTime. And what we did is we wrote a set of Objective-C classes that wrap many of these components. For example, the sequence grabbers, standard compression, and the broadcast APIs.

So let's get right into the demo. Could I demo one on both screens, please? Okay, so here we have the broadcaster in its simplified view. In this view, we hide most of the settings, and you just select A set of presets, and we're going to provide some presets with this application, settings that we think are really good.

Presets are just a subset of all the settings. So, for example, we have an audio, video, and network presets. For those of you that want to do your own presets or just change the settings, you can show details, and then we have settings galore. We have all the standard compressors supported by QuickTime.

And same with the devices, we're using the sequence grabbers, so those IIDC cameras you learned about this morning, they'll work with this application. So let's try a broadcast. Could I have demo one on the screen on my right and demo two on the screen on my left, please? Okay, so let's start this one up. We have some interesting content.

[Transcript missing]

And if you want to try this application out, it comes pre-installed with Jaguar Server, which is on two of the CDs you received here this week. Thanks. Back to you. Thank you, Adrian. The two weeks are almost up. My mind is uneasy. I desire a refreshing warm beverage. have brought you liquid sustenance to quench your thirst. Thank you. Ah! This beverage is scalding and caffeinated. I cannot drink it.

[Transcript missing]

Okay, don't leave yet. There's still more to come. Throughout the day, we'll be doing QuickTime sessions and also on Friday. Those of you that want to develop your own QuickTime components, we talked about the extensibility, you could write your own media handlers or codex, tons of codex. Please go to the session on Friday at 9:00 a.m.

Please stick around after lunch, come back in this hall today. We have a lot more and even more interesting things to show this afternoon. On Friday, there will also be a session on QuickTime for the web. Let me point Thursday afternoon at 2:00 in the Civic Center for those of you that are dealing with streaming issues and want to learn more about the new QuickTime streaming server, please go there and of course our feedback session. And oh, Jeff Lowe, you want to contact him with all your developer tech support questions.

You'll see this slide often today. For more information, we have the sample code out there. And please, please take advantage of this. We're bringing the engineers on site here to work with you. Come with your code, sit down with us, have a chat, and let us write the stuff for you to get it working inside your application. You won't get many opportunities like this. So please do this. Oh. Can I stop? If you can take the babble from my hand, it will be time for you to leave.

What an unfortunate lot is mine. If only I had leveraged the power of QuickTime's robust developer APIs, I might have pleased my master and earned the right to go home and change out of this wretched, smelly gee. Grasshopper, if you can take the pebble from my hand, it will be time for you to leave. It is time for you to leave. Zang.