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

WWDC05 • Session 138

AppleScript for C, C++, and Java Programmers

Application Technologies • 1:17:21

This high-level introduction to AppleScript is designed for C, C++, and Java programmers. You will learn how to take advantage of AppleScript using programming methods already familiar to you from these other languages.

Speaker: Sal Soghoian

Unlisted on Apple Developer site

Transcript

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

  • Hello. I guess my mic is on and I guess we're beginning. Okay. Thank you for the nice introduction. I'm... I'm being facetious. It's the end of the day. Everybody's tired. We all want to go to sleep, right? Yes. Let's go party. I'm Sal Soghoian. I'm the AppleScript Product Manager and the Automated Product Manager for Apple Computer. Thank you for coming here today and spending some time with me.

When we originally were talking about what sessions to design for the Developer Conference this year, one of the ideas that kept coming up was the fact that there's a lot of interest in using AppleScript, especially now that Automator has expanded the scope of what the language can do. There's been a lot of interest from programmers in using AppleScript, maybe not full-time, maybe just an occasional script. And it's always been very daunting and challenging for programmers to use this language. They're very frustrated by it.

And I thought that maybe a session on AppleScript for programmers, people that already know how to program, people already know how to use code, people already know how to make money doing what they do, but occasionally want to use AppleScript and would like it demystified for them. That's what this session is about. Is that what you understood to be true? Okay.

[Transcript missing]

If you want this presentation, there is a URL that you can go get the presentation. It's up on www.automator.us. You can download this presentation in your leisure and peruse it again to become an educated scripter. That's not my real name, it's just what Steve calls me. Saul, who you all know. My real email address is [email protected]. You're welcome to send me an email.

Okay, this session, like I just stated, is for people that are used to programming, understand structures, understand, you know, constructs, understand repetitive loops, understand all those kind of things, but they're interested in learning about AppleScript and what makes it so funky and so cool. Sal Soghoian So what you're going to learn today is, first of all, what is AppleScript, what a basic overview of what the language is and how it works, all the little funky things about it, and how it can target scriptable applications, how you can refer to scriptable items within the applications, including disk items in the Finder or tracks in iTunes or other applications. Sal Soghoian You're going to learn how to find items, use AppleScript to find things. Sal Soghoian AppleScript's wonderful. Sal Soghoian It's really, really good at locating specific things within an application and then returning those back to you so that you can do cool stuff with them.

Sal Soghoian You're going to learn the basic things about how AppleScript does a repeat loop, how AppleScript does a conditional, how AppleScript does an error handler. Sal Soghoian It's a little bit different than what you're used to. Sal Soghoian Some of the things might look similar. Sal Soghoian Some of them just won't make any sense at all, and some of them you'll go, what am I doing this for? Sal Soghoian I could be having lunch downstairs instead.

And then we'll look at some of the AppleScript tools that are on the computer, like the script editor and the script menu. So let's begin. What is AppleScript? Well, AppleScript is a very high-level language that's used to control and query scriptable applications. Those include things like Microsoft Office, all the Adobe Creative Suite, iPhoto, iDVD, iTunes are some of the apps, the address book. There's a lot of scriptable applications, and AppleScript is the language that's used to talk to these applications and to get them to do what you want to do.

It's designed to be used by people who are, dare I say normal? No. Are we normal? No, we're not normal, are we? We're better than normal. Okay. So we're on this side of normal. AppleScript is designed to be used by, you know, motivated Macintosh customers who want to be able to control the computer to get it to do what they want to do. And AppleScript was originally designed back in 1992 to be that way, that tool for them to be able to control their computer. It's well integrated into Mac OS X. It's lots of scriptable applications like I just talked about.

It has scriptable access to the different frameworks, to shell web services, data events, image events, XML parsing, PList parsing. All of those things are accessible from AppleScript. So the scope of the language is rather broad. It can do a lot of different things. It's a duct tape role that covers the entire computer.

And now we have AppleScript Studio, which allows you to build applications, native Mac OS X applications, using AppleScript. So we're a peer development language with the other languages in the operating system. And now with Automator and Tiger, we've taken it to the next step where you can take discrete bits of functionality and present them to the customer and allow them to put them in the order that they want to accomplish the kind of things that they want to do. Now, 80% of Apple's top-tier customers use AppleScript.

For example, this picture is of a rack of excerpts. Those racks of excerpts are handling 7,000 print publication jobs daily. I can't tell you where the company is, but that's a rack of excerpts running different applications, all controlled with AppleScript. This is a money situation. AppleScript's really a money technology.

There are a lot of major corporations that you know about that build their business using this language. So even though it's fun and it's easy to write, it's a very powerful language and it has money attached to it. How does it work? Well, you compose these AppleScript scripts.

Oh, it actually looks nicer up there. Are designed in an editing application like Script Debugger, which is from late-night software. Wonderful script writing tool and debugging tool. Or the Script Editor application, which comes in your application's AppleScript folder. And this is what a script looks like. This is a script window.

And you can see it's very fancy interface to it. The scripts are written from left to right, and they're read from the top down. Makes sense, right? When executed, a script, statements, and commands are converted by the operating system into Apple events that are sent to the targeted application. And then the application does whatever it is you're telling it to do and returns the result back to the script.

For example, tell application finder to get the name of the front finder window, returns the result here of whatever the front finder window is. So it's this communication circle that AppleScript's really good at. It's not the Apple event architecture, because that's part of the core of the OS. It's a high-level language that controls and queries the Apple event architecture underneath it. And it's your best friend for doing quick things, for doing powerful things, for doing redundant tasks. AppleScript's really great.

Now, you can save scripts once you've written them as documents that get run from the system-wide script menu or an application script menu like the script menu in iTunes or Soundtrack Pro. Or you can save them as self-running applications that look like this, or as self-running applications that accept items dragged onto them, hence the blue arrow, meaning drag onto me. That's called a droplet.

AppleScript has an English-like syntax, and now here's where everything gets funky. It's not the normal kind of language that you're used to. For example, what do I mean by English-like syntax? Okay. Move the green car before the red car. That's something I would say. Get the name of every student whose graduation comes after June 1st. That's something that we would say. If your first name begins with a B, then stand in the line on the left. Otherwise, stand in the line on the right.

Now, these are kind of statements that are typical to the English language. These are the kind of statements that we use every day. Well, AppleScript was designed to mimic this kind of a syntax. So the goal being that someone could just think of what they want to do and the actual code would be what they just thought. Of course, it didn't count on TV dumbing down America so that we can't speak anymore. But that's the basic principle of what's going on. I can't resist being political.

So let's look at a syntax comparison. Now, can you see that? Yes, okay, good. This is a script from using Python. Are you familiar with Apps Script, which is a -- it's a Python scriptable OSA thing? So let's take a look at the difference between the two languages and how they are functionally different.

Now, let's see, what does this do? Well, I know that it uses the finder, and it gets something. Okay, what's it going to get? It's going to get the name of folders -- get the name of every folder of home, of the home directory. So it's going to have -- tell the finder to get the name of every folder of home. Well, that's what AppleScript is. So there's the same thing, but in two different languages.

You can see that there's totally a 180-degree different approach in the way that the syntax is done. So let's take a look at another one. Okay, let's see. This is going to count the words of documents one. Tell TextEdit. Okay, this is going to have TextEdit count the words of the first document.

Yes. Tell app.txtedit to count the words of the first document. So that's the same thing in AppleScript. Let's take a look at this one. This one has something. Ooh, it's got a test. Let's see. It's going to delete test something. It's is equal to a return. Test paragraphs, document one. Tell application text edit to delete every paragraph of the first document where it is a return. Okay.

Tell TextEdit to delete every paragraph of the front document where it is a return. So inherently 180-degree shift in your thinking. This is a little bit of a challenge, but we're going to spend some time looking at the syntax so that you can understand why it's this way and how you can momentarily escape reality and let your mind drift and write a line of AppleScript and then come back into writing some structured code again.

So here's a typical way that AppleScript is written. One of the things that AppleScript is commonly used for is to get and set the values of various properties of scriptable objects, whether it's the color of a box or whether it's the font of a word or something. Sal Soghoian So here's a typical syntax. Set the property of some object to a certain value.

An example of that would be set the color of the current box to red. Set the name of the third track of the first playlist to Fred. set the label index of every folder of Home to 3. So this type of syntax is very common to AppleScript. And once you're familiar with that, once you understand that, then it'll become easier for you to learn how to write these types of scripts.

[Transcript missing]

The syntax of AppleScript is similar to English. It says what it does most of the time, and that's why a lot of customers like it. It's because they can go back into their scripts months later and actually read the script and figure out what it does. "Buy Maalox by the gallon" because no matter what you do, it's going to drive you crazy.

So let's look at how you use AppleScript to talk to an application. You notice I'm using these friendly terms like talking. It's all part of my plan. So a tell statement. Well, tell statement is the rudiment functional statement of AppleScript. It's the workhorse of the AppleScript world. It targets a scriptable application.

It's a single line beginning with the verb tell. It contains two elements. One, a reference to the object that you're going to be scripting. And two, the action that you want to be performed. This structure is the heart of AppleScript. Most of what you do with AppleScript follows this idea of using a tell statement to target an application or a scriptable object. And they always contain a reference to the object. So a tell statement is a reference to the object that you're going to script and the action to be done.

Makes sense, right? For example, tell application QuickTimePlayer to tell the front movie to tell the last track to get its duration. So this particular version of syntax I wrote to mimic the kind of dot structure that we saw earlier. Now, the reference to the object in here is the front movie and the last track. So you can see that the front movie owns the last track and is telling it to do something. The action to perform in this case is to get its duration.

Now, this is not a typical syntax that scripters would use. They would most often say it's something like this. Tell application QuickTimePlayer to get the duration of the last track of the front movie. This is a valid tell statement because it contains the two things that we're looking for. One, a reference to the object that's going to be scripted.

In this case, the last track of the front movie. And two, the action to be performed. In this case, get the duration. So, any way you want to put these two things together, as long as you have a reference to the object that's going to be controlled, and the action to be performed, and the statement starts with the verb tell, followed by the object that's the parent object, which is usually the application, you're fine. Any way that you want to write it is fine indeed. It will work. And if AppleScript works, it's right. There is no right way to do something. There's no right way to make money. Well, maybe there is, okay.

So this is usually the way that you'll see AppleScript done. Notice the little new line character over there, which is option L or shift return. That just indicates that I couldn't fit it all on one line, and that's all that is. So here's a tell statement. Let's look at some more examples of what a tell statement looks like. Again, it begins with the verb tell, right? And it always contains a reference to the object to script and then the action to perform.

Tell application iTunes to delete every track of playlist My Party List whose artist is Bon Jovi. Okay? And this, I like them. I do. I listen to them. When nobody's around, I'll be listening to them and all the old stuff from the 70s. I am that old. I'm a dinosaur looking for a tar pit.

Okay, so what is the object to control? What is the scriptable object we're looking for? In this case, it's every track of Playlist My Party Mix whose artist is Bon Jovi. That's the first element of the tell statement. What is the second? The action to perform. And in that case, it's the verb delete. So this tell statement contains everything that we're looking for and will function and execute in iTunes very easily. It cleans and waxes in one motion. It's very nice. It not only finds and it does at the same time. Finds, does. Finds, does. The power of AppleScript.

Let's take a look at another one. Tell Application Finder to duplicate every document file of the entire contents of Fullscript. It's the object that's being targeted. It's every document file of the entire contents of Folder Documents of Home whose name contains Smith Project to the disk name backup.

Woof. Okay, what does that do? Well, it goes into your Documents folder, finds every documents file that contains the name Smith Project in its name, then copies it over onto this disk name backup. All of that done with one line of AppleScript. First of all, it's the object that's being targeted. It's every document file of the entire contents of Folder Documents of Home. It's the object that's being targeted. It's every document file of the entire contents of Folder Documents of Home whose name contains Smith Project to the disk name backup.

And the action to perform is duplicate to the disk name backup. Now, here's an interesting split, right? This is typical in the English language, and it drives people crazy, especially Germans, when they're trying to learn the English language, is that you kind of split things a lot with English. But that's very typical. The action to perform is duplicate those items to the disk name backup.

Now, there'll be often times, does any of this make sense? Does that kind of make sense? Groan if it does. Okay. You're going, yeah, it makes sense, but I don't want to learn it. I don't want to. You can't make me learn it. Oh, no. Okay. Now, there's times when you want to do more than just one thing with a group of a scriptable object, right? You might want to perform a series of actions with it.

Well, instead of writing a series of tell statements, there's this construct in AppleScript called a tell block. And a tell block targets one or more actions at a scriptable object. It opens with a, it has an opening statement. Pardon me for a second. This has no gin in it. Okay.

[Transcript missing]

It gives you better visual organization. So here's our same script again. Now, you'll notice that the sections up here all pertain to doing something with the finder preferences. Well, instead of writing each line, "Set desktop shows removable media of the finder preferences to false," and then doing that over and over, we can put all of those statements within their own tell block that talk to the finder preferences object. So to do that, you do something like this.

[Transcript missing]

Now, the tell blocks only affect the things that are within their scope. The statements that are in blue right now still are controlled by the thing that's on the outside, the outside tell block, which is the finder. Sal Soghoian So, we went from this to this. That's an example of nested tell blocks.

Okay, so that's a basic structure of AppleScript, the tell block, nested tell blocks, and then you come across these. Sal Soghoian You'll see these quite a bit in people that are learning the script, you know, for the first time, is they kind of walk the object hierarchy using tells, and it looks something like that.

Sal Soghoian You know, tell application finder to tell home to tell home. Sal Soghoian You know, tell folder documents to tell folder Smith project to tell every item, set the label index to three, set the comment to Smith project final, and then you have all these closing enta, enta, enta, enta, enta, enta.

Well, you know, there's a more elegant way to do that, and you'll probably end up doing it yourself. A much cleaner way to do that is something like this, where you have an outer tell block that is the application, and then an inner tell block where you're opening part of that statement is a little bit longer reference to a particular object. It doesn't have to be a single object. It can be part of an object that's in an object hierarchy, in this case, folder documents of home.

And it's a tell block just like any other tell block, and the things that occur there pertain to folder documents of the Smith project folder of the finder, of the home folder. So that's an example of a...

[Transcript missing]

What does activate do? It's kind of like tan hut. It means come to the foreground. If you're not already launched, activate means launch the application. The verb launch means open but don't show any UI, open up in the background.

Here's just a little other tip. That's basically the idea behind tell blocks. Now you saw that I set a lot of properties using the tell statements in that tell block. Here's just a shortcut for you. With some applications like the Finder, you can set all the properties in one action by setting the property record. Here you go.

Set the properties of the Finder preferences to, and then you'll notice that there's this thing here. There's a curly brace, and it goes all the way down there with stuff in it, and it ends in a curly brace over there where it says .668. This is a record, a property record. These are the key values or the properties that you're going to be setting, and then there's the values for those that match them.

They're separated by a colon. So desktop shows hard disk colon value false. Desktop shows removable media colon false. Desktop shows connected service false. So by executing this one line of AppleScript, you can set all of those properties in one motion rather than having to execute a series of tell statements.

That's just a little tip that I'm giving you extra here. Okay. So that's tell blocks. That's the basic structure of how to write a script using a tell statement where you're directing an action at a specific scriptable application or scriptable object. A tell block, a tell statement only uses a tell statement. A tell statement always contains a reference to the object that you're going to control and the action to do with that object.

Does that help clear up a little bit of the mystery about how tell statements are done? A little bit different, isn't it? Yeah, once you get used to it, it's not so bad. Well, let's look at some of the AppleScript data types. Like, what are the kind of things that AppleScript can deal with? Well, it deals with integers. So there's some integers. It deals with reels. So there's some reels. It deals with strings.

It deals with Booleans. But we don't call them zero and one. We call them true and false, right? and it deals with lists. This is a list. You might call them arrays. And they always begin with an open curly brace and a closed curly brace, and they can contain anything.

Any data type supported by AppleScript can go inside the list, even other lists like down there. So you can have lists of lists of lists of lists or lists of lists of lists of lists or numbers and text together. Lists are really, in AppleScript, can contain whatever you like. This is the record that we just looked at. It kind of looks like a list, but it's really a set of key value, key value, key value kind of things.

Those are the data types that AppleScript supports. There's probably some more in there too, but those are the basic ones that we need to know. Any questions about those? Okay. Operators. Well, let's look at these. In addition, we use the plus sign as a plus sign. Think of AppleScript's operators as the ones that you would learn in the fourth grade. We even have a rounding control for AppleScript.

There's a verb for rounding, and it says, round as taught in school. and it takes from .5 up and stuff like that. So there's addition. Multiply, we use the asterisk.

[Transcript missing]

We also have an exponential, which looks like this. So that's 2 to the fourth power 16. The square root of 4 would be an exponential 0.5.

And we have concatenation for text. So once upon a time and in a village far away, we used the ampersand character, a single ampersand character, as a way to concatenate items in AppleScript. In this case, if you concatenated those two, it would be once upon a time in a village far away.

There's no space in there. With AppleScript, you can actually add a space by putting the word "space" in between the two. So once upon a time plus space in a village far away would give you once upon a time in a village far away. As a matter of fact, there's a couple special terms you can use the word "space," "tab," or "return" for paragraph return, anywhere in where you're concatenating text together, and AppleScript understands that. You can can cat, can cat, can cat. You can can add lists together. You can join lists together.

[Transcript missing]

That's it. That's our basic characters. You see that we don't have cosine, tangent, that kind of stuff. AppleScript is kind of weak on those areas. There are subroutines you can do, but it's often great just to drop into the shell for a second, do shell command, and then cosine of blah, and then take that and go out with it. Let's look at some basic coercions that AppleScript uses.

To coerce something, you use the term as followed by the class that you want to coerce to. For example, this text string of the character 1 as integer would give you the number 1 as integer. 1 as a Boolean turns into true. Naturally, 0 as a Boolean would turn into false.

1 as Unicode text turns into 1 as Unicode text. And Fred as a list turns into a list of 1 with Fred. These are some basic coercions that you're going to use quite a bit when you're in the world of AppleScript. There's a couple more coercions we're going to see as we go along here.

uses text item delimiters when you want to course lists to strings. Here is our list of people. Sal Soobob. When you course a list to a string, you will get them all jumbled together to Sal Soobob. You will have this thing called AppleScript's text item delimiters. You can set AppleScript's text item delimiters to whatever you want. In this case, I'm using a dash.

Then I'm going to say, "Okay, now take that same thing as Unicode text." That would change it to this. Then remember always to set your delimiters back to a null string, which is two straight quotes. You don't want to leave your delimiter set for something weird in case you have another script that's using delimiters and all of a sudden, you're going to have to change it.

You don't want to leave your delimiter set for something weird in case you have another script that's using delimiters and all of a sudden, you're going to have to change it. delimiters and all of a sudden your stuff starts changing because it's a global thing. Which brings us up to the topic of variables. All right. So, this is so great for me that I don't have to explain what a variable is. This is amazing.

Do you realize how hard that is to explain this concept to somebody that's, you know, not a programmer? You know, it's a container like a Tupperware. You put stuff in, you take it out, right? Yes. So, I'm really, I am so thrilled. You can use that. You can use it. So I'm so thrilled to be talking to an educated group like yourselves. Very handsome, I might add, too. Because what I'm about to tell you will drive you mad.

Okay, a variable to AppleScript, it considers things variables that any word or contiguous bit of text that is not part of the AppleScript language itself. So when you're in the script editor, you'll see words that are bolded. Those are AppleScript's own words, like every, tell, by, the, those kind of things. You can't use those as variables. Also, the terminologies of any scripting additions.

AppleScript has an extensible architecture that uses these things called scripting additions to enhance the language. They're global in scope, so they work all the time, regardless of whether you're in a tell block or not. So you have to be aware of their terminologies, too. And finally, if you have a variable being declared within a tell block, you have to make sure that the name of the variable that you're using is not part of the application's own scripting dictionary.

Variables can contain any data type supported by AppleScript, like numeric, textual, lists, references, image data, booleans, enumerations, records, whatever you like. Variables do not need to be declared or typed. Whoa. All variables are local unless indicated otherwise. Okay, so let's look at this. Any word or contiguous text not part of the AppleScript language or terminology. So let's say, so X. X is usually a good variable. Here's one, page 12. This underscore project. The last strawberry.

You can even use words separated by spaces as long as you put the vertical pipes around them, then they will be considered a variable as well. So, it's pretty flexible as to what you want to call or name your variables. Everybody has their own style of variable naming and their own procedures for doing it that make sense to them. Use whatever you want. AppleScript doesn't care.

For example, now in this instance, you'll see that it says set folder to path of the startup disk. Well, it's trying to use folder, the word folder, as a variable. It can't do that because the word folder is part of AppleScript. You can't use that as a variable. Sal Soghoian So what you can do instead is you set a folder to path to the startup disk, and then what happens is the path to the startup disk is now placed into the container called a folder. The verb set is used to instantiate that variable.

Here's another example. Tell application iTunes, "Set track to the first track "of the front library playlist." Well, the first track there can't be used as a variable name because track is part of the iTunes dictionary, and it goes, mm-mm, does not compute. So what you wanna do instead is do something like this, "Set this track to the first track "of the front library playlist." If you run it, you get back some reference that looks like this.

[Transcript missing]

Okay, that's the basic idea behind variables. Let's look at item references, or how you refer to AppleScript objects. This is the one thing you must know. Scriptable objects are referred to by their position in their object hierarchy or where they are in their chain of command. In order to identify a scriptable object to AppleScript, you have to say it in one of those manners. You have to identify it as being where it is in its chain of command.

For example, Nested references. There are different kinds of references. There's nested references, path references, alias references, Unix references, and file URLs that we're going to look at. I'm going to focus a lot on the finder and dealing with files, because that's a common thing that programmers have a hard time dealing with AppleScript is, "Okay, I've done everything I can to move this file from here to there.

It won't do it. What am I doing wrong?" Although the same principles that we're going to see here pertain to scriptable objects within other applications like iPhone or iTunes or QuickTime Player, we're going to focus a little bit on the finder so that you get some hints about how to deal with files. So let's look at a nested reference. Nested references are described in items positioned in its object hierarchy from the bottom of the chain all the way up to the top, and they use the possessive term "of" to identify containment within that hierarchy. in that hierarchy.

Nested references are the default reference format returned by scriptable applications such as the Finder, System Events, or iTunes, or Soundtrack Pro. And they can also be used for other applications besides files as well. For example, folder document, a folder username, a folder users of startup disk. You'll notice that it uses the possessive of to indicate that it belongs to folder username that indicates the possessive of to indicate that it's part of folder users, that it also belongs to the startup disk. Document file, cars, PDF of folder documents, a folder username of the folder users of the startup disk.

Frame 13 of Track Video Overlay of Movie 2. That's a nested reference. Text Box 4 of Page 2 of Spread 13 of Document 1. It's kind of like a mailing address, right? Sal Soghoian, 123 Elm Street, Anywhere, USA. That's how you're identified by your location, where you are in your object hierarchy, where you are in your chain of command.

Transition 3 of Video Track 2 of Program 1 of Project TV. So these kind of nested references are the default format that AppleScript applications return when you request something. When you're querying an application to find a particular object, you always get back these nested references. And they all use the possessive of as a way to indicate containment.

Let's look at path references. Now we're going to start dealing with files. So those are nested references that the Finder uses, that the System Events app uses, and that other scriptable applications use. But let's look at some of the other kind of file references. And this is some of the stuff that really gets people that aren't familiar with AppleScript. And we're working toward changing this to make it universal, but for right now, this is your new nightmare.

Path references are used to pass references to a disk item to the finder system events. They are text strings read left to right that contain the names of each item in the hierarchical chain, and they're delineated by colons. They are preceded with a class identifier, something like disk, folder, document, file, or item. And path references to folders and disks always end with a colon. Here are some examples.

A disk Macintosh HD colon. So that's a path reference to a disk that's mounted on your computer. Folder Macintosh HD colon users colon username colon documents colon. So there's the path, the HFS path to that particular folder, and it's preceded with the class identifier folder. Item is a generic way to talk about anything. It could be a file or a folder or a font, a suitcase or anything. There again is a path.

Document file Macintosh HD user Sal document, same kind of idea. Item is another generic way to get to something. So that's all within the finder. You can use the system events app, too, to talk, to refer to objects using these kind of path things as well. The only difference is that the system events app uses the class identifier file instead of document file that the finder uses. Now, you can construct that. You can construct these things yourself and then pass them to the app and place the proper class thing in front of it, and the app will respond and work with it. That's a path reference.

Alias references, they're universal. All applications use alias references and will accept them. And they're very similar to a path reference. Only difference is that they are preceded with the term alias, and they're also referred to items that are actually there. So if you have an alias reference to a font, and you have an alias reference to a file on your desktop, and it's in your script, you close the script, move the thing on the desktop to a different folder, open your script back up, it will now be, the alias reference will now be in the new location. So when you use an alias reference, it has to be to something that's not theoretical, but actually on disk. If you're using something theoretical, then you can use a path and pass that to the application instead.

can be used within or without tell blocks. Alias Macintosh HD. Here is another one to a file. POSIX references. They are based upon the Unispace architecture. They are not usually supported by scriptable applications. There are a couple of scriptable applications that will accept them with the open command, but generally you are better off not using those and instead coercing them into alias. Let's look at some examples of a POSIX path.

See, that's a typical thing. And there's a quoted form, naturally, on the end. Now, POSIX references, when you want to convert them from a POSIX reference to an alias that you can use with AppleScript, there's a couple ways that you can do that with AppleScript. We do provide some light out of the darkness.

There's this thing called POSIXPATH in POSIXFile, and it looks like this. So the POSIXPATH, if you want to derive the POSIXPATH of an alias, of an AppleScript alias reference, you just put POSIXPATH of in front of it, and you'll notice that you returned the POSIXPATH to that particular file or folder or whatever it is. If you want the quoted form, instead of having to use concatenation with a bunch of strings, just ask for the quoted form of the POSIX path of, and it will derive the POSIX path for you and place it there.

Coercing POSIX Paths If you want to go the other way and change a POSIX path to a file, then you use this as POSIX file, and now you'll see it says File Macintosh HD User Sal Documents that now you can pass to a scriptable application. If you want to coerce that to an alias, do a double coercion as POSIX file as alias, and you've now gone from a POSIX path to an alias reference that AppleScript uses.

Those are your lifesavers. You can build little subroutines with those, and it becomes just an easy thing to do back and forth. Eventually, we hope to make it so that you won't have to worry about any of this stuff, but for right now, I want to give you guys the truth and the good stuff.

File URLs are really interesting. I never thought that anybody did with them until I discovered guys writing scripts that would generate HTML and actually control their drives based upon file references. If you ask the Finder and the System Events apps for a file URL on something, it looks like this.

Tell Application Finder to get the URL of folder documents of home, you actually get the real URL, and it's also encoded for you automatically, too. So then you can then take that and put it into any HTML that you're generating on the fly as well and use it that way. But they're not usually used with applications.

So when you want to coerce reference types, you can coerce these following ones together. You can coerce a nested reference to an alias reference by just saying its alias, path reference to an alias reference, POSIX path to POSIX file to an alias reference, alias reference to a POSIX path.

All of those are possible. Now here's an example. Folder applications of the startup disk is a nested reference. I'm coercing it to an alias, and now it becomes an alias. Folder Macintosh HD:applications: is a path reference. I'm coercing it to an alias, and now it becomes an alias reference.

POSIX path of alias Macintosh HD. Now I get the POSIX path back and then

[Transcript missing]

You can get a range of items by using index. You can say items 2 through 5. You can say get items 1 through minus 1, which means the same thing as saying this, get every item of the startup disk.

And you can also, since AppleScript is very verbose, you can use words like first, second, third, fourth. You can even use first there, get the first item of home. You can use these kind of things, first, 23rd, 16th, 32nd. The AppleScript language will actually accept those as well.

Items can be referenced by their position relative to other items in that list of items. You can use terms like front, first, back, last, middle. Get the last item of the startup disk, the middle track of the front library. You can use the words after or before. The item before the last item, the item after the middle item.

You can even do things randomly by using the word "some" and it will return some random item of the startup disk. The second way to find things, and this is really powerful, this is where AppleScript cooks, is by property. For example, I could say, "Everybody in the middle section who's wearing a red shirt." I just located a certain subset of people based upon a property, the color of their shirt.

Well, AppleScript does that very well too, because every scriptable item on disk belonging to an application usually has something like a name, a kind, a size, a creation modification date. And you can use those properties to locate items. The first document file whose name contains Smith Project. The first folder whose size is greater than 500,000. Every document file whose file type is JPEG.

Every document file whose name extension is PDF. So you can really use AppleScript to locate the subset of things that you want to manipulate. And you construct queries, and they're constructed by combining this. Oh, I'm going to love this. My favorite part. A positional indicator, target object type, target container, object specifier, target property, comparison operator. Yeah, target property, vague. Okay.

I just wanted to say those things because we never think about them, but that's what they are anyway. Here's a query. The first document file of home whose name contains Smith. Well, the positional indicator is first. That could be last, the second, the third, every, whatever you want. The target object type in this case is a document file. You could say folder. You could say whatever object you're looking for, track, you know, movie. This is your target container that you're looking to search.

That could be an application. That could be a directory. Object specifier, whose. You could also use where on occasion. Target property. You're looking for the name property and the comparison you're using contains. You could say does not contain, is not in, is part of, is not in, is part of. No, I don't know.

You can't say part of. Does not contain, doesn't contain, is greater than or equal to, is less than. All of the comparison operators you can use. And then there you can look, change the value. So if we wanted to do that, we could say, well, I'm going to use this. I'm going to use this.

I'm going to use this. And then I can change the value. And then, you can change the value. And then you can change the value. And then you can change the value. And then you can change the value. And then you can change the value of the query. And then you can change the value of the query.

And then you can change the value of the query. To have some other thing like Smith project, AC stats, things like that. Now, if you want to search every folder within a folder using the finder, you just say document file, the entire contents of folder documents of home whose name contains Smith project.

And that does all of your iterations and recursive routine for you all in one statement. So this is an example of how Apple script can find things. Here's another one. You can combine your searches by using the word and. Application finder to get the first item in the startup disk whose name begins with S and name ends with folder. It returns something. Here's another case of and. Every document file's name extension is in this list and name contains Smith project. And you can use both of them together.

So you can say every document file of folder pictures of home whose file type is JPEG or name extension is in this list and name contains Smith project. So using these kind of queries with Apple script, you can really locate things to work with very easily in a single line.

Instead of iterating, you can really locate them all at once. You can do four repeat loops and stuff like that. You just use one line of Apple script to find the objects that you're looking for. Now we're going to look at something else. Special folders. A common thing that programmers often have a problem with is once they understand how to find things and how to use these paths, they come up against the generic problem. You want to write a script that works on someone else's machine and you want to get to one of the designated folders.

But you don't know how to do it because you're trying to construct paths by piecing things together, getting the user name and inserting that. You don't need to. Designated folders on the computer are part of Apple script's repertoire. Now the finder has four locations that it knows about itself, the startup disk, home, desktop and trash.

So when you say desktop in a script, it doesn't make any difference how the user has named their drive or any of their other structures. It will find that folder for you and return you the path that's appropriate to the machine. Therefore, your script is generic and you can use it the way that you want. So here's an example. Every item in the desktop, everything of home.

And you can tell it to empty the trash. There's also a path to command and it has four domains that you can use. So if I want to say path to the library folder from the user domain will give me this reference, this alias reference to the user's library. Here's the local library at top level.

Here's the system library and there's the network library. So the path to command has a lot of the designated folders of the OS built into it and they're written in English. So they used to use these codes here on the left. But now since Panther, we now have implemented the words in there.

Thank you, Cheryl, very much. So now it just becomes easy to say path to any of these folders and it will get you to the path to the local folder that you need. And then you can work your way down to where you're trying to get to. And so how do you do that? Well, here's an example. You say set the parent folder to the path to the document folder as Unicode text.

You're breaking it down into a path. Then you say set the item path to the parent folder plus this name of this file. And that joins them together. And then you say set this item to the item path as alias. And then that turns it as an alias.

But what you really want to do is do all of that in one clean and waxed motion. And then you're going to see that the item path is going to be in one motion like this, using nice parens. Notice the parens. This item to the path to the document folder as Unicode text gets done first.

Then it gets concatenated and then it gets coerced into an alias, all in one motion. So that's using special folders to locate the particular things that you're looking for and then using those to get to where you want. The system events app uses those terms documents folders natively. So you can just use those within a system event app as well. Info tools.

Let's look at a couple of a couple additional tools here. You also have some other tools, the list disk, list folder, info for command and system info record that give you information about files. You'll live and die on these commands. They're very useful for you. List disk is a very simple command.

You point it, you say list disks, and it gives you a list of the disks that are mounted on your computer. If you say list folder and you point it to a particular folder, you say without invisibles, it gives you a list of all the names of the items in the folder. If you want the invisibles, then you get the dot names as well.

The info for is a really powerful command that descriptors use a lot. Info for, you give it the path to a particular file or folder, and it returns a record that looks like this. Again, a record contains the key value pairs. So here are some of the keys that pertain to that particular file. The record that you get back changes depending upon what kind of item you're asking information for, and then it matches the values that go with that.

So you can get very important things like the version, its busy status over here to see if the file's open, its file type, its extension, is it hidden, its icon position, the creation date, those kind of information you can get very quickly with a single command. So you get all the information about a file that you need to know to start working with it with the info for command. And then there's a new one in Tiger called System Info, and System Info gives you the basic information about the OS, including the Ethernet address.

And the system version, the home directory, the computer name, and the IP4 version address as well. Those are things that you often want to use in scripts, and now you have a single place to go to use them. So clean and wax is basically what we just talked about earlier, was finding something and then putting a verb before it to do something.

Like delete every file of the startup disk whose name contains Smith Project. Or move every file of the startup. Or move every file of the startup disk whose name contains Smith Project to the folder named backup. It's where you do a find and then place a verb before it. But that just works with a single item. Now we need to learn the conditionals and the repeat structures and the error handlers that allow us to go beyond that.

So conditional statement. Okay, so we have a dialogue here. Display dialogue, your prize is behind the door. This is a command to bring up a user interface that looks like this where the user has three buttons. When they click a button, the result of that is returned as a record with a key value of button return and a value of whatever button they pressed. So we're going to use this command here to demonstrate how conditionals work.

Okay, display dialog. If the button returned to the result is A, then say no prize here. So here's our command, and then this is our conditional. This is a conditional statement. It's a single-line conditional. Just one condition on a single line. It begins with the if, and then it has the thing that's comparing if the button returned is the result A. Then it has the verb, I mean, then it has the word then, and then the action to do based upon that. So that's a single-line conditional.

then it has the word "then" and then the action to do based upon that. So that's a single line conditional. So in the first comparison, if the button return to the result is not B, then you're going to do what that says. Otherwise, you have an else. This is a catch-all. It's not a specific. It's just whatever else goes to this particular action here. In this case, we have it set up so that B is the winning door and A and C are the losing ones.

Now, if you want to do three, then you can do something like this, where you have your command, and then you have a statement where you're copying the value of the button pressed into a variable called button pressed. Then you're comparing it. If it's A, then you say you want a pizza. Now you have something called else if. For each other condition that's not the generic catch-all of else, you use else if. Else if the button pressed is B, then you do this.

[Transcript missing]

Repeat loops. Let's take a look at these. Here's some of your basic repeats in AppleScript. Repeat, if you begin a repeat, you end a repeat. So it's always this in AppleScript. If you begin a tell, you end a tell. If you begin a if, you end a if. If you begin a repeat, you end a repeat. This is your most fundamental repeat, and you give it a number of times, and then it does whatever's inside of there.

Here's an example of repeat while. Repeat while some condition is being met. It has your basic repeat structure. There's your conditional while this number mod 2 is 0, and then it executes. You have repeat until, the same kind of structure, a repeat, and then there's the one until this number mod 2 is 0.

[Transcript missing]

Here's another example. Here we go, and this time I'm going to just use a repeat, same kind of thing, and I'm going to copy one of the items from the list and display it in a dialog. So when I run this, it runs four times, each time displaying a different dialog as it goes from the left to the right of the list. Now, you can also, say, change your starting number. In this case, I'm starting from three to the count of the friends list.

So in that case, I get two dialogs, right, because I'm starting from the third item in the list. I can go change the, where I want to end my repeat. So in this case, I'm getting three dialogs from the first to the third. See how this works? Now, in this case, here we go again, I'm going by two. Notice the by two.

So in this case, it skips every other one in the list, and you can iterate every other object in the list by adding the by two to your repeat. Now, if you want to go backwards down your list, you go I from the count of the friends list to one by minus one.

And now we get Scarlett, Carl, Sue, and then the Sal. You can also do the skip every other one in reverse and get Scarlett and Sue by adding by minus two, and that's your basic repeat structures. So you have your conditionals, your basic repeats. Here's your error handlers.

Fred as integer. If we try doing Fred as integer, you'll get this. You get an error because you can't coerce the word Fred into an integer, right? Well, if we want to protect ourselves from that, we can do this thing called the try statement or error handler. If you begin a try, you end a try, just like anything else in AppleScript. You start, you end it, and anything in between, if there's an error, it just doesn't post the error and the script continues.

It doesn't stop. It just continues. Now, if we want to do something with that error handler, then we try something like this. Fred as integer. Now, you'll notice that we have the try opening and closing here, and now we have this new thing in the middle called onError.

So, any script statements before that, if one of those cause an error, it jumps down to where it says onError and then executes whatever you have in between the onError and the end try. In this case, we have a dialogue that will display saying there was a problem. Not too useful, but at least it lets the user know something happened. We control the error, not the OS, and when the user clicks the cancel button, the script will stop.

If we want to do something that has a little bit more meaning, we can get the error message that's returned from the system by placing a variable after the onError, and then use that variable down there in our script so that now we get the error message that was created by the system. In this case, can't make Fred into an integer.

So here's another example. You'll notice in this one, we're starting off the script. It's going to ask the user for a file that's a JPEG. Then it's going to use the image events application to flip it horizontally. Now, in that open dialogue where you're asking the user to find a file, if they click the cancel button, you'll get this, right? It'll drop down because it's throwing a -128 cancel error, and it will display this. Well, the user knows that they canceled.

They don't need to see that again. So how do we take care of that situation? Well, we do it by...

[Transcript missing]

Subroutines and Handlers I'll give you a quick one on this one. Here's some routines where I'm using the save verb to say something using different voices. It's a pain to write that. We can turn it into a nice little subroutine like this. This is the subroutine.

It's at the bottom of your script. You usually put them there. You notice that it has a name, speak, and it has pass parameters here that you used inside the subroutine. To call it, you just call it from within your script by using the name of it and passing in some parameters.

So that will be your subroutine. Now, if you have the subroutine and it's within a tell block from another application like this, then you'll have to put the word my before the subroutine so that the script knows that that subroutine belongs to the script and the finder won't look for it in its own dictionary and throw an error. And that's how you use subroutines. You can use the open handler. It looks like this. I open these items.

You get this. You save your, your script as an application, and it becomes a droplet just by having an open handler in it. When you have an open handler, anything that's dragged onto it will be put into these items. They will be references to the files or folders or whatever it is you drag onto them. They look like this. You'll look at it in the slides when you get home later tonight and go, oh, okay, cool. This automatically searches them and then does a process for you over here.

This one other handler I wanted to show you, this is the idle handler. Here's one that speaks the time every 15, every 10 minutes, and you'll notice that it has an idle handler like this. It has on idle and end idle, and it has this, there's the things that happen, and at the end, you return the value that you want to wait. You save this as a self-running application and make sure that you have the stay open thing saved, and now you have a script that runs in the background and will do whatever you want.

So that's just a little bit about, well, I don't know, I don't know if you've ever heard of it, but it's a little bit about, well, I don't know if you've ever heard of it, but it's a little bit about, what AppleScript is. I was amazed that we actually got through all that. That's pretty good. And we don't have any time for questions, but what I want you to do is instead come to the hands-on lab, come visit the AppleScript team, go to the AppleScript website, and also download this presentation and use it. Thank you so much. Appreciate it.