Learn to Program using Alice

World-Level Methods

Learn about writing and using world-level methods that require parameters.  Also learn about some restrictions (relative to more conventional OOP programming environments) that exist in the Alice approach to passing and using parameters of type Object.

Published:  April 1, 2007
Last updated:  October 25, 2007
By Richard G. Baldwin

Alice Programming Notes # 145


Preface

Part of a series

This tutorial lesson is part of a series designed to teach you how to program using the Alice programming environment under the assumption that you have no prior programming knowledge or experience.

Have some fun

Because Alice is an interactive graphic 3D programming environment, it is not only useful for learning how to program, Alice makes learning to program fun.  Therefore, you should be sure to explore the many possibilities for being creative provided by Alice while you are learning to program using these tutorials.  And above all, have fun in the process of learning.

General

In the previous lesson titled "Data Types and Variables" I taught you about data types and variables.  I presented and explained two Alice programs.  The first program illustrated the use of local variables for storing data that is completely internal to a function.  The second program illustrated the use of variables for saving input data provided by the user for later use by the program.  I also explained the difference between local variables belonging to methods, and property variables belonging to objects.

In this lesson, I will teach you how to write and use world-level methods that require parameters.  I will show you how to use the incoming parameters in code that you write in the method.  I will also alert you to and explain some restrictions (relative to more conventional OOP programming environments) that exist in the Alice approach to passing and using parameters of type Object.

Viewing tip

I recommend that you open another copy of this document in a separate browser window and use the following links to easily find and view the figures and listings while you are reading about them.

Figures

Listings

Supplementary material

Once you have mastered Alice, I recommend that you also study the other lessons in my extensive collection of online programming tutorials.  You will find a consolidated index at www.DickBaldwin.com.

General background information

You can define new methods at either of two levels in Alice.  Whether the distinction between these levels is real or conceptual isn't clear.  In any event, the two levels are commonly referred to as follows and you should treat them as being real:

Regardless of the level, each method that you define may require incoming parameters or it may not require incoming parameters, depending on its purpose and your programming approach.

You learned a lot about how to write world-level methods with no parameters in the earlier lesson titled "Learn to Program using Alice, The Program Development Cycle" (see Resources).  I won't go over that material again in this lesson.  Rather, in this lesson, I will concentrate on writing and using world-level methods that do require parameters.  I will tackle class-level methods in a future lesson.

Preview

I will present and explain two programs in this lesson.  The first program named Alice0145a illustrates writing and using world-level methods that require a parameter of type Object.  In the process of that explanation, I will expose and explain some fairly serious restrictions (relative to more conventional OOP programming environments) that exist in the Alice approach to passing and using parameters of type Object.

The second program named Alice0145b illustrates passing and using parameters of type Number and DirectionThese parameters are used in the conventional manner to instruct a method that knows generally how to behave how it should behave specifically.

Discussion and sample code

The program named Alice0145a

This is a relatively simple program that defines and uses a world-level method named closeOrderDrill to cause a drill team consisting of three penguins and three cows to perform in a manner similar to the drill team at the local high school at half time during the Friday night football game.  Although I could have used any of the objects from the gallery to populate this world, I chose penguins and cows for a very special reason that I will describe later.

Figure 1 shows the drill team standing at attention awaiting the command to begin marching.

Figure 1. Drill team standing in formation in program Alice0145a.

Marching to the right

Figure 2 shows the drill team marching to the right.

Figure 2. Marching to the right in program Alice0145a.

Write or download and run the program

If you either write or download this program and then run it, you will see that the drill team marches in a square ending up back where they started.

To write the program, you will need to create a new world and populate it with three penguins and three cows as you see in Figure 1.  Rename the penguins penguin1, penguin2, and penguin3, and rename the cows cow1, cow2, and cow3.  You don't need to be concerned about their initial positions because that will be taken care of in software when the program first starts running.

Rename the default method to main.

A new world-level method

You will need to create a new world-level method named closeOrderDrill with one parameter of type Object named theObject.  I will explain how to create this method later.  Remember, however, that as you learned in the earlier lesson that explained the program development cycle (see Resources) you must define methods in Alice from the bottom up.  That means that you must complete at least a stub for the method named closeOrderDrill before you can write the code for the main method.

Source code for the program named Alice0145a

Listing 1 presents the source code for this program.  You can also download an executable version of the program (see Resources).

Write the method stub for closeOrderDrill

Because Alice requires you to write methods starting at the bottom of the hierarchy and working your way up from there, let's write a stub for the world-level method named closeOrderDrill.

Select world in the object tree and select the methods tab below the object tree.  Click the button labeled create new method.  This will cause a New Method dialog to appear on the screen.  Enter the name of the new method in the dialog and click the OK button.  When the dialog goes away, a new tab should appear in the program edit pane showing the name of the new method in the format world.closeOrderDrill.  This indicates that this is a world-level method.

Declaring a parameter

Make sure that the tab for the new method is highlighted and click the button labeled create new parameter.  This will cause the Create New Parameter dialog to appear on the screen as shown in Figure 3.  (Note the similarity of this dialog to the dialog for creating variables that you learned about in the earlier lesson on data types and variables, see Resources.)

Figure 3. The Create New Parameter dialog.

Deleting an unwanted method
Lots of items in Alice can be deleted by right-clicking the item and selecting the delete entry in the resulting popup menu.  However, that is not the case for methods.  If you create a method and decide later that you don't need it, highlight the object to which the method belongs in the object tree, select the methods tab below the object tree, and drag the tile containing the name of the method to the trash can at the top of the screen.  If other methods reference that method, you will need to go through a clean-up dialog before you will be allowed to delete the method.

Populate the dialog

Enter the name of the parameter into the text field, select the radio button for type Object, and click the OK button.  When you do this, the method signature in the edit pane for your new method should show that it requires one parameter of type Object named theObject.

The method stub is complete

That completes the definition of the stub for the new method.  The existence of the stub will make it possible for us to write the code for the main method that calls the closeOrderDrill method.  We will write the main method at this time and come back later to fill in the body of the new method.

The main method

Take a look at the source code for the main method in Listing 1.  All of the code in the doTogether block that follows the comment beginning with "Set the stage..." is code that you have seen before, so I won't explain that code in this lesson.  The purpose of this code is to get all of the members of the drill team in position.

Do the drill

Now skip down to the code following the comment that reads "Do the drill."  This code begins by inserting a one-second pause in the action.  Then it calls the new method named closeOrderDrill six times.  Each call to the method passes a different member of the drill team as a parameter to the method.

Although these six method calls appear in sequential order in the code, they are contained in a doTogether block, meaning that all six methods will be executed concurrently.  Therefore, what ever the behavior of the method might be that behavior will be executed with respect to each member of the drill team concurrently.

Why not use a loop?
If we had already completed our study of loops, I would have used a loop to replicate the two motions four times in succession instead of actually replicating the code four times.  However, we haven't studied loops yet, so I couldn't use them in this lesson.

Behavior of the method named closeOrderDrill

Now skip down to the code in the new method named closeOrderDrill.  As you can see, the body of the method contains four replications of the same code that causes the incoming object to execute the same two motions.  The first motion causes the object to turn LEFT by ninety degrees.  The second motion causes the object to move FORWARD by one meter.  When those two motions are executed four times in succession, the members of the drill team have moved in a square and end up back where they started.

Note that these method calls are made on the incoming parameter.  Therefore, the two motions are applied to whatever object is received as an incoming parameter, regardless of whether it is a cow or a penguin.  In fact, it could be any object that exists in the world other than the world itself.  The method wouldn't know the difference.

Calling methods on parameters

The drag and drop procedure for calling methods on parameters of type Object is a little different from the procedure that I have presented in earlier lessons for calling methods on ordinary objects that appear in the object tree.  Although this isn't the only allowable way to do it, the procedure that I have presented in earlier lessons is:

Houston, we have a problem

The method parameter doesn't appear in the object tree, so you can't select a methods tab on the left corresponding to that object.  Therefore, we don't have a tile there to drag to the right. 

And the solution is...

Drag the parameter down from the top of the edit pane and drop it at the appropriate location in the edit panel.  When you do that, the menu shown in Figure 4 will appear.

Figure 4. Menu of available methods for parameter of type Object.

An aside regarding the writing of regular code

Although I don't believe I have mentioned it before in this series of tutorial lessons, rather than going through the four-step procedure shown above for calling methods on objects that appear in the object tree, you can write Alice code using a an approach that is similar to the approach used for parameters of type Object.  Simply drag an object from the object tree and drop it into the appropriate location in the edit pane.  A menu similar to that shown in Figure 4 will appear on the screen, allowing you to call a method on the object.

However, that approach suffers from the same problem that I will describe below.  The problem is that the menu doesn't provide access to custom methods.  That isn't a serious problem for the case of objects from the object tree.  You can always revert back to the four-step procedure described above to gain access to the custom methods belonging to objects in the object tree.

Which methods are available for the parameter of type Object?

Selecting the first item shown at the top of Figure 4, which is titled set value, produces essentially the same behavior that you get when you drag a variable into the edit pane and drop it on a line all by itself.  It allows you to set the value of the parameter from inside the method to any existing object.  Although, it isn't entirely clear to me at this time what the outcome would be from setting the value of the incoming parameter to some other value, I will leave that topic for another day.  On this day, I am interested in the list of available methods that can be called on the incoming parameter of type Object.

Sixteen of twenty primitive methods

If you examine Figure 4 carefully, you will see that the menu contains the first sixteen of the twenty primitive methods that are available in the methods tab for all objects (see Appendix A in Resources for a discussion of primitive methods).  The last four methods that appear on the methods tab are not included in the list of available methods.  However, those four methods are somewhat redundant so the fact that they are not included in the menu is of no great loss.  They are mainly convenience versions of other primitive methods.

No custom methods are available

What is a loss, however, is that the eight custom methods that are defined for penguin objects (including glide, jump, and walk) and the three custom methods that are defined for cow objects (walk, walkTowards, and tailSwish) are not included in the list of available methods.  As a long time object-oriented programmer, I understand why they are missing, and I won't bore you with the technical details.  With a more conventional object-oriented programming language, however, the type of the incoming parameter could be changed from type Object to type Penguin, which would cause those custom methods to become available.  If there is any way to accomplish this in Alice, I haven't been able to determine what it is so far.

Setting a non-existing property value
Apparently if you call a method to set a property value for a property that doesn't exist (such as the color property for the camera) the method call will simply be ignored.

A tentative conclusion

For the time being, and until I learn differently, I am going to conclude that when you pass an object as a parameter to a method, the methods that can be called on the incoming object parameter will be limited to sixteen of the twenty primitive methods that are available for all objects (other than the world object), plus five special methods that can be used to set the values of the following five properties that are common to all objects other than the light, camera, and world objects:

A workaround
See this link for a workaround for this problem.

A serious restriction

It is not possible to call any custom methods belonging to the incoming object.  This is a serious restriction and greatly reduces the benefits of modularizing your program through the writing of methods that require incoming parameters that are objects.

An outstanding teaching and learning language

Despite this restriction, I still believe that Alice is an outstanding teaching and learning language.  I mention this and other shortcomings of Alice solely to keep the purpose of the Alice programming language clearly in perspective.

The program named Alice0145b

Now that I have succeeded in throwing cold water all over Alice, let me go back and start over on a more positive note.  We might say that while a method knows generally how to behave, one of the purposes of parameters is to instruct the method on specifically how to behave.

The closeOrderDrill method knows how to behave

Consider the method named closeOrderDrill in Listing 1 for example.  This method is written in such a way that it already knows specifically how to behave because it doesn't have any optional behaviors.  In particular, the method causes the incoming object to make the following movements four times in succession:

Making the method more general

We could make the behavior of this method more general by allowing for optional behaviors.  For example, we could change the specification for the behavior to cause the incoming object to make the following movements four times in succession:

Note that in this new specification, the actual direction to turn and the actual distance to move are not specified in the behavior.  Therefore, this method will need some help in knowing how to behave whenever it is called.  That help can come in the way of two additional parameters, one containing the direction to turn, and the other containing the distance to move.

Source code for the program named Alice0145b

The source code for the program named Alice0145b is presented in Listing 2.  You can also download an executable version of the program (see Resources).

Consider the code for the method named closeOrderDrill shown in Listing 2.  The first thing to notice about this method is that it has two new parameters:

Creating the two new parameters

The procedure for creating these two new parameters is the same as before with one minor difference.  For the parameter of type Direction, you will need to click the radio button labeled Other in Figure 3, and then scroll down the list and select the item labeled Direction.

Using a parameter in program code
To use the value of a parameter in code that you write in the method, simply drag the name of the parameter down and drop it into the appropriate location in the statement that you are writing.

Substituting parameter values

Now consider the two statements in the first doInOrder block, noting the values being passed to the turn and move methods.  Whereas in the earlier program, the direction parameter for the turn method was hard-coded as LEFT, this parameter now contains the name of the second incoming parameter, which is named direction.

What this means is that before the turn method is called, the program will extract the value contained in the incoming parameter named direction and will pass that value as the first parameter to the method named turn.  Therefore, the method that called this method (main in this case) is able to control the behavior of the method named turn, which in turn controls the behavior of this method named closeOrderDrill.

The same treatment is applied to the distance parameter in the call to the move method.  The contents of the parameter named distance are passed as the second parameter to the method named move.

A more general method with optional behaviors

Therefore, this version of the method named closeOrderDrill knows generally how to behave, but it doesn't know specifically how to behave.  Its specific behavior is determined by parameter values that are supplied by the method that calls this method, (which in this case is the main method).

The main method

Now turn your attention to the main method in Listing 2.  You can skip over everything down to the comment that reads "Do the drill," because all of that code is the same as before.

Note the parameter values

Note in particular the values that are being passed to the method named closeOrderDrill each time it is called.  In the previous program, there was only one required parameter and it was the name of the object.  This time, as before, the method is called six times in succession, once for each member of the drill team.  However, in this case, two additional parameter values must be passed to the method each time it is called.

Turning instructions

In this case, the closeOrderDrill method is being instructed to cause the object to turn RIGHT each time a penguin is passed as a parameter, and the method is being instructed to cause the object to turn LEFT each time a cow is passed as a parameter.

Making the program more general
If you would like to make the program even more general, you could use the user dialog functions of the world to solicit input from the user as to the values to be passed as parameters.

Distance instructions

Similarly, the closeOrderDrill method is being instructed to cause the object to move by 2 meters each time a penguin is passed as a parameter, and is being instructed to cause the object to move by only 1 meter each time a cow is passed as a parameter.  As you might imagine, this causes the formation to behave differently than was the case in the earlier program.

Do it this way this time

In summary, this version of the method named closeOrderDrill knows generally how to behave, but doesn't know specifically how to behave.  It is up to the code in the main method in this program to instruct the closeOrderDrill method as to specifically how it should behave.  Further, the instructions on specifically how to behave can change from one call to the method to the next call to the method.

Jargon review

The previous lessons have used quite a lot of jargon.  You will need to understand that jargon in order to read and understand other programming material.  Therefore, I will review some of that jargon here to solidify it in your mind.

Modularization or modular design

In several earlier lessons, including the lessons titled "Your First Alice Program" and "The Program Development Cycle" (see Resources), you learned how to subdivide your program into methods and functions.  When programmers break up a large problem into smaller units, they are applying the principle of modularization or modular design.

Pseudocode

Sometimes when designing your program, it is useful to create a brief code-like description of the program using text that simulates the actual code in the program.  The representation using English-like statements of a solution to a programming problem, is called pseudocode.

An algorithm

Whenever you need to begin a process to construct something (like making a peanut-butter sandwich) you need to identify the steps and get them fixed in your mind:

  1. Get the bread from the pantry.
  2. Get the jar of peanut butter from the pantry.
  3. Get something that can be used to spread the peanut butter on the bread, etc.

Typically the steps involved in writing a computer program are much more complex than those required for making a sandwich.

A step by step procedure for solving a problem is called an algorithm.

Syntax

When you write a paper for your English class, you need to use correct grammar.  Otherwise, you will probably lose points on the paper.

When you write a computer program, you need to use the correct grammar for the programming language in which the program is being written.  Otherwise, it will not be possible to compile and run the program.

The term syntax refers to grammar rules that you must follow when coding in a high-level language.

In a future lesson titled "Syntax, Runtime, and Logic Errors," I will explain that one of the major problems encountered by students using languages other than Alice is making syntax errors.  While it is not possible to make a syntax error using the drag and drop programming procedure in Alice, when using languages other than Alice, it is quite common for students to fail to properly follow the grammar rules for the language in which the student is writing the program.

Source code

It is possible to write computer programs at a variety of levels ranging from the lowest level machine language to high-level languages such as Alice, Java, C++, and C#.  Depending on the language involved, the process of creating the program may involve the creation of a variety of different computer file types.

Although it is not true with Alice, many languages such as Java, C++, and C# require the creation of a file that contains high-level language code.  A file that contains high level language code is called a source file.

When you create an Alice program (world) you create Alice source code in the program edit mode using drag and drop procedures.

When you pull down Alice's File menu and select Export Code For Printing, you create a human-readable representation of your source code.  However, it is not a true source-code file (in the sense of Java, C++, and C#) because it cannot be imported back into the Alice development environment.

Format of Alice world file
An Alice world file is a zip-style compressed file containing a variety of file types such as xml, txt, png, and bin.

When you pull down Alice's File menu and select Save World, you create a machine-readable version of your program code that can be loaded back into the Alice development environment at a later time.  However, an inspection of such a file reveals that it is not a true Alice source-code file in the same sense as the source-code files used with Java, C++, and C#.

The bottom line is that there is no such thing as a true source-code file in Alice in the same sense that there are source-code files in Java, C++, and C#.

String concatenation

A common need in programming is the need to join two or more strings into a single string by connecting the end of one string to the beginning of a second string.  This is commonly referred to as string concatenation.

In Alice, this is accomplished using the function identified as a + b in the string section of the functions tab belonging to the world.

Figure 5 shows a sample of the source code that might result from the use of the a + b function to concatenate two strings.

Figure 5. Sample string-concatenation code.
public void main ( ) {
  String myFirstName = John-; 
  String myLastName = Jones; 
  String y = default string;
    y .set( value , ( myFirstName + myLastName ) );
  print( y );
}

When executed, the code in Figure 5 would join the two strings producing the following output text:

the value of world.main.y is John-Jones

Run the programs

Executable versions of the programs that I explained in this lesson are available for downloading (see Resources).  I encourage you to either download the programs, or copy the code from Listing 1 and Listing 2 into your Alice development environment and play it.  Experiment with the code, making changes, and observing the results of your changes.

Summary

In this lesson, I concentrated on teaching you about writing and using world-level methods that require parameters.  I presented and explained a program named Alice0145a that illustrated world-level methods that require a parameter of type Object.  In the process of that explanation, I exposed and explained a fairly serious restriction (relative to more conventional OOP programming environments) that exists in the Alice approach to passing and using parameters of type Object.

I also explained that some methods know generally how to behave, but don't know specifically how to behave.  I presented and explained a program named Alice0145b that illustrates this concept.

Finally, I reviewed some of the jargon that is commonly used in programming textbooks.

What's next?

The next lesson will deal with class-level methods as well as saving and importing objects, which is a form of inheritance.

Lab project

Beginning with the program named Alice0145b, create a new program.

The behavior of the new program is the same as the behavior of the original program except that the program asks the user to enter two numeric values.  The first numeric value is the distance that the penguins are to move.  The second numeric value is the distance that the cows are to move.

Modify the original program to solicit these two numeric values from the user and to use the two numeric values to control the distance moved by the penguins and the cows.

Save your world in a file named Alice145LabProjA.a2w and be prepared to deliver it to your instructor in whatever manner the instructor specifies.

Make certain that your preferences are set to Java Style in Color.

Select Export Code For Printing... on the File menu and save your source code in a file named Alice145LabProjA.html.  Also be prepared to deliver this file to your instructor in whatever manner the instructor specifies.

View a movie of the lab project

You can download and play a small, low-quality movie of my version of the lab project as it being executed from the Resume button (see Resources).  This movie was designed to give you a rough idea of how your program should behave.  The movie was purposely recorded in low-quality format in a small window in order to reduce the file size and hence reduce the download time.

Because of the low quality of the movie, the execution of your program should provide much smoother animation than the movie, and should be much less grainy than the movie.  Also, because of the low quality of the movie, the timing in the movie doesn't necessarily match the duration times specified for the lab project.  In fact, the timing for this movie seems to be worse than any of the other lab projects that I have converted to movies up to this point.

I attempted to synchronize the beginning of the recording with the beginning of the program execution by starting, then quickly pausing, and then resuming the execution.  If you watch closely, when the movie starts running, you will see the mouse pointer click the Resume button, and the movie will show one complete pass through the program.

You should view this movie in its original size.  If you allow the media player to enlarge it, the quality will be poor.

Resources

General resources

Resources from earlier lessons in the series titled "Learn to Program using Alice"

Downloads

Complete program listings

Complete listings of the programs discussed in this lesson are shown in Listing 1 and Listing 2 below.

Listing 1. Source code for program named Alice0145a.

Alice0145a's Code

Created by: Dick Baldwin

world

Methods

  public void main ( ) {
    
       // Copyright 2007, R.G.Baldwin
  // Demonstrates world-level methods with parameters.
  // Set the stage, could make invisible.
  doTogether { . . . . . . }
       // Position the camera.
  doTogether { . . . . . . }
       camera .setPointOfView( world ); duration = 0 seconds
  camera .turn( LEFT , 0.5 revolutions ); duration = 0 seconds
  camera .move( BACKWARD , 10 meters ); duration = 0 seconds
  camera .move( UP , 2 meters ); duration = 0 seconds
  camera .move( RIGHT , 4 meters ); duration = 0 seconds
  camera .pointAt( penguin2.head ); duration = 0 seconds
  }
  // Position the penguins.
  doTogether { . . . . . }
       penguin1 .setPointOfView( world ); duration = 0 seconds
  penguin2 .setPointOfView( world ); duration = 0 seconds
  penguin3 .setPointOfView( world ); duration = 0 seconds
  penguin1 .move( RIGHT , 1 meter ); duration = 0 seconds
  penguin3 .move( LEFT , 1 meter ); duration = 0 seconds
  }
  // Resize and position the cows.
  doTogether { . . . . . . . . . . . }
       cow1 .resize( 0.8 ); duration = 0 seconds
  cow2 .resize( 0.8 ); duration = 0 seconds
  cow3 .resize( 0.8 ); duration = 0 seconds
  cow1 .setPointOfView( world ); duration = 0 seconds
  cow2 .setPointOfView( world ); duration = 0 seconds
  cow3 .setPointOfView( world ); duration = 0 seconds
  cow1 .move( RIGHT , 1 meter ); duration = 0 seconds
  cow3 .move( LEFT , 1 meter ); duration = 0 seconds
  cow1 .move( BACKWARD , 2 meters ); duration = 0 seconds
  cow2 .move( BACKWARD , 2 meters ); duration = 0 seconds
  cow3 .move( BACKWARD , 2 meters ); duration = 0 seconds
  }
  }
  // Do the drill.
  doInOrder { . . }
       wait( 1 second );
  doTogether { . . . . . . }
       world.closeOrderDrill ( theObject = penguin1 );
  world.closeOrderDrill ( theObject = penguin2 );
  world.closeOrderDrill ( theObject = penguin3 );
  world.closeOrderDrill ( theObject = cow1 );
  world.closeOrderDrill ( theObject = cow2 );
  world.closeOrderDrill ( theObject = cow3 );
  }
  }
  }


  public void closeOrderDrill ( Object theObject) {
    
       // Demonstrates world-level method with parameter.
  // Note: Custom methods like penguin.walk not available.
  // Do same movement four times in succession.
  // Note: Haven't studied the use of loops yet.
  doInOrder { . . }
       theObject .turn( LEFT , 0.25 revolutions );
  theObject .move( FORWARD , 1 meter );
  }
  doInOrder { . . }
       theObject .turn( LEFT , 0.25 revolutions );
  theObject .move( FORWARD , 1 meter );
  }
  doInOrder { . . }
       theObject .turn( LEFT , 0.25 revolutions );
  theObject .move( FORWARD , 1 meter );
  }
  doInOrder { . . }
       theObject .turn( LEFT , 0.25 revolutions );
  theObject .move( FORWARD , 1 meter );
  }
  }

 

Listing 2. Source code for program named Alice0145b.

Alice0145b's Code

Created by: Dick Baldwin

world

Methods

  public void main ( ) {
    
       // Copyright 2007, R.G.Baldwin
  // Demonstrates world-level methods with parameters.
  // Set the stage, could make invisible.
  doTogether { . . . . . . }
       // Position the camera.
  doTogether { . . . . . . }
       camera .setPointOfView( world ); duration = 0 seconds
  camera .turn( LEFT , 0.5 revolutions ); duration = 0 seconds
  camera .move( BACKWARD , 10 meters ); duration = 0 seconds
  camera .move( UP , 2 meters ); duration = 0 seconds
  camera .move( RIGHT , 4 meters ); duration = 0 seconds
  camera .pointAt( penguin2.head ); duration = 0 seconds
  }
  // Position the penguins.
  doTogether { . . . . . }
       penguin1 .setPointOfView( world ); duration = 0 seconds
  penguin2 .setPointOfView( world ); duration = 0 seconds
  penguin3 .setPointOfView( world ); duration = 0 seconds
  penguin1 .move( RIGHT , 1 meter ); duration = 0 seconds
  penguin3 .move( LEFT , 1 meter ); duration = 0 seconds
  }
  // Resize and position the cows.
  doTogether { . . . . . . . . . . . }
       cow1 .resize( 0.8 ); duration = 0 seconds
  cow2 .resize( 0.8 ); duration = 0 seconds
  cow3 .resize( 0.8 ); duration = 0 seconds
  cow1 .setPointOfView( world ); duration = 0 seconds
  cow2 .setPointOfView( world ); duration = 0 seconds
  cow3 .setPointOfView( world ); duration = 0 seconds
  cow1 .move( RIGHT , 1 meter ); duration = 0 seconds
  cow3 .move( LEFT , 1 meter ); duration = 0 seconds
  cow1 .move( BACKWARD , 2 meters ); duration = 0 seconds
  cow2 .move( BACKWARD , 2 meters ); duration = 0 seconds
  cow3 .move( BACKWARD , 2 meters ); duration = 0 seconds
  }
  }
  // Do the drill.
  doInOrder {
       wait( 1 second );
  doTogether { . . . . . . }
       world.closeOrderDrill ( theObject = penguin1 , direction = RIGHT , distance = 2 );
  world.closeOrderDrill ( theObject = penguin2 , direction = RIGHT , distance = 2 );
  world.closeOrderDrill ( theObject = penguin3 , direction = RIGHT , distance = 2 );
  world.closeOrderDrill ( theObject = cow1 , direction = LEFT , distance = 1 );
  world.closeOrderDrill ( theObject = cow2 , direction = LEFT , distance = 1 );
  world.closeOrderDrill ( theObject = cow3 , direction = LEFT , distance = 1 );
  }
  }
  }


  public void closeOrderDrill ( Object theObject, Direction direction, Number distance) {
    
       // Demonstrates world-level method with parameter.
  // Specific behavior is based on parameter values.
  // Do same movement four times in succession.
  // Note: Haven't studied the use of loops yet.
  doInOrder { . . }
       theObject .turn( direction , 0.25 revolutions );
  theObject .move( FORWARD , distance meters );
  }
  doInOrder { . . }
       theObject .turn( direction , 0.25 revolutions );
  theObject .move( FORWARD , distance meters );
  }
  doInOrder { . . }
       theObject .turn( direction , 0.25 revolutions );
  theObject .move( FORWARD , distance meters );
  }
  doInOrder { . . }
       theObject .turn( direction , 0.25 revolutions );
  theObject .move( FORWARD , distance meters );
  }
  }

 


Copyright

Copyright 2007, Richard G. Baldwin.  Faculty and staff of public and private non-profit educational institutions are granted a license to reproduce and to use this material for purposes consistent with the teaching process.  This license does not extend to commercial ventures.  Otherwise, reproduction in whole or in part in any form or medium without express written permission from Richard Baldwin is prohibited.

About the author

Richard Baldwin is a college professor (at Austin Community College in Austin, TX) and private consultant whose primary focus is a combination of Java, C#, and XML. In addition to the many platform and/or language independent benefits of Java and C# applications, he believes that a combination of Java, C#, and XML will become the primary driving force in the delivery of structured information on the Web.

Richard has participated in numerous consulting projects and he frequently provides onsite training at the high-tech companies located in and around Austin, Texas.  He is the author of Baldwin's Programming Tutorials, which have gained a worldwide following among experienced and aspiring programmers. He has also published articles in JavaPro magazine.

In addition to his programming expertise, Richard has many years of practical experience in Digital Signal Processing (DSP).  His first job after he earned his Bachelor's degree was doing DSP in the Seismic Research Department of Texas Instruments.  (TI is still a world leader in DSP.)  In the following years, he applied his programming and DSP expertise to other interesting areas including sonar and underwater acoustics.

Richard holds an MSEE degree from Southern Methodist University and has many years of experience in the application of computer technology to real-world problems.

Baldwin@DickBaldwin.com

-end-