TweetFollow Us on Twitter

Rapid Prototyping

Volume Number: 14 (1998)
Issue Number: 2
Column Tag: Programming Techniques

Rapid Prototyping

by John Schettino

An Object Oriented Approach to Using FaceSpan and AppleScript to Prototype Applications

Software Development 101

Just the other day I read a posting to a Macintosh programmers news group that asked a simple but powerful question. What design methodologies do most Macintosh programmers use? As I stared at the phosphors of my monitor, I recalled my years of formal study in Software Engineering. I learned all the state of the art (in the late 80s) software design methods when I was getting my Masters degree -- but what do I actually use in practice?

The answer is a bit surprising. It turns out that I usually use a technique called either incremental development or rapid prototyping. This approach relies on my own expertise in ad-hoc design and the fact that I'm usually working alone on a project. It doesn't hold up quite so well for large programmer teams. The basic idea is to quickly implement a subset of the application, use it -- or better yet let the customer use it, see what works and what doesn't, and then repeat the cycle. Each time through the cycle refine:

  • the requirements (what the application is supposed to do)
  • the interface (how the application looks)
  • the behavior (what the application does), and
  • the design (how the application is structured)

For this approach to succeed, using tools that support very fast implementation of successive versions of the prototype is critical. Discarding the prototype once it has served its purpose is also critical. This prevents overattachment to the initial version's implementation. It also keeps me from over-polishing the prototype! For these reasons I've selected AppleScript and FaceSpan as my Rapid Prototyping Environment.

The Tools

AppleScript is the Macintosh's bundled scripting language. It is a reasonable programming language for prototyping, since it includes basic block-programming constructs, subroutines, and several data types. It supports classes with data and member functions, and fairly complex data structures. There is also a wide array of scripting additions on the Internet that I use to round out the language. AppleScript is close enough to Java, C, or C++ to allow me to re-implement the prototype in any of those languages. It also reads a bit like psudocode so it can be used as a specification language for the final implementation. The big plus for AppleScript is that it can call on third-parties to perform complex tasks. That means databases, emailers, text editors, and even the Finder can be called on to perform major portions of a prototyped application. The big minus with AppleScript is that it completely lacks any capabilities for interface creation.

FaceSpan is a product from Digital Technology International that works as an interface tool with AppleScript or other OSA scripting languages, such as Frontier. Using FaceSpan I can create interfaces for AppleScript prototypes. The interface consists of several different styles of windows containing standard Macintosh interface elements. I then attach scripts to the windows and elements to process the events they generate. All the windows and scripts are contained in a single project file. I run the project within the FaceSpan environment while I'm developing it. Once it is working correctly, I save the project as a standard Macintosh executable file. In many ways it's simpler than it sounds.

The combination of AppleScript and FaceSpan is similar to HyperCard with several key advantages. Most important is the elimination of the Card/Background/Stack metaphor. In FaceSpan each window and it's window items behave as a unit, with their own message hierarchy. This yields "Mac-like" prototypes instead of "HyperCard-like" prototypes. FaceSpan also fully supports color, QuickTime, Drag and Drop, and other key Mac technologies. It has a rich set of interface elements to choose from. I've done pretty fancy interfaces with FaceSpan, creating and destroying window items on the fly, implementing direct manipulation interfaces, and so on. Some of the more interesting effects require a bit of script code, but at least that code is easily reused in other projects.

The Method

I like methods. A method is a little less formal than a procedure. It is a general description of the steps needed to get something done. If there is something in this method that doesn't work for you, then just work around it. The primary reason I develop a prototype is to refine my understanding of the application I'm creating. I also use it to get end-user feedback early in the design and implementation process while it is easy to make changes. The method I use to meet these goals with FaceSpan and AppleScript is quite simple:

  • First, create the static portions of the interface.
  • Second, add enough AppleScript to animate the interface at the most basic level.
  • Finally, add more AppleScript to implement as much of the application behavior as is needed for the prototype.

This three-step approach is not specific to FaceSpan and AppleScript. It's the same method I use in any language. When using these tools it is just a lot faster to complete each step. Depending on the goal of the prototype it is usually possible to stop before completing all three steps. For example, a UI designer might simply want to draw a possible interface and add a bit of AppleScript to animate it. The prototype could then be handed over to users and its usability could be assessed.

Drawing Interfaces in FaceSpan

Begin with whatever you know about the desired application's look and behavior and start creating windows in FaceSpan. This is a good time to review the Macintosh Human Interface Guidelines, also known as the human-computer interface (HCI) guidelines. I'm a big fan of following these, because applications that follow the guidelines are easier for users to learn and use. The FaceSpan Window Editor is a great environment to experiment with different layouts, but even more so, it's a place where the developer can see first hand the effects of following (or ignoring) the HCI guidelines. Here's a simple example. There are detailed rules for laying out the elements of a modal dialog box. The first dialog box below follows these rules to the letter, the second does not.

Figure 1. Conforming and Non-conforming dialog boxes.

Although the two contain the same buttons, the first conforms to the HCI guidelines. The default push button is in the right location, there is a correct amount of white space between the window items and the window border, and the icon is placed correctly. The result is a dialog box that is instantly recognizable to a Mac user. FaceSpan encourages this type of consistency throughout the application, but it by no means enforces it.

FaceSpan's Window Editor creates three different types of windows. Document windows are used for main windows. They can be resizable, closeable, and zoomable. Their optional titles are distinct from their name, as used in scripts. Modal windows can be titled or untitled and, unlike Document windows, must be closed before any other windows can receive events. The last window type is floating Windoid. These are windows that float on top of all Document windows. They are usually used for tool palettes.

A window contains zero or more window items. The upper limit of window items is 330. There are 14 different types of window items, and these types are further customizable using Forms. For example, the Button window item can have either a standard or a 3-D visual representation.

The Window Editor consists of a pair of tool palettes. The window under construction is displayed almost exactly as it will appear. New window items can be dragged onto the window, or drawn on the window. Window items have several properties that control their behavior. For example the visible and enabled properties determine if a particular window item is visible, and usable. If its enable property is false, it displays in a grayed-out style.

Figure 2. The FaceSpan Window Editor.

Figure 2 shows a complex preferences Modal window in FaceSpan's window editor. This window uses several window items, including labels, textboxes, boxes, checkboxes, and buttons (called push buttons by FaceSpan.)

In addition to the window editor, an application has full control over the menu bar. Basic menu capabilities are supported, as well as limited (single level) hierarchical menus. The menu bar support is the weakest portion of FaceSpan. Applications can have only a single menu item in the Apple menu and have no access to the Help menu.

Animating the Interface

There are three basic forms of interface behavior: workflow control, feedback, and application specific behavior. The next step in prototyping is to implement the first two forms. By workflow control I mean the degree to which the application controls what the user can do at any given point in time. This includes simple things like push button and menu sensitivity, as well as window interactions. It also includes managing dependant window items. Feedback is the use of visual and auditory messages in the application. For example, feedback is displaying a confirmation dialog box when the user closes a window, or playing a beep when invalid data is entered into a text box.

The first step is to get the ball rolling at application startup. Let's assume I have a prototype that needs to open three windows when it is launched. I make a project in the FaceSpan environment, draw three windows in the Window Editor, and then save the project as an executable. When the user double clicks the appliction icon in the Finder, it launches just fine, but no windows are displayed. I need to add some AppleScript to the project to link the launching event to several actions. When the user launches a FaceSpan application a run event message is sent to the project script. If the user drops a file on the application icon, an open event message and a list of file references is sent to the project script instead. I want to open three windows when the user launches the application, so I add an on run handler in the project script:

on run
  -- get prefs
  set {p1, p2, p3} to storage item "positions"
  open window "Call Manager" 
    with properties {bounds:p1}
  open window "Status" -
    with properties {position:p2, zoomed:false}
  open window "Call Manager - driver" 
    with properties {position:p3, zoomed:false}
end run

Most Macintosh applications keep track of window positions for the user. I can do that for my prototype as well. This handler uses a storage item to keep track of user placement of the windows. Storage items are named containers where an application can store and recall any type of data. The actual data is kept in the resource fork of the application. Recall that this is the executable version of the project file.

When the user double clicks the application icon, the on run handler of the project script is called. I begin by recalling three positions (positions are a FaceSpan datatype that specifies the x, y, width, and height of a window) from storage. I use each position to place and size each window exactly where the user left them when they last quit the prototype. I open each window use the open window command. A Window is controlled by the settings of its properties, and I can set the values of window properties in the open window command using the with properties modifier. I use this to set the initial position of each window to the stored value. I need to create the initial values for the three positions and save them in the "positions" storage item within the FaceSpan environment. I also need to somehow capture the current location and size of each window and update the storage item when the user quits the prototype.

Once a window is open the user can interact with it. They can click buttons, enter text into textboxes, check checkboxes and radio buttons, and so on. If there are no scripts attached to a window then these actions don't do anything specific to the prototype. The window behaves like a fill-in-the-blanks form. All the window items and the window itself will work, but unless the prototype does something with the information or actions the user takes, not much else will. FaceSpan does a lot of the hard work: the user can enter text into text fields, select radio buttons or checkmarks, tab between fields, scroll scrollable textboxes, and what not. What is missing is the application-specific actions that link the whole interface together.

For example, the modal dialog window in Figure 2 has a checkbox (displayed as a pull-down flag) labeled "Advanced Options." When the user toggles this checkbox "on" the window should expand to show the window items below it, and the OK push button should move down to the bottom. Clicking it again should collapse the window back to its original size and move the OK push button back to the original location. When I draw the dialog window in the FaceSpan Window Editor I set the OK push button growth property to move both. That tells FaceSpan to move it in both directions whenever the window size changes. In effect it becomes attached to the lower right corner of the window. What I want to do is resize the window between two fixed sizes, based on the setting of the "Advanced Options" checkbox. I add a handler to the script attached to the checkbox that resizes the window when the user changes the checkbox's value. That handler is very simple:

on hilited theObj
  if hilite then
    set height of my window to 555
    set height of my window to 345
  end if
end hilited

When the user clicks to push a button, checkbox, or radio button window item the hilited event is sent to its attached script. The hilite property of the checkbox is true if it is checked and false otherwise. This little script changes the window size to one of two sizes, based on the hilite property value, each time the checkbox is clicked.

Figure 3.

I create lot of the animation of a prototype interface using similar techniques. Handlers for push button clicks (on hilited) or listbox selections (on selection made) usually enable or disable other window items, open or close other windows, or enable or disable menu items.

When the interface is fully animated the prototype is sufficient to answer a lot of questions about the final product. Does the interface work well? Is it easy to figure out how to accomplish a given task? Is feedback clear and consistent? The final step for a prototype is to add some or most of the application specific behavior. This is both a valuable and a dangerous step. Valuable because of what it can reveal about a potential design, and dangerous because if the prototype becomes "too functional" there is a real danger to ship it. By using FaceSpan and AppleScript, you are relieved of that danger, while still retaining the benefit of trying out a design before committing many hours to a C++ implementation. In other words, you're pretty much assured of having to throw away the prototype!

Adding Application-Specific Behavior

Adding application behavior is pretty much an exercise in AppleScript programming. The FaceSpan message hierarchy provides a lot of flexibility in the placement of handlers for FaceSpan event messages as well as application specific handlers. My job is to convert the various FaceSpan event messages into application-specific messages. FaceSpan event messages signal interface events (hilited, selection made, and so forth) while application-specific messages signal much higher-level events (produce a report, export to file, open database, and so on.) I then write handlers for those application-specific messages in AppleScript. This approach lets me reuse more of the design from the prototype because I'm able to separate the application-specific portions of each handler from the interface-specific portions. If I go on to implement the final application in C++ or Java, the interface code will be quite different than FaceSpan. The actual application specific behavior will also be coded differently, but the AppleScript code I write in the prototype can act as pseudocode.

A simple example is a push button in a window. When the user clicks the push button FaceSpan sends a hilited event message to its attached script, and then on to the window the button is in, and finally to the project script. The message flows along the message hierarchy until it is handled by a script, so I can place the on hilited handler wherever it makes the most sense. My rule is to place the handler in the script attached to the window or window item closest to the item generating the event message, unless a very similar action is performed regardless of which window item is generating it. For push buttons, I generally put the on hilited handler in the script attached to the push button. This handler converts the FaceSpan event message (hilited) into an application-specific function call. Function calls in AppleScript send a user-defined command message corresponding to the function name into the message hierarchy. Here's an example script that converts a FaceSpan event message to an application-specific user-defined command:

on hilited theObj set address to contents of textbox "digits" - as string sendCall(address) set contents of textbox "digits" to "" end hilited

The handler is from a prototype Call Management application. In this prototype the main window consists of a graphical representation of a call, a textbox named "digits", and a push button labeled "Send". When the user clicks Send, I want to extract the current phone number from the textbox and place a telephone call to that number. I then want to clear the textbox. There are two different things happening here. Getting the phone number and clearing the textbox are both interface-specific actions, so I take care of them in this handler. The second action is placing a call to the entered number. That has nothing to do with the interface, and I'd like to separate the code out so I can at least have the option of reusing the design. I do this by calling a user-defined function. This in effect converts the FaceSpan hilited event message into an application-specific event message named sendCall(). Now all I have to do is implement the AppleScript handler for sendCall(). This handler is totally separate from the FaceSpan interface, and can be placed in a script anywhere along the message hierarchy (window item, window, and project). Where this is placed depends on several factors, including the ultimate target implementation language. For this prototype, I placed the handler in the project script:

on sendCall(phoneNum)
  if isConnected then
    tell window "Status"
      setMsg("Dial " & phoneNum)
    end tell
    tcp write data "Dial " & phoneNum & LF -
      stream tcpDialogSocket
  end if
end sendCall

In the handler I send a protocol message through a TCP/IP socket to a host application. I also enable what amounts to a thread in another window (again using an application-specific message named enableWaiting()) that uses the FaceSpan idle handler to poll a TCP/IP socket for a reply. I'm taking advantage of the excellent shareware TCP/IP Scripting Addition by Mango Tree Software to perform the TCP/IP operations.

Don't get too hung up on the actual code, what's more important is to understand what it shows. When I implement the actual application it's pretty clear that the code must write a string to a TCP/IP socket to make a call, and once it's done this it must wait for a response. This design applies just as well to the final application as it does to this prototype.

Object Oriented Programming

I generally take an object-oriented approach to application design. FaceSpan and AppleScript fully support object-oriented implementations. For those not interested in or concerned with objects, a purely functional approach can also be used. If objects are important to the prototype, then there are several options available when using the FaceSpan/AppleScript combination. FaceSpan's windows and window items are themselves objects, while AppleScript includes its own script objects.

Objects in FaceSpan

In FaceSpan, every window is considered a window template. This means that FaceSpan considers every window, including all its window items and attached scripts, to be a class of sorts. An application can either use the template directly, or it can create several instances of the template. Each instance contains a complete copy of the window, including window properties and attached script properties. Each window instance is assigned a unique window id property. The open window command opens a window based on the template created in the Window Editor.

Window items also are objects. They contain properties as well as data, and can be created and destroyed dynamically. When a window is created in the Window Editor, the initial set of window items is specified and their property values are set. The application has complete control over these values, and can even override them when the window template is opened. The following code fragment dynamically creates several window items in a window.

on displayCall(calledNumber, calledNumberId, -
    isActive, isRadio, isInConf, -
    isConf, lineFrom, nodeX, nodeY)
  local xPos, ypos, iconArt, lineProps
  set ypos to (nodeY * 60) - top
  set xPos to nodeX * 80
  if isRadio then
    set radioItem to id of (make radio button -
      with properties {position:{4, ypos},width:16,-
      height:16, script:none, hilite:isActive, -
      cnum:calledNumber, cid:calledNumberId} -
      at end of window id theWindow)
    set index of window item id radioItem to 2
  end if
  set theIndex to -
    (index of graphic line "divLine") + 1
  if isConf then
    set iconArt to {class:resource info, -
      type:"cicn", name:"group", id:5001}
    set iconArt to {class:resource info, -
      type:"ICON", name:"Big Off Tone", id:5002}
  end if
  set iconItem to id of (make icon with properties-
    {artwork:iconArt, position:{4 + xPos, -
    ypos - 10}, width:36, height:36, -
    draggable:true, droppable:true, script:none,-
    selection rule:as push button, -
    balloon:"ISP Id is: " & calledNumberId, -
    cnum:calledNumber, cid:calledNumberId, -
    conf:isInConf} at end of window id theWindow)
  set index of window item id iconItem to theIndex
  if (lineFrom = -1) then 
    set lineProps to {position:{18, ypos + 8}, -
      width:80, height:1, script:none}
  else if (lineFrom = 0) then 
    set lineProps to {position:{(80 * (nodeX - 1)) -
      + 22, ypos - 60}, width:1, height:68, -
    set lineProps to {position:{(80 * lineFrom) + -
      14, ypos + 8}, width:80 * (nodeX - lineFrom),-
      height:1, script:none}
  end if
  set lineItem to id of (make graphic line -
    with properties lineProps -
    at end of window id theWindow)
  set index of window item id lineItem to theIndex
  if (lineFrom = 0) then
    set lineItem to id of (make graphic line -
      with properties {position:{(80 * (nodeX - 1))-
      + 22, ypos + 8}, width:72, height:1,-
      script:none} at end of window id theWindow)
    set index of window item id lineItem to theIndex
  end if
  set labelItem to id of (make label -
    with properties {position:{xPos + 10, ypos + -
    24}, width:80, height:16,contents:calledNumber,-
    script:none} at end of window id theWindow)
  set index of window item id labelItem to theIndex
end displayCall

This is a meaty handler that creates several window items. It shows several interesting things. First, the algorithm used to place the radio button, icon, label, and lines is reusable. I used virtually the same algorithm in a Java and a NewtonScript version of the final application. Second, the application has total control over the placement and property values for window items it creates. Third, I'm adding application-specific properties to the radio button and icon window items. I use these window items to hold information I need (caller number and conference information) to associate with the call, but don't want to store separately. Finally, notice that each window item has its script property set to none. This is one case where I take advantage of the FaceSpan message hierarchy for performance reasons. Whenever one of these window items generates an event message I can handle it in the window's attached script with a general handler. Here's the hilited event handler:

on hilited theObj
    if class of theObj is radio button then
      set theCallId to cid of theObj
    end if
  on error
  end try
end hilited

I dynamically create radio buttons, icons, graphic lines, and labels as children of the window. Of these, only radio buttons and icons generate the hilited event message. In this prototype I don't want to perform any actions if the user clicks one of the dynamic icons, and there are no other radio buttons in the window except those I create dynamically. When I add the on hilited hander to the script attached to the window, it is called whenever the user clicks something (radio button, checkbox, push button, or icon) in the window, but only if that window item does not include its own on hilited hander in its attached script. In this case I need to verify only that the class of the sender of the message is radio button. If it is, then it must be one of my dynamically created ones.

I use the class of operator to determine if the object generating the message is a radio button. If it is, then I convert the FaceSpan event message into an application specific message named switchCall(). I retrieve the application specific property cid from the radio button, since that's the id that the server process knows about. This is an example of treating window items like objects, since each item contains its own unique data.

Objects in AppleScript

AppleScript also has its own little-used object/class system. Each script in AppleScript is considered a Script object that contains methods (called handlers) and data (called properties.) The script/end script command defines a script object within a script. The basic form is:

script className
  property parent: otherClassName

  property p1: value1

  on handlerName(params)
end script

A script object can have zero or one parent script property, zero or more other properties, and zero or more handlers. This is more like Java than C++ since there is only single inheritance. There is also no private or protected data or methods. Everything is public. For prototyping, this is not a major hardship. Script objects are a little different than classes in most object-oriented languages in that the script/end script commands actually make a single instance. In the above example the commands make a single instance of the class named className. To make several instances of the class I'd have use the copy command to copy className. Instead of doing this, I can place the script/end script commands in a handler. Then the handler acts like a constructor. Every time I call the constructor a new instance of the class is created. Parameters to the hander can be used in the property statements of the script to provide initial values to newly created objects. This is an example of a simple constructor handler:

on makeMyObj(name)
  script myObj
    property myName: name
    on getName()
      return myName
    end getName
  end script

  return myObj

Calling makeMyObj("Fred") returns an instance of the myObj script object with its myName property initialized to "Fred".

Combining script objects with FaceSpan allows for encapsulating all of the handlers and data associated with a group of dynamic window items into one object. I use this technique to bind all the methods and data for a meeting in a meeting object in an example in by book, AppleScript Applications: Building Applications in FaceSpan and AppleScript, in the DateMinder application. This application implements a PIM that includes a Day view. The Day view is a window that displays a cluster of three window items for each meeting in a day. Here is a portion of the constructor and script object for a meeting:

on makeDayItem(itemclass, itemDetails, itemNote)
  local pos, startAt, meetingLength
  if itemclass = "Meeting" then
    set {pos, startAt, meetingLength} to itemDetails
    updateCalendarMeetMarks(startAt, true)
    set startAt to 0
    set meetingLength to 0
    set pos to itemDetails
    updateCalendarOtherMarks(itemclass, true)
  end if
  script DayObject
    property theIndex : 0
    property barIndex : 0
    property iconIndex : 0
    property textIndex : 0
    property myPos : pos
    property myTime : startAt * 15 * minutes
    property myLength : meetingLength
    property myClass : itemclass
    property myNotes : itemNote

    on getItemInfo()
      if itemclass = "Meeting" then
        return {itemclass:myClass, xPos:myPos,-
          starttime:myTime, duration:myLength, -
        return {itemclass:myClass, xPos:myPos, -
      end if
    end getItemInfo
    on resizeMeeting(theObj)
    end resizeMeeting

    on createImage()
    end createImage

    on updateMeeting(newTime, newDuration, newText)
    end updateMeeting

    on move (theInfo)
    end move

    on redraw()
    end redraw

    on openWindow()
    end openWindow

    on closeWindow()
    end closeWindow

    on windowName()
    end windowName

    on updateWindow()
    end updateWindow

    on adoptDetailWindow(oldWindowName)
    end adoptDetailWindow

    on updateItemText(newNote)
    end updateItemText

    on updateItemTextAndDisplay(newNote)
    end updateItemTextAndDisplay

    on remove()
    end remove
  end script
  return DayObject
end makeDayItem

I call the makeDayItem() handler to create a day item object. Once it is created I draw it's graphical representation in the Day window by calling the createImage() handler. An example of this is in the handler called when the user drags an icon onto the window to create a new meeting:

on newDayItem(theClass, theInfo)
  local theDayItem
  set theDayItem to -
    makeDayItem(theClass, theInfo, "")
  set end of theDayItems to theDayItem
  tell theDayItem to createImage()
end newDayItem

In this handler I create a new day item object by calling the day item constructor handler, and save the object in a list of all day items stored in a property. I then call the createImage() handler in the object to draw the object in the window. Any script needing to access data associated with the object, or to change its contents or location, need call only handlers in the object. I don't have to know how it is implemented, what window items are associated with it, or how to modify their properties. As I said, it's a powerful combination.

Moving From Prototype to Product

Once the prototype is completed and ready to retire, I don't just ignore it. Rather it can be mined for valuable information. The interface will have to be reimplemented in the target language (using PowerPlant, or the Constructor for Java, or by hand coding, depending on the implementation language). The prototype serves two roles here: it acts as a guide when laying out the interface and as a specification for naming the elements of the interface.

The same holds true for the AppleScript scripts. They act as a high-level specification language for the final code. Algorithms implemented in AppleScript are highly reusable, as are data structures and class hierarchies. I'm not suggesting that it's just a matter of "porting over" to C++ or Java, but at least I've already got a working solution to use when I'm doing the final implementation.

One Example of a Prototype That Worked

This is not just some abstract article - I've used these techniques many times when creating prototypes for GTE Laboratories. Here at the labs fast turn around times are critical when we're mocking up applications. By using this method and these tools, I've created many successful demos using AppleScript and FaceSpan. When we recreate a particular application in a production system, we first capture the design by dissecting the prototype.

One such example is a Call Management client application for an Internet telephony project. This application drives a server front end to allow the user to create and manage many telephone calls. Calls can be placed, merged into conferences, and dropped. Furthermore the user can have many calls active at the same time. The ultimate implementation target for the client application was Java, but much of the protocol used to communicate between the client and server was undefined and we needed a usable prototype in just two weeks. Using the method outlined in this article, and the TCP/IP osax from Mango Tree Software, I was able to create a professional prototype with a direct manipulation interface. This prototype carried us through the demo, and then was used for the final Java application over the next two months. The running application is shown below.

Figure 4.

As you can see, the application looks and behaves like any other Macintosh application. The icons on the scrolling display support drag & drop -- just drag a phone icon on top of another to merge the calls into a conference, or drag a phone icon out of a conference and onto the main window to split that call out of the conference.

Building this prototype in FaceSpan and AppleScript let me focus on the important details including creating a layout algorithm for the call graph, finalizing and debugging the TCP/IP protocol between client and server, and creating an enjoyable and usable interface for call manipulation. I didn't need (or have time) to struggle with the details of coding the application in C++ or Java. Even so, I was still able leverage the time spent on the prototype when building the final version in Java. I also re-implemented it in a custom NewtonScript application. Even there the time spent on the prototype reaped large rewards when designing the GUI in the Newton Toolkit and implementing the application in NewtonScript.

Prototyping Can Work For You

There are at least three good reasons to create a prototype before building an application. A prototype can help answer tough questions about an interface: how usable is it, does it work better one way or another, what is the optimal placement of controls in a window. A prototype is usually ready to use in short order and can fill in for the final application while it is being written. A prototype also lets you play "what if" games with different algorithms and data structures. As long as you're willing to throw it away, it's almost always worth the investment in time.

FaceSpan and AppleScript provide a powerful and rich environment for rapid prototyping. FaceSpan interfaces can be designed such that they are full Macintosh interfaces. The tool provides a fast way to mock up interfaces, and those interfaces can be quickly modified as the prototype evolves. In a similar manner AppleScript is a wonderful prototyping language. The syntax is like psuedocode, so the resulting scripts act as documentation when moving to C++ or Java. It supports object-oriented programming, as well as a huge library of osax building blocks and access to scriptable applications. These tools and this method are valuable additions to any programmer's toolbox.


John Schettino is an author and Senior Member of the Technical Staff at GTE Laboratories, Inc. He is the co-author of the books BASIC for the Newton: Programming for the Newton with NS BASIC and AppleScript Applications: Building Applications with FaceSpan and AppleScript, both published by AP Professional. He is also a contributing editor for the Handheld Systems Journal and for the web eZine Mobilis, where he writes about Newton and WindowsCE. You can reach him via


Community Search:
MacTech Search:

Software Updates via MacUpdate

Yummy FTP Pro 1.11.14 - $14.99 (50% off)
Yummy FTP Pro is an advanced Mac file transfer app which provides a full-featured professional toolkit combined with blazing speeds and impeccable reliability, so whether you want to transfer a few... Read more
ExpanDrive 5.4.4 - Access cloud storage...
ExpanDrive builds cloud storage in every application, acts just like a USB drive plugged into your Mac. With ExpanDrive, you can securely access any remote file server directly from the Finder or... Read more
Dash 3.4.3 - Instant search and offline...
Dash is an API documentation browser and code snippet manager. Dash helps you store snippets of code, as well as instantly search and browse documentation for almost any API you might use (for a full... Read more
Civilization VI 1.0.2 - Next iteration o...
Sid Meier’s Civilization VI is the next entry in the popular Civilization franchise. Originally created by legendary game designer Sid Meier, Civilization is a strategy game in which you attempt to... Read more
TurboTax 2016 - Manage your 2016 U.S. ta...
TurboTax guides you through your tax return step by step, does all the calculations, and checks your return for errors and overlooked deductions. It lets you file your return electronically to get... Read more
Microsoft Office 2016 15.30 - Popular pr...
Microsoft Office 2016 - Unmistakably Office, designed for Mac. The new versions of Word, Excel, PowerPoint, Outlook and OneNote provide the best of both worlds for Mac users - the familiar Office... Read more
FotoMagico 5.3 - Powerful slideshow crea...
FotoMagico lets you create professional slideshows from your photos and music with just a few, simple mouse clicks. It sports a very clean and intuitive yet powerful user interface. High image... Read more
Acorn 5.6.1 - Bitmap image editor.
Acorn is a new image editor built with one goal in mind - simplicity. Fast, easy, and fluid, Acorn provides the options you'll need without any overhead. Acorn feels right, and won't drain your bank... Read more
iMazing 2.1.8 - Complete iOS device mana...
iMazing (was DiskAid) is the ultimate iOS device manager with capabilities far beyond what iTunes offers. With iMazing and your iOS device (iPhone, iPad, or iPod), you can: Copy music to and from... Read more
Logic Pro X 10.3 - Music creation and au...
Logic Pro X is the most advanced version of Logic ever. Sophisticated new tools for professional songwriting, editing, and mixing are built around a modern interface that's designed to get creative... Read more

Red's Kingdom (Games)
Red's Kingdom 1.0 Device: iOS Universal Category: Games Price: $4.99, Version: 1.0 (iTunes) Description: Mad King Mac has kidnapped your father and stolen your golden nut! Solve puzzles and battle goons as you explore and battle your... | Read more »
Turbo League Guide: How to tame the cont...
| Read more »
Fire Emblem: Heroes coming to Google Pla...
Nintendo gave us our first look at Fire Emblem: Heroes, the upcoming mobile Fire Emblem game the company hinted at last year. Revealed at the Fire Emblem Direct event held today, the game will condense the series' tactical RPG combat into bite-... | Read more »
ReSlice (Music)
ReSlice 1.0 Device: iOS Universal Category: Music Price: $9.99, Version: 1.0 (iTunes) Description: Audio Slice Machine Slice your audio samples with ReSlice and create flexible musical atoms which can be triggered by MIDI notes or... | Read more »
Stickman Surfer rides in with the tide t...
Stickson is back and this time he's taken up yet another extreme sport - surfing. Stickman Surfer is out this Thursday on both iOS and Android, so if you've been following the other Stickman adventures, you might be interested in picking this one... | Read more »
Z-Exemplar (Games)
Z-Exemplar 1.4 Device: iOS Universal Category: Games Price: $3.99, Version: 1.4 (iTunes) Description: | Read more »
5 dastardly difficult roguelikes like th...
Edmund McMillen's popular roguelike creation The Binding of Isaac: Rebirth has finally crawled onto mobile devices. It's a grotesque dual-stick shooter that tosses you into an endless, procedurally generated basement as you, the pitiable Isaac,... | Read more »
Last week on PocketGamer
Welcome to a weekly feature looking back on the past seven days of coverage on our sister website, PocketGamer. It’s taken a while for 2017 to really get going, at least when it comes to the world of portable gaming. Thank goodness, then, for... | Read more »
ROME: Total War - Barbarian Invasion set...
To the delight of mobile strategy fans, Feral Interactive released ROME: Total War just a few months ago. Now the game's expansion, Barbarian Invasion is marching onto iPads as a standalone release. [Read more] | Read more »
Yuri (Games)
Yuri 1.0 Device: iOS iPhone Category: Games Price: $3.99, Version: 1.0 (iTunes) Description: It's night. Yuri opens his eyes. He wakes up in a strange forest.The small, courageous explorer rides on his bed on casters in this... | Read more »

Price Scanner via

13-inch 2.7GHz Retina MacBook Pro on sale for...
B&H Photo has the 2015 13″ 2.7GHz/128GB Retina Apple MacBook Pro on sale for $100 off MSRP. Shipping is free, and B&H charges NY tax only: - 13″ 2.7GHz/128GB Retina MacBook Pro (MF839LL/A): $... Read more
Laptop Market – Flight To Quality? – The ‘Boo...
Preliminary quarterly PC shipments data released by Gartner Inc. last week reveal an interesting disparity between sales performance of major name PC vendors as opposed to that of less well-known... Read more
IBM and Bell Transform Canadian Enterprise Mo...
IBM and Bell Canada have announced they are joining forces to offer IBM MobileFirst for iOS market-ready enterprise applications for iPad, iPhone or Apple Watch. Bell, Canada’s largest communications... Read more
Otter Products is Closing… For a Day of Givin...
On Thursday, Feb. 9, Otter Products is closing doors to open hearts. In partnership with the OtterCares Foundation, the company is pausing operations for a day so all employees can volunteer with... Read more
15-inch 2.2GHz Retina MacBook Pro on sale for...
Amazon has 2015 15″ 2.2GHz Retina MacBook Pros (MJLQ2LL/A) available for $1799.99 including free shipping. Apple charges $1999 for this model, so Amazon’s price is represents a $200 savings. Read more
Back in stock: Apple refurbished 13-inch Reti...
Apple has Certified Refurbished 2015 13″ Retina MacBook Pros available for up to $360 off original MSRP, starting at $1099. An Apple one-year warranty is included with each model, and shipping is... Read more
CalcTape for macOS 1.2 Adding Machine App for...
schoettler Software has announced CalcTape 1.2, an update to their desktop calculator for macOS. When it comes to adding long columns of numbers, doing complex calculations or playing around with... Read more
New MacBooks And MacBook Pros WIth Kaby Lake...
Digitimes’ Joseph Tsai cites a Chinese-language Economic Daily News (EDN) report that unnamed market watchers are predicting Apple MacBook shipments to grow 10 percent in 2017, and projecting 15... Read more
New 2016 13-inch MacBook Pros on sale for up...
B&H Photo has the new 2016 13″ MacBook Pros in stock today and on sale for up to $150 off MSRP. Shipping is free, and B&H charges NY sales tax only: - 13″ 2.9GHz/512GB Touch Bar MacBook Pro... Read more
New 15-inch Touch Bar MacBook Pros in stock a...
B&H Photo has the new 2016 15″ Apple Touch Bar MacBook Pros in stock today and on sale for up to $150 off MSRP. Shipping is free, and B&H charges NY sales tax only: - 15″ 2.7GHz Touch Bar... Read more

Jobs Board

*Apple* & PC Desktop Support Technician...
Apple & PC Desktop Support Technician job in Los Angeles, CA Introduction: We have immediate job openings for several Desktop Support Technicians with one of our Read more
*Apple* Retail - Multiple Positions - Apple,...
SalesSpecialist - Retail Customer Service and SalesTransform Apple Store visitors into loyal Apple customers. When customers enter the store, you're also the Read more
*Apple* Retail - Multiple Positions (Multi-L...
Job Description: Sales Specialist - Retail Customer Service and Sales Transform Apple Store visitors into loyal Apple customers. When customers enter the store, Read more
*Apple* Retail - Multiple Positions - Apple,...
Job Description: Sales Specialist - Retail Customer Service and Sales Transform Apple Store visitors into loyal Apple customers. When customers enter the store, Read more
*Apple* & PC Desktop Support Technician...
Apple & PC Desktop Support Technician job in Stamford, CT We have immediate job openings for several Desktop Support Technicians with one of our most well-known Read more
All contents are Copyright 1984-2011 by Xplain Corporation. All rights reserved. Theme designed by Icreon.