Graphics Techniques Part 1

One of the most exciting features of your HP 9000 Series computer is its graphics capability. The graphic techniques chapters introduce you to the powerful set of graphics statements in BASIC and teach you how to use them to produce pleasing output.

If you use HP BASIC/WS and you want to know what binary to load for a particular keyword or option, see the HP BASIC Language Reference. Note that you must load the BIN files named GRAPH and GRAPHX before you can enter most graphics statements. You may need to load other BIN files, depending on what computer you have. Refer to the HP BASIC Porting and Globalization manual for information about BIN files. Finally, some of the example graphics programs require BIN files such as MAT that you might not readily associate with graphics.

If you have HP BASIC/WS, you should have a disk called Manual Examples. The part numbers for this disk vary depending on what disk drive you have, but the disk contents are identical. The Manual Examples disk contains many of the programs discussed in the graphics chapters, which you can load and run as you read through the chapters.

If you have HP BASIC/UX, the graphics examples are located in the ``/usr/lib/rmb/demo/manex'' directory.

The file name for an example program is cited when the program is discussed so that you know which program to run. These file names are identical for HP BASIC/WS and HP BASIC/UX.

Why Graphics?

Some data follow. As quickly as you can, determine if the overall trend is steady, rising or falling. Are there any periodic motions? If so, how many cycles are represented in the 50 points?
Set of Voltage Data
Time (sec.) Voltage Time (sec.) Voltage
1 16.10 26 16.24
2 16.25 27 16.27
3 16.25 28 16.44
4 16.28 29 16.44
5 16.36 30 16.57
6 16.31 31 16.60
7 16.27 32 16.70
8 16.08 33 16.72
9 16.10 34 16.66
10 16.06 35 16.58
11 16.07 36 16.62
12 16.17 37 16.46
13 16.14 38 16.33
14 16.26 39 16.34
15 16.34 40 16.36
16 16.40 41 16.45
17 16.56 42 16.52
18 16.60 43 16.56
19 16.44 44 16.77
20 16.51 45 16.89
21 16.35 46 16.80
22 16.41 47 16.96
23 16.28 48 16.80
24 16.19 49 16.74
25 16.30 50 16.77

Following is a graph of the data in the preceding table. Observe that the graphical nature of the data makes the change in voltage over time clearer. Clarity and understandability at a glance is what computer graphics is all about.

Many example programs are included in the pages that follow. Type in and run them as you progress from simply drawing a jagged line to creating complex graphics.

Graph of Voltage Data


Drawing Lines

To draw lines, you can simply PLOT the X and Y coordinates of the point you want to draw a line to. The following program does just that.

 
10    GINIT                      ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL"  ! Use the CRT screen
30    GRAPHICS ON                ! Turn on the graphics screen
40    FOR X=2 TO 100 STEP 2      ! Points to be plotted...
50      PLOT X,RND+50            ! Get a data point and plot it against X
60    NEXT X                     ! RND returns a value between 0 and 1
70    END                        !
 

Example of Plotting Random Data

The GINIT statement on line 10 means Graphics Initialize. This is almost always the first graphics statement you execute. It sets various graphics parameters to their default values, and it is a shorthand way to execute up to 14 other statements (see the HP BASIC Language Reference manual for details).

The GRAPHICS ON statement on line 30 allows you to see what the program is drawing if you have separate alpha and graphics. On bit-mapped displays, graphics and alpha are always on, unless you have modified the display mask. More on this later.

Line 50 contains the heart of the program. In a loop, the PLOT statement draws to each successive point, which is determined by the loop control variable ``X'' for the X direction and the value returned by the function ``RND+50'' for the Y direction. The constant, 50, centers the line on the screen so it is not displayed in your softkey display area.

Scaling

The problem with the previous plot is that it doesn't show much information; it's too straight. If we exaggerated the Y direction to the point where we could see the variations, the line would better represent the plotted data.

This problem can be remedied by scaling. Scaling means defining the values the computer considers to be at the edges of the plotting surface. By definition, the left edge is the minimum X, the right edge is the maximum X, the bottom is the minimum Y, and the top is the maximum Y. Thus any point you plot which has X and Y coordinates within these ranges will be visible.

Two statements are available to define your own values for the edges of the plotting surface. The first one is SHOW, which forces X and Y units to be equal. This is called isotropic scaling, and it is often desirable. For example, when drawing a map, you will probably want one mile in the east-west direction to be the same size as a mile in the north-south direction. Here is an example of SHOW:

 SHOW 0,100,16,18 

This statement defines the plotting area such that there is a rectangle in that area with a minimum X=0, maximum X=100, minimum Y=16, and maximum Y=18, using isotropic units. As mentioned above, isotropic means that one unit in the X direction equals one unit in the Y direction. Thus, if the plotting area were square, the above SHOW statement would define the minimum X to be 0, maximum X to be 100, minimum Y to be -33 (not 16) and maximum Y to be 67 (not 18). This is because the X and Y units must be identical, so the SHOW statement centers the specified area in the plotting area, allowing whatever extra room it needs to ensure that the rectangle is completely contained in the plotting area. There will be extra room in either the X or Y direction, but not both.

Since you defined the unit sizes with the SHOW statement, you were working with user-defined units (UDUs). Both the SHOW statement and the WINDOW statement (covered next) specify user-defined units.

The MAX and MIN functions provide a method for determining the maximum and minimum values of a set of numbers. However, these functions require the MAT binary. For example:

 
110   Ymin=INT(MIN(Y(*)))
120   Ymax=MAX(Y(*))
130   Ymax=INT(Ymax)+(Ymax<>INT(Ymax))
 

Line 110 calculates the greatest integer less than or equal to the minimum value in an array of Y values. Lines 120 and 130 calculate the smallest integer greater than or equal to the maximum value in the array of Y values.

The following example uses a SHOW statement to define the edges of the screen to appropriate values. The X values used in the SHOW statement (0 and 100) represent 100 data points and indicate that axes are more meaningful when the origin is at zero and not at 1. The Y values for this type of plot must be determined by you or by the computer itself. We are using a random number function to simulate data received from some device. The Y values used in the example (16 and 18) come from the RND function. In real applications, you probably will not know beforehand what the range of the data will be, in which case you can use the method described above to determine it.

 
10    GINIT                      ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL"  ! Use the internal screen
30    GRAPHICS ON                ! Turn on the graphics screen
40    SHOW 0,100,15,19           ! Isotropic scaling: left, right, bottom, top
50    FOR X=2 TO 100 STEP 2      ! Points to be plotted...
60      PLOT X,RND+17            ! Get a data point and plot it against X
70    NEXT X                     ! RND returns a value between 0 and 1
80    END                        !
 

$ag.gif$

Better Use of X-Axis Scaling

As you can see, SHOW centers the curve on the screen, but since the range of X values is so much larger than the range of Y values (0 to 100 versus 16 to 18), there is still not enough resolution to see what the data is doing.

In this example, we are dealing with data types (seconds and volts) that are not equal. Thus, it would be better to use unequal, or anisotropic, scaling to graph the relationship in the example. To do this, we can use the other scaling statement, WINDOW. WINDOW does not force X units to be equal to Y units. Instead, the axis range determines the scaling.

 
10    GINIT                     ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL" ! Use the internal screen
30    GRAPHICS ON               ! Turn on the graphics screen
40    WINDOW 0,100,15,19        ! Anisotropic scaling: left,right,bottom,top
50    FOR X=2 TO 100 STEP 2     ! Points to be plotted...
60      PLOT X,RND+17           ! Get a data point and plot it against X
70    NEXT X                    ! RND returns a value between 0 and 1
80    END                       !
 

Better Use of Y-Axis Scaling

In this plot, we can easily see variations in the data. To test how the Y axis range, 15-19, affects relative variations in the data, change ``WINDOW 0,100,15,19'' to ``WINDOW 0,100,30,50'' and change ``RND+17'' to ``RND+40''. Run the program again and note that the line is less ragged (remember that RND ranges between 0 and 1).

There is still one problem, though. We can see relative variations in the data, but what units are being used -- microvolts, millivolts, megavolts, dozens of volts, or what? We also need to be able to specify a subset of the screen for plotting the curve and put explanatory notes outside this area. The next section tells you how to do this.

Defining a Viewport

A viewport is a subset of the plotting area called the soft clip area. It is delimited by the soft clip limits. Clip, because line segments which attempt to go outside these limits are cut off at the edge of the subarea. Soft, because we can override these limits by turning off the clipping with the CLIP OFF statement (more about this later). There are hard clip limits also, which are defined to be the absolute limits of the plotting area. There is no way to override the hard clip limits.

GDUs and UDUs

Before we define a viewport, we need to know about the two different types of units that exist. These two types of units are UDUs (user-defined units) and GDUs (graphics display units). For viewports to be predictable, they must always be specified in the same units. Since users can change UDUs, GDUs are used when specifying the limits of a VIEWPORT statement. GDUs are fixed for the CRT, so a viewport is associated with the screen, rather than the graphical model used in your program.

The length of a GDU is defined as 1 percent of the shorter edge of the plotting area. The lower left of the plotting area is always 0,0. GDUs are isotropic; that is, one unit in the X direction is the same distance as one unit in the Y direction. For a CRT display, the Y-axis is always shorter, and thus it is 100 GDUs in length.

Unless you specify otherwise, the display screen (but not necessarily an external plotter) has the following expanse:

The RATIO statement returns the ratio of the X-axis hard clip limit to the Y-axis hard clip limit for the current PLOTTER IS device. For a typical CRT this ratio is in the approximate range 1.25 to 1.33. To find this ratio for your display, just type ``RATIO'' [Return]. You can include the RATIO expression in another BASIC statement, for example:

 
VIEWPORT 0,RATIO*100,20,80
 

This practice ensures that the clipping limits you specify will work for any display type. Some approximate RATIO values for typical displays follow:

Thus, the length of the X axis is in the range of approximately 125 to 133 GDUs for any of the listed displays.

Specifying the Viewport

VIEWPORT defines the extent of the soft clip limits in GDUs. It specifies a subarea of the plotting surface which acts just like the entire plotting surface except you can draw outside the subarea if you turn off clipping (more about clipping later). The VIEWPORT statement in the following program specifies that the lower left-hand corner of the soft clip area is at 10,15 and the upper right-hand corner is at 120,90. This is the area that the WINDOW statement affects. Also note line 50--the FRAME statement. This draws a box around the current soft clip limits so you can see the area specified by VIEWPORT.

 
10    GINIT                     ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL" ! Use the internal screen
30    GRAPHICS ON               ! Turn on the graphics screen
40    VIEWPORT 10,120,15,90     ! Define subset of screen area
50    FRAME                     ! Draw a box around defined subset
60    WINDOW 0,100,15,19        ! Anisotropic scaling: left,right,bottom,top
70    FOR X=2 TO 100 STEP 2     ! Points to be plotted...
80      PLOT X,RND+17           ! Get a data point and plot it against X
90    NEXT X                    ! RND returns a value between 0 and 1
100   END                       !
 

Using VIEWPORT to define Soft-Clip Limits

Labeling a Plot

By using VIEWPORT, we now have enough room to include labels on the plot. Typically, in a Y-vs.-X plot, a title for the whole plot is centered at the top, a Y-axis title is placed on the left edge, and an X-axis title is placed at the bottom.

LABEL lets you write text onto the graphics screen. You can position the label by using a MOVE or PLOT statement to get to the point at which you want the label to be placed. The lower left corner of the label is at the point to which you moved. In other words, move to the position on the screen at which the lower left corner of the text is placed. Note that the LORG statement will move you to the lower left corner of the label. (The relative origin for labels can be changed with the LORG statement.)

Notice in the following plot that the Y-axis label on the left edge of the screen is created by writing one letter at a time. We only need to move to the position of the first character in that label because each label statement automatically terminates with a carriage return/linefeed. This causes the pen to go one line down, ready for the next line of text. (There is a better way to plot vertical labels; we'll see it in the section titled "Data-Driven Plotting.")

 
10    GINIT                      ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL"  ! Use the internal screen
30    GRAPHICS ON                ! Turn on the graphics screen
40    MOVE 45,95                 ! Move to left of middle of top of screen
50    LABEL "VOLTAGE VARIANCE"   ! Write title of plot
60    MOVE 0,65                  ! Move to center of left edge of screen
70    Label$="Voltage"           ! Write Y-axis label
80    FOR I=1 TO 7               ! Seven letters in "Voltage"
90      LABEL Label$[I,I]        ! Label one character
100   NEXT I                     ! et cetera
110   MOVE 45,10                 ! X: center of screen; Y: above key labels
120   LABEL "Time (seconds)"     ! Write X-axis label
130   VIEWPORT 10,120,15,90      ! Define subset of screen area
140   FRAME                      ! Draw a box around defined subset
150   WINDOW 0,100,16,18         ! Anisotropic scaling: left/right/bottom/top
160   FOR X=2 TO 100 STEP 2      ! Points to be plotted...
170     PLOT X,RND+16.5          ! Get a data point and plot it against X
180   NEXT X                     ! et cetera
190   END                        ! finis
 

Labeled Plot

Now we know what we are measuring--voltage versus time--but we still do not know the units being used. We need an X-axis and a Y-axis labeled with numbers in appropriate places. The AXES statement will work here.

Axes and Tick Marks

The AXES statement draws X and Y axes and short lines perpendicular to the axes to indicate the unit spacing. These short lines are called tick marks. The axes may intersect at any desired point; it need not be the actual origin--0,0. The tick marks may be any distance apart, and you can select the major tick count for each axis. The major tick count is the total number of tick marks drawn for every large one. This makes it convenient to count by fives or tens or whatever you choose. Insert the ``AXES'' statement in your program and rerun it to see the difference.

 
10    GINIT                      ! Initialize various graphics parameters.
20    PLOTTER IS CRT,"INTERNAL"  ! Use the internal screen
30    GRAPHICS ON                ! Turn on the graphics screen
40    MOVE 45,95                 ! Move to left of middle of top of screen
50    LABEL "VOLTAGE VARIANCE"   ! Write title of plot
60    MOVE 0,65                  ! Move to center of left edge of screen
70    Label$="Voltage"           ! Write Y-axis label
80    FOR I=1 TO 7               ! Seven letters in "Voltage"
90      LABEL Label$[I,I]        ! Label one character
100   NEXT I                     ! et cetera
110   MOVE 45,10                 ! X: center of screen; Y: above key labels
120   LABEL "Time (seconds)"     ! Write X-axis label
130   VIEWPORT 10,120,15,90      ! Define subset of screen area
140   FRAME                      ! Draw a box around defined subset
150   WINDOW 0,100,16,18         ! Anisotropic scaling: left/right/bottom/top
160   AXES 1,.1,0,16,5,5,3       ! Draw X- and Y-axes with appropriate ticks
170   FOR X=2 TO 100 STEP 2      ! Points to be plotted...
180     PLOT X,RND+16.5          ! Get a data point and plot it against X
190   NEXT X                     ! et cetera
200   END                        ! finis
 

Plot with Axes and Tick Marks

Line 160 of the program contains the AXES statement and its parameters. The parameters are explained as follows:
``1,.1'' The X axis has 1 display unit between tick marks, and the Y axis has .1 display unit between tick marks, in current display units.
``0,16'' The Y axis crosses the X axis at X=0. The X axis crosses the Y axis at Y=16.
``5,5'' These counts are the number of "minor" (shorter) ticks between "major" (longer) tick marks on the axes. The value of 5 specifies that a major tick mark will appear every fifth tick mark.
``,3'' The value of 3 specifies that the major ticks are 3 GDUs long (the default is 2).

Using Graphics Effectively

The Manual Examples disk (``/usr/lib/rmb/demo/manex'' for HP BASIC/UX users) contains programs found in this chapter. As you read through the following sections, load the appropriate program and run it. Remember that some of the programs require the MAT (matrix) BIN file. You can also type in the listed programs and run them. Either way, experiment with them until you are familiar with the demonstrated concepts and techniques.

More on Defining a Viewport

Recall that the VIEWPORT statement defines a subset of the screen in which to plot. More precisely, the VIEWPORT statement defines a rectangular area into which the WINDOW coordinates will be mapped. VIEWPORT immediately rescales the plotting area; thus, it is a good programming practice to follow every VIEWPORT statement with a WINDOW statement. The VIEWPORT also invokes clipping at its edges. There will be more about clipping later in this chapter.

The Y direction edge values default to 0 through 100 in Y. The X direction left edge value is 0. The right edge value can vary depending on what computer you have (approximately 128-133). Technically, these are UDUs, although default UDUs are equivalent to the GDUs until you change the UDUs with a SHOW or a WINDOW. To recap the important characteristics of GDUs:

As mentioned earlier in the section titled "Scaling," it is trivial to determine how long the shorter edge of screen is in GDUs, but substantially more involved to calculate the length of the longer edge in GDUs. Since GDUs have X and Y units of the same length, the length in GDUs of the longer edges of the plotting surface is closely related to the aspect ratio of the plotting surface. The aspect ratio is the ratio of width to height of the plotting surface. A function called RATIO returns the quotient of these values.

Using RATIO, we can derive two formulas which are almost indispensable when writing a general VIEWPORT statement:

 
X_gdu_max=100*MAX(1,RATIO)
Y_gdu_max=100*MAX(1,1/RATIO)
 

These two statements define the maximum X and Y in GDUs. This will work no matter what plotting device you are using. Now that we have ``X_gdu_max'' and ``Y_gdu_max'' defined, we have complete control of the subset we want on the plotting surface. Suppose we want:

We would specify:

 VIEWPORT .1*X_gdu_max,.99*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max 

Now, let's return to the program which defined the viewport, and update the VIEWPORT statement. (Run the example program in file ``SinViewprt''.)

 
100   CLEAR SCREEN                 ! Clear the alpha display
110   GINIT                        ! Initialize various graphics parameters.
120   PLOTTER IS CRT,"INTERNAL"    ! Use the internal screen
130   GRAPHICS ON                  ! Turn on the graphics screen
140   X_gdu_max=100*MAX(1,RATIO)   ! How many GDUs wide the screen is
150   Y_gdu_max=100*MAX(1,1/RATIO) ! How many GDUs high the screen is
160   VIEWPORT .1*X_gdu_max,.99*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max          
                                    ! Define subset of screen area
170   FRAME                        ! Draw a box around defined subset
180   WINDOW 0,100,16,18           ! Anisotropic scaling: left/right/bottom/top
190   FOR X=2 TO 100 STEP 2        ! Points to be plotted...
200     PLOT X,RND+16.5            ! Get a data point and plot it against X
210   NEXT X                       ! RND returns a value between 0 and 1
220   END
 

General Purpose VIEWPORT

Special Considerations about Scaling

If you scale the plotting area with WINDOW or SHOW using "large" coordinates, and then execute a MOVE, PLOT or DRAW command followed by another WINDOW or SHOW using "small" coordinates, a math overflow error may occur. What do we mean by "large" or "small" coordinates? Coordinates greater than 107 are considered large in this case, while coordinates less than 60,000 are considered small.

The following example program produces an overflow error:

 
10   PLOTTER IS CRT, "INTERNAL"
20   A = 5.4 * 10^7           ! Choose a "large" coordinate value
30   WINDOW 0,10,0,A          ! Scale the plotting area
40   MOVE 0,A                 ! Move to edge of plotting area
50   WINDOW 0,10,0,10         ! Math overflow error occurs here
60   MOVE 5,5
70   END
 

To avoid this error, add line 45 as shown below:

 
10   PLOTTER IS CRT, "INTERNAL"
20   A = 5.4 * 10^7           ! Choose a "large" coordinate value
30   WINDOW 0,10,0,A          ! Scale the plotting area
40   MOVE 0,A                 ! Move to edge of plotting area
45   MOVE 0,0                 ! Avoids math overflow error
50   WINDOW 0,10,0,10
60   MOVE 5,5
70   END
 

Why Does This Math Overflow Error Occur?

The graphics system does most of its math with real numbers until it is time to deal with actual pixel locations on the screen. (The word "pixel" is a blend of the two words "picture element." It is the smallest addressable point on a plotting surface.) At this time, it converts the real values to integers. When working with large values (such as 107), overflows can occur.

In the example above, line 40 moves the graphics pen to the edge of a very large plotting area which is defined in REAL coordinates. When the plotting area is rescaled to much smaller (REAL) values in line 50, the location of the graphics pen does not change. In other words, the graphics pen retains its large REAL coordinate values.

When the second WINDOW command is executed in line 50, the graphics system attempts to convert the large REAL coordinate values of the graphics pen position to INTEGERs according to the newly scaled plotting area. Since the original plotting area is much greater than the newly scaled plotting area, these large REAL coordinate values cannot be mapped into INTEGER values (since INTEGERs are limited to the range 0 through 65,535), and a math overflow error occurs.

More on Labeling a Plot

Three statements complement the LABEL statement. The first is CSIZE, which means character size. CSIZE has two parameters: character cell height (in GDUs) and aspect ratio. The height measures the character cell size. A character cell contains a character and some blank space above, below, left of, and right of the character. The amount of blank space depends on which character is contained in the cell.

This small program shows how the CSIZE statement changes the size of characters. (Run the example program in file ``Csize''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   DIM Text$[50]                 ! Allow the long strings
120   GINIT                         ! Initialize various graphics parameters
130   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
140   GRAPHICS ON                   ! Turn on the graphics screen
150   FRAME                         ! Draw a box around the screen
160   WINDOW -1,1,10,1              ! Anisotropic units
170   LORG 4                        ! Bottom center of labels is ref. pt.
180   FOR I=1 TO 6                  ! Six labels total
190     READ Csize,Text$            ! Read the characters cell size and text
200     CSIZE Csize                 ! Use Csize
210     MOVE 0,SQR(I)*3+1           ! Move to appropriate place
220     LABEL Text$                 ! Write the text
230   NEXT I                        ! Looplooplooplooplooploop
240   DATA 30,T,20,his,10,isjustlike,7,thosecutelittlecharts
250   DATA 5,thatyoualwaysseeinyourfriendly
260   DATA 3,neighborhoodoptometristsoropticiansoffice.
270   END
 

Changing Graphics Character Size

The FOR..NEXT loop writes lines of text on the screen with different character sizes. The DATA statements contain both pieces of information. Incidentally, notice that the WINDOW statement specifies a Ymin larger than the Ymax. This causes the top of the screen to have a lesser Y-value than the bottom. This is perfectly legal.

The next program deals with the relationship between the size of the character, per se, and the size of the character cell. (Run the example program in file ``CharCell''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140   FRAME                         ! Draw a box around the screen
150   SHOW 0,36,-7.5,22.5           ! Isotropic units; Left/Right/Bottom/Top
160   FOR X=0 TO 36                 ! \
170     FOR Y=0 TO 15               !  \
180       MOVE X-.1,Y+.1            !   \
190       DRAW X+.1,Y-.1            !    \
200       MOVE X+.1,Y+.1            !     > Draw all the little Xs.
210       DRAW X-.1,Y-.1            !    /
220     NEXT Y                      !   /
230   NEXT X                        !  /
240   FOR I=0 TO 27 STEP 9          ! \
250     CLIP I,I+9,0,15             !  \
260     FRAME                       !   > Draw boxes around the character cells
270   NEXT I                        !  /
280   CLIP OFF                      ! Deactivate clipping so LABELs will work
290   CSIZE 50                      ! Character cells half the screen high
300   MOVE 0,0                      ! Starting point (LORG 1 by default)
310   LABEL "AbCd"                  ! Sample letters
320   CSIZE 7,.45                                 ! \
330   LORG 6                                      !  \
340   MOVE 18,22                                  !   > Write the title
350   LABEL "Size of Character in Character Cell" !  /
360   END
 

Character Cells

As the diagram shows, a character is drawn inside a rectangle, with some space on all four sides. The character's height and width are measured in GDUs and are specified by the CSIZE statement. Program lines 250 through 280 subdivide the rectangle into four 9 wide by 15 high grids. Characters are drawn in this framework, called the symbol coordinate system. Of course, the little Xs in the plot above are not drawn when you label a string of text; they are there solely to show the position of the characters within the character cell.

The definition of aspect ratio for a character is identical to the definition of aspect ratio for the hard clip limits mentioned earlier: the width divided by the height. Thus, if you want short, fat letters, use an aspect ratio of 1.5 or larger. If you want tall, skinny letters, use an aspect ratio less than 0.5.
``CSIZE 3'' Cell 3 GDUs high, aspect ratio 0.6 (default).
``CSIZE 6,.3'' Cell 6 GDUs high, aspect ratio 0.3 (tall and skinny).
``CSIZE 1,2'' Cell 1 GDU high, aspect ratio 2 (short and fat).

Note that you do not have to specify a second parameter (the aspect ratio) in the CSIZE statement since it defaults to 0.6.

The second statement you need is LORG, which means label origin. This lets you specify which point on the label ends up at the point moved to before writing the label. (Run the example program in file ``Lorg''.)

 
100   CLEAR SCREEN              ! Clear the alpha screen
110   GINIT                     ! Initialize various graphics parameters
120   PLOTTER IS CRT,"INTERNAL" ! Use the internal screen
130   GRAPHICS ON               ! Turn on the graphics screen
140   SHOW 0,10,10.5,0          ! Isotropic scaling: Left/Right/Bottom/Top
150   FRAME                     ! Draw a box around the screen
160   FOR Lorg=1 TO 9           ! Loop on LORG parameters
170     LORG 2                  ! Left-center origin for the "LORG n ="
180     CSIZE 4                 ! Characters cell 4 GDUs high
190     MOVE 0,Lorg             ! Move to position for "LORG n =" label
200     LABEL "LORG";Lorg;"="   ! Write the label
210     MOVE 8+.1,Lorg+.1       ! \
220     DRAW 8-.1,Lorg-.1       !  \
230     MOVE 8-.1,Lorg+.1       !   >  Draw an "X" to show where pen is
240     DRAW 8+.1,Lorg-.1       !  /
250     LORG Lorg               ! Specify LORG for "TEST",
260     CSIZE 6                 ! ...and larger letters
270     MOVE 8,Lorg             ! Move the center of the "X"
280     LABEL "TEST"            ! Write "TEST", using current LORG
290   NEXT Lorg                 ! And so forth
300   END
 


Label Origins

The ×s indicate where the pen was moved to before labeling the word "TEST". This diagram means, for example, that if LORG 1 is in effect and you move to 4,5 to write a label, the lower left of that label would be at 4,5. This automatically compensates for the character size, aspect ratio, and label length. It makes no difference whether there is an odd or even number of characters in the label. If LORG 6 had been in effect, and you had moved to 4,5, the center of the top edge of the label would be at 4,5. You can readily see how useful this statement is in centering labels, both horizontally and vertically.

The third statement you need to know is LDIR, meaning label direction. LDIR specifies the angle at which the subsequent labels will be drawn. The angle is specified in the current angular units, and is either DEG (degrees) or RAD (radians). For example, assuming degrees is the current angular mode:
``LDIR 0'' Writes label horizontally to the right.
``LDIR 90'' Writes label vertically, ascending.
``LDIR 14'' Writes label ascending a gentle slope, up and right.
``LDIR 180'' Writes label upside down.
``LDIR 270'' Writes label vertically, descending.

In the program below, note that LORG 2 was specified and remained in effect for many LDIRs. Each label is centered on the left edge relative to the label. (Run the example program in file ``Ldir''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140                                 ! (Series 200 computers)
150   FRAME                         ! Draw a box around the screen
160   WINDOW -1,1,-1.1,1            ! Anisotropic units; Left/Right/Bottom/Top
170   DEG                           ! Angular mode: Degrees
180   LORG 2                        ! Label origin is left center
190   FOR Angle=0 TO 350 STEP 10    ! Every 10 degrees
200     LDIR Angle                  ! Labeling angle
210     MOVE 0,0                    ! Move to center of screen
220     LABEL "-------LDIR";Angle   ! Write using the current LDIR
230   NEXT Angle                    ! And so on
240   END
 

Changing Label Directions (Ldir)

The label origin specified by LORG is relative to the label, not the plotting surface, and is independent of the current label direction. For example, if you specified

 
LORG 3
DEG
LDIR 90
MOVE 6,8
 

and then wrote the label, it would be written going straight up, not horizontally. Therefore, it is the upper left corner of the label which is at point 6,8 relative to the rotated label. Relative to the plotting device, however, it is the lower left corner of the label which is at 6,8 (in this example) because the label has been rotated.

The statement which actually causes labels to be written is LABEL. LABEL accounts for the most recently specified CSIZE, LDIR and LORG when it writes a label. You must position the label, however, by using (for example) a MOVE statement to get to the point at which you want the label to be placed.

All four statements have been utilized in the following program. (Run the example program in file ``SinLabel''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters.
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140   X_gdu_max=100*MAX(1,RATIO)    ! Determine how many GDUs wide the screen is
150   Y_gdu_max=100*MAX(1,1/RATIO)  ! Determine how many GDUs high the screen is
160   LORG 6                        ! Reference point: center of top of label
170   MOVE X_gdu_max/2,Y_gdu_max    ! Move to middle of top of screen
180   LABEL "VOLTAGE VARIANCE"      ! Write title of plot
190   DEG                           ! Angular mode is degrees (used in LDIR)
200   LDIR 90                       ! Specify vertical labels
210   CSIZE 3.5                     ! Specify smaller characters
220   MOVE 0,Y_gdu_max/2            ! Move to center of left edge of screen
230   LABEL "Voltage"               ! Write Y-axis label
240   LORG 4                        ! Reference point: center of bottom of label
250   LDIR 0                        ! Horizontal labels again
260   MOVE X_gdu_max/2,.07*Y_gdu_max! X: center of screen; Y: above key labels
270   LABEL "Time (seconds)"        ! Write X-axis label
280   VIEWPORT .1*X_gdu_max,.99*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max          
                                     ! Define subset of screen area
290   FRAME                         ! Draw a box around defined subset
300   WINDOW 0,100,16,18            ! Anisotropic scaling: left/right/bottom/top
310   FOR X=2 TO 100 STEP 2         ! Points to be plotted...
320     PLOT X,RND+16.5             ! Get a data point and plot it against X
330   NEXT X                        ! et cetera
340   END
 

Many times it's nice to have bold letters. You can achieve this effect by plotting the label several times, moving the label origin just slightly each time. In the following version of the program, notice lines 180 through 210. The loop variable, ``I'', goes from -.3 to .3 by tenths. This is the offset in the X direction of the label origin. Since this is being labeled with LORG 6 in effect, the label origin (the point moved to immediately prior to labeling) represents the center of the top edge of the label. (Run the example program in file ``SinLabel2''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters.
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140   X_gdu_max=100*MAX(1,RATIO)    ! Determine how many GDUs wide the screen is
150   Y_gdu_max=100*MAX(1,1/RATIO)  ! Determine how many GDUs high the screen is
160   LORG 6                        ! Reference point: center of top of label
170   FOR I=-.3 TO .3 STEP .1       ! Offset of X from starting point
180     MOVE X_gdu_max/2+I,Y_gdu_max! Move to about middle of top of screen
190     LABEL "VOLTAGE VARIANCE"    ! Write title of plot
200   NEXT I                        ! Next position for title
210   DEG                           ! Angular mode is degrees (used in LDIR)
220   LDIR 90                       ! Specify vertical labels
230   CSIZE 3.5                     ! Specify smaller characters
240   MOVE 0,Y_gdu_max/2            ! Move to center of left edge of screen
250   LABEL "Voltage"               ! Write Y-axis label
260   LORG 4                        ! Reference point: center of bottom of label
270   LDIR 0                        ! Horizontal labels again
280   MOVE X_gdu_max/2,.07*Y_gdu_max! X: center of screen; Y: above key labels
290   LABEL "Time (seconds)"        ! Write X-axis label
300   VIEWPORT .1*X_gdu_max,.99*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max          
                                     ! Define subset of screen area
310   FRAME                         ! Draw a box around defined subset
320   WINDOW 0,100,16,18            ! Anisotropic scaling: left/right/bottom/top
330   FOR X=2 TO 100 STEP 2         ! Points to be plotted...
340     PLOT X,RND+16.5             ! Get a data point and plot it against X
350   NEXT X                        ! et cetera
360   END
 

This method can also be used to offset in the Y direction. Or, offset both X and Y. This will give you characters that are thick in a diagonal direction, which makes them look like they are coming out of the page at you. However, a more typical bolding is produced by offsetting only in the X direction.

Axes and Grids

AXES and GRID do similar operations. We've already seen how to use the AXES statement. The GRID statement causes the major tick marks to extend all the way across the plotting surface.

Once we have the axes drawn, we must label various points along them with numbers designating the values at those points. Once again, we use the LABEL statement. (Run the example program in file ``SinAxes''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters.
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140   X_gdu_max=100*MAX(1,RATIO)    ! Determine how many GDUs wide the screen is
150   Y_gdu_max=100*MAX(1,1/RATIO)  ! Determine how many GDUs high the screen is
160   LORG 6                        ! Reference point: center of top of label
170   FOR I=-.3 TO .3 STEP .1       ! Offset of X from starting point
180     MOVE X_gdu_max/2+I,Y_gdu_max! Move to about middle of top of screen
190     LABEL "VOLTAGE VARIANCE"    ! Write title of plot
200   NEXT I                        ! Next position for title
210   DEG                           ! Angular mode is degrees (used in LDIR)
220   LDIR 90                       ! Specify vertical labels
230   CSIZE 3.5                     ! Specify smaller characters
240   MOVE 0,Y_gdu_max/2            ! Move to center of left edge of screen
250   LABEL "Voltage"               ! Write Y-axis label
260   LORG 4                        ! Reference point: center of bottom of label
270   LDIR 0                        ! Horizontal labels again
280   MOVE X_gdu_max/2,.07*Y_gdu_max! X: center of screen; Y: above key labels
290   LABEL "Time (seconds)"        ! Write X-axis label
300   VIEWPORT .1*X_gdu_max,.98*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max          
                                     ! Define subset of screen area
310   FRAME                         ! Draw a box around defined subset
320   WINDOW 0,100,16,18            ! Anisotropic scaling: left/right/bottom/top
330   AXES 1,.05,0,16,10,5,3        ! Draw axes with appropriate ticks
340   CLIP OFF                      ! So labels can be outside VIEWPORT limits
350   CSIZE 2.5,.5                  ! Smaller chars for axis labeling
360   LORG 6                        ! Ref. pt: Top center     |\
370   FOR I=0 TO 100 STEP 10        ! Every 10 units          | \
380     MOVE I,15.99                ! A smidgeon below X-axis |  > Label X-axis
390     LABEL USING "#,K";I         ! Compact; no CR/LF       | /
400   NEXT I                        ! et sequens              |/
410   LORG 8                        ! Ref. pt: Right center   |\
420   FOR I=16 TO 18 STEP .25       ! Every quarter           | \
430     MOVE -.5,I                  ! Smidgeon left of Y-axis |  > Label Y-axis
440     LABEL USING "#,DD.DD";I     ! DD.DD; no CR/LF         | /
450   NEXT I                        ! et sequens              |/
460   PENUP
470   FOR X=2 TO 100 STEP 2         ! Points to be plotted
480     PLOT X,RND+16.5             ! Plot a data point
490   NEXT X
500   END
 

Labeled Axes (Sinaxes)

Note that the tick marks drawn by the AXES statement extend only toward the interior of the graph. Clipping (automatically put into effect by the VIEWPORT statement) was still active at the soft clip limits. If the CLIP OFF statement had been placed before the AXES statement, the tick marks would have extended on both sides of the axes. However, the axes themselves would have extended across the entire width of the hard clip limits and right through the axes' labels.

The CLIP OFF statement was necessary, though. The LABEL statement draws the letters as a series of vectors (lines), and any lines which are outside the current soft clip limits (when CLIP is ON) are cut off. This means that had line 350 (the CLIP OFF) been missing from the program, none of the axis labels would have been drawn, since they are all outside the VIEWPORT area. Of course, the main titles ("VOLTAGE VARIANCE", "Voltage", and "Time (seconds)") would still have been drawn, because they are done before the VIEWPORT is executed.

If your graph needs to be read with more precision than the AXES statement affords, you can use the GRID statement. This is similar to AXES, except the major ticks extend across the entire soft clip area, and the minor ticks for X and Y intersect in little crosses between the grid lines. The previous program has only one change: the AXES statement has been replaced by a GRID statement.

 
GRID 5,.25,0,16,2,2,1         ! Draw grid with appropriate ticks
 

Labeled Grid

Note that not only was AXES replaced by GRID, some of the parameters were changed also because the minor ticks specified in the AXES statement were so close together that the minor tick crosses drawn by the GRID statement would have overlapped. The end result would have been a grid with even the minor ticks extending all the way across the soft clip area.

Strategy: Axes Versus Grids

On many occasions, an application is defined such that there is no question as to which statement to use. Other times, however, you want to weigh the alternatives carefully before setting your program in concrete. To aid you in the decision, here are some advantages and disadvantages to both statements.

Advantages of AXES:

Advantages of GRID:

However, if you want to estimate data points accurately from the finished plot, but also want to prevent the plot from appearing cluttered, it can be done. Below is a plot drawn by a program identical to the previous one except for the GRID statement. The GRID statement used specifies exactly the same parameters as the AXES statement (two programs ago) with one exception: the major tick length parameter is reduced. This causes the tick crosses to be reduced to dots. Using this strategy allows easy interpolation of data points (to the same accuracy previously used in the AXES statement), but does not clutter the graph as much as normal ticks would.

 
GRID 1,.05,0,16,10,5,.0001    ! Draw grid with appropriate ticks
 

Be aware that the computer still thinks of these smaller tick marks as crosses, which means that both the horizontal and vertical components must be drawn. This looks to you like drawing and then redrawing each dot. Therefore, you can expect this type of grid to take a while to plot when you send it to a hard-copy plotter.

Another way to compromise between ease of interpolation and lack of clutter is to use both AXES and GRID in the same program. Note the program below. GRID is used for the major tick lines, but since the minor tick crosses are not desired within each rectangle between the major tick lines, AXES is used to specify minor ticks. (Run the example program in file ``SinGrdAxes''.)

 
100   CLEAR SCREEN                  ! Clear the alpha display
110   GINIT                         ! Initialize various graphics parameters.
120   PLOTTER IS CRT,"INTERNAL"     ! Use the internal screen
130   GRAPHICS ON                   ! Turn on the graphics screen
140   LORG 6                        ! Reference point: center of top of label
150   X_gdu_max=100*MAX(1,RATIO)    ! Determine how many GDUs wide the screen is
160   Y_gdu_max=100*MAX(1,1/RATIO)  ! Determine how many GDUs high the screen is
170   FOR I=-.3 TO .3 STEP .1       ! Offset of X from starting point
180     MOVE X_gdu_max/2+I,Y_gdu_max! Move to about middle of top of screen
190     LABEL "VOLTAGE VARIANCE"    ! Write title of plot
200   NEXT I                        ! Next position for title
210   DEG                           ! Angular mode is degrees (used in LDIR)
220   LDIR 90                       ! Specify vertical labels
230   CSIZE 3.5                     ! Specify smaller characters
240   MOVE 0,Y_gdu_max/2            ! Move to center of left edge of screen
250   LABEL "Voltage"               ! Write Y-axis label
260   LORG 4                        ! Reference point: center of bottom of label
270   LDIR 0                        ! Horizontal labels again
280   MOVE X_gdu_max/2,.07*Y_gdu_max! X: center of screen; Y: above key labels
290   LABEL "Time (seconds)"        ! Write X-axis label
300   VIEWPORT .1*X_gdu_max,.98*X_gdu_max,.15*Y_gdu_max,.9*Y_gdu_max          
                                     ! Define subset of screen area
310   WINDOW 0,100,16,18            ! Anisotropic scaling: left/right/bottom/top
320   AXES 1,.05,0,16,5,5,3         ! Draw axes intersecting at lower left
330   AXES 1,.05,100,18,5,5,3       ! Draw axes intersecting at upper right
340   GRID 10,.25,0,16,1,1          ! Draw grid with no minor ticks
350   CLIP OFF                      ! So labels can be outside VIEWPORT limits
360   CSIZE 2.5,.5                  ! Smaller chars for axis labeling
370   LORG 6                        ! Ref. pt: Top center     |\
380   FOR I=0 TO 100 STEP 10        ! Every 10 units          | \
390     MOVE I,15.99                ! A smidgeon below X-axis |  > Label X-axis
400     LABEL USING "#,K";I         ! Compact; no CR/LF       | /
410   NEXT I                        ! et sequens              |/
420   LORG 8                        ! Ref. pt: Right center    |\
430   FOR I=16 TO 18 STEP .25       ! Every quarter            | \
440     MOVE -.5,I                  ! Smidgeon left of Y-axis  |  > Label Y-axis
450     LABEL USING "#,DD.DD";I     ! DD.D; no CR/LF           | /
460   NEXT I                        ! et sequens               |/
470   PENUP                         ! LABEL statement leaves the pen down
480   FOR X=2 TO 100 STEP 2         ! Points to be plotted...
490     PLOT X,RND+16.5             ! Get a data point and plot it against X
500   NEXT X                        ! et cetera
510   END
 

Using AXES and GRID

Note that two AXES statements were used. The parameters are identical save for the position of the intersection. The first AXES specifies an intersection position of 0,16: the lower left corner of the soft clip area. The second specifies an intersection position of 100,18: the upper right corner of the soft clip area.

Also note that the FRAME statement was removed; the lines around the soft clip limit were being drawn by the AXES statements and the GRID statement anyway.