Hints and Kinks on VAX GKS
Hints and Kinks on VAX GKS
Brian J. Kramper
The purpose of this document is give an overview of VAX GKS and summarize its salient functions so the casual user does not need to pore over the three volumes from which this is condensed. I have also tried to point out problems I encountered in learning to use this product.
Rather than using the same format as DEC for grouping the functions, I have tried to group them as one is likely to use them: opening or closing a workstation, setting up the workstation, graphics primitives, etc. Hopefully, this will enable readers to progress much faster than I did into using this product.
The first call to GKS must be the gks$open_gks. VAX GKS keeps VT330 and VT340 devices in ReGIS graphics mode as long as the workstation is open. Because of this ASCII text written to the screen via ``write'' statements are interpreted as ReGIS commands and may leave the terminal in an unpredictable state. For these devices it is recommended that the file form be used and that necessary output to the screen be implemented using the gks$text or gks$message functions.
$DESCRIPTOR(error_file, ``sys$error:'') for output to a terminal$DESCRIPTOR(error_file, ``errorfile.tmp'') for output to a file
Now that GKS has been opened, you can open a workstation and activate it. Multiple workstations may be opened from the same terminal, but each of them must have a unique work_station_id and device_connection_id pair. Note that the workstation_id is used with many of the GKS calls and must be saved throughout the session. The other important variable is the workstation_type which is an output from opening the workstation. The safest sequence is to open the workstation initially with the default device_connection_id GKS$K_CONID_DEFAULT and the default workstation_type GKS$K_WSTYPE_DEFAULT, then use gks$inq_ws_type to get the actual type of the workstation you are using and save the type, close the workstation using gks$close_ws and re-open the workstation using the actual type.
Calls to close the workstation are made in the reverse order from opening the workstation: first deactivate the workstation, then close it, and finally close GKS.
One reason for inquiring and saving the actual workstation type is to determine the actual size of the workstation screen with which you are working. The call to gks$inq_max_ds_size returns the size of the workstation surface both in actual device coordinates and in raster units, and tells whether the surface is measured in meters. These dimensions can be used in setting up the display portion of the workstation surface and in transformations for various parts of the workstation surface.
The portion of the workstation surface to be used is determined by the coordinate arguments to gks$set_ws_window and gks$set_ws_viewport. The coordinates specified for the window determine the proportions for the display, whereas the coordinates for the viewport are in actual device coordinates. The two coordinate systems need to be proportional in order for the window to map proportionally to the viewport. These two calls are only used once per open workstation. Note that the first argument in each of these calls is a workstation_id.
The gks$set_window and gks$set_viewport may be used as often as necessary to map portions of the workstation surface for different purposes. Note that the first argument for each of these functions is a transform. These transforms may be selected within a created segment to determine how a particular set of primitives is to be placed in the specified segment.
The gks$set_viewport_priority function specifies the relative input priority of the transforms. This function must be called prior to using stroke or locator input devices which attempt input from locations on the workstation surface which fall within the area of multiple viewports so that the correct transform is used to convert to world coordinates. The relative_priority determines whether the first transform has lower ( GKS$K_INPUT_PRIORITY_LOWER) or higher ( GKS$K_INPUT_PRIORITY_HIGHER) priority than the reference_transform.
The following GKS functions allow the application program to control the updating of the workstation surface in several different ways.
The gks$clear_ws function performs its tasks in the following order:
GKS$K_CLEAR_CONDITIONALLYGKS$K_CLEAR_ALWAYS
The gks$redraw_seg_on_ws function performs its tasks in the following order:
The gks$set_defer_state function determines when the display regenerations occur. A global interaction is a request for input from any open workstation. A local interaction is a request for input from the specified workstation.
GKS$K_ASAP generates images as soon as possibleIf implicit regenerations are allowed, all visible segments stored on the workstation are redrawn, but output not stored in segments is lost. Pending or subsequent changes in the workstation surface such as output bundle index changes, segment attribute changes, transformation changes, etc., result in implicit regenerations. If implicit regenerations are suppressed, the surface is placed in GKS$K_NEWFRAME_NECESSARY, but do not occur until the next workstation update, usually gks$update_ws.GKS$K_BNIG generates images before the next global interaction
GKS$K_BNIL generates images before the next local interaction
GKS$K_ASTI generates images at some time determined by the workstation
GKS$K_IRG_SUPPRESSED suppress implicit regenerationsGKS$K_IRG_ALLOWED allow implicit regenerations
The gks$update_ws function generates all deferred output for the specified workstation without clearing the screen. If the state of the workstation at the time of the call to gks$update_ws is GKS$K_NEWFRAME_NOTNECESSARY or if the update_flag argument in the call has been set to GKS$K_POSTPONE_FLAG, implicit regenerations continue to be suppressed. Otherwise the following tasks are performed:
GKS$K_POSTPONE_FLAGGKS$K_PERFORM_FLAG
The common storage unit under GKS is the segment. Primitives which are NOT drawn within a segment are NOT saved and are NOT redrawn when the workstation surface is updated. If you want a primitive saved across a regeneration or update, it must be entered in a segment which is associated with the particular workstation.
gks$create_seg allows you to store all output and output attribute functions on all active workstations until gks$close_seg is called. Only one segment may be opened at a time, and once a segment is closed it must be either deleted (using the gks$delete_seg function) or renamed (using the gks$rename_seg function) before it can be used again.
Text strings can be stored in a segment or not, depending on the usage. If the string is part of the display, it should be stored in a segment; if not, i.e., it is an informational or diagnostic message, it should need not be placed in a segment. The two attributes which are most frequently changed for text strings are the height and spacing. The default height is 0.01 or 1% of the display size. The default spacing is 0.0 or no spacing between characters.
The gks$inq_text_extent function yields several useful pieces of information about a text string and its placement on the workstation surface. By giving the x- and y-coordinates and the text string, GKS returns the location where a new text string may begin (the concatenation coordinates) and the size of the rectangle which contains the text string (the extent rectangle). The concatenation coordinates are given in world coordinates as single values. The extent rectangle is an array of coordinates describing the rectangle starting with the lower left corner and proceeding counter-clockwise. The concatenation coordinates and extent rectangle are useful in computing the placement and size of the echo areas for string input devices.
The gks$message function allows an application to deliver a message to a workstation at an implementation-dependent location on the workstation surface.
The gks$polyline function has three arguments. The first argument is the number of points to be connected. The second and third arguments, x_coordinates and y_coordinates, are arrays of at least length number_of_points given in world coordinates. If you are using transforms, the data is given in units of this coordinate system. By default these values are clipped. The default width for a line is 1.0, the nominal width for the workstation, but can be varied by using gks$set_pline_linewidth.
The gks$polymarker function has the same arguments as the gks$polyline function. The default size for a marker is 1.0, the nominal size for the workstation, but it can also be varied by using gks$set_pmark_size. Although the nominal size for markers other than the dot are too large for plotting, a size of 0.75 or less for the asterisk and 0.4 or less for the other three markers seems to be usable. There are five polymarker symbols available with the default symbol for a marker being the asterisk:
GKS$K_MARKERTYPE_ASTERISKGKS$K_MARKERTYPE_DOT
GKS$K_MARKERTYPE_PLUS
GKS$K_MARKERTYPE_CIRCLE
GKS$K_MARKERTYPE_DIAGONAL_CROSS
Note that markers may NOT be changed within a segment.
Transforms may be used to map data with different scale factors into the same workstation surface area. By using two transforms with different window coordinates, a device with a data range of 0.0 to 100.0 may be mapped into the same surface area as a device with a data range of 10.0 to 20.0. Each transform can then be selected individually to map a different set of data to the same workstation surface area. (See gks$set_window and gks$set_viewport functions under the section on Setting up the workstation.)
By default, VAX GKS segments are set to GKS$K_UNDETECTABLE. A segment must be set to GKS$K_DETECTABLE before it can be selected using a pick device.
By default, VAX GKS segments are set to GKS$K_NORMAL. By setting a segment to GKS$K_HIGHLIGHTED, the selected segment extent rectangle is changed to an alternative foreground color on color output devices and to reverse video on monochrome output devices at the next regeneration. If a segment is not visible when an attempt is made to highlight it, the highlighting does not take place until the segment is again made visible.
By default, VAX GKS segments are set to GKS$K_VISIBLE. By setting a segment to GKS$K_INVISIBLE, the segment is erased from the workstation surface at the next regeneration. Depending on the capabilities of the workstation and whether the segment overlays another segment, the application may need to call either the gks$update_ws function or the gks$redraw_seg_on_ws function.
The six classes of input devices available under VAX GKS by constant identifiers are:
GKS$K_INPUT_CLASS_CHOICEGKS$K_INPUT_CLASS_LOCATOR
GKS$K_INPUT_CLASS_PICK
GKS$K_INPUT_CLASS_STRING
GKS$K_INPUT_CLASS_STROKE
GKS$K_INPUT_CLASS_VALUATOR
The choice class device is used to set up menus, but is limited in the number of choices for certain combinations of workstation and input device. The locator class device allows you to get the coordinates of a particular point on the workstation surface. The pick class device allows you to select segments which you have made detectable via the gks$set_seg_detectability function. The string class device allows you to input alphanumeric text strings.
Each device is further identified by up to six different prompt and echo types.
There are also three operating modes for soliciting input from these devices:
GKS$K_INPUT_MODE_REQUESTGKS$K_INPUT_MODE_SAMPLE
GKS$K_INPUT_MODE_EVENT
The operating mode is selected by using the gks$set_xxx_mode function where xxx is one of the six device classes. Whether the prompt and input values are echoed on the workstation surface is also controlled through this function by specifying GKS$K_ECHO or GKS$K_NOECHO.
Request and sample mode are synchronous and suspend or block program execution until input is received. Event mode allows asynchronous input via the event queue. The gks$await_event function checks the queue for ANY input from ANY device on ANY open workstation. An entry on the queue consists of the workstation identifier, the input class of the device and the logical input device number. Once the class of the device that generated the event is determined, one of the gks$get_xxx functions can be called to service the event. One significant problem has surfaced in the use of the pick device in event mode. Once the pick device has been initialized and set into event mode, resetting the device to request mode does NOT remove the pick prompt from the workstation surface. This problem is especially evident when, following the resetting of the pick device to request mode, the string device is initialized for event mode. The host continues to send cursor updates for the pick device and the updates are sometimes interpreted as input for the string device causing a string event to occur.
The normal sequence of operations for using any of the devices consists of four basic steps: inquiring the present state of the device, initializing the device, setting the operating mode and echo state of the device and getting the information from the device.
When inquiring the present state of a pick device, four variables need to be initialized: workstation_id, device_number, value_type and record_buffer_length. The device_number is dependent on the application and the workstation type. The value_type should normally be set to GKS$K_VALUE_REALIZED so that the graphics handler returns the input values as they are implemented. The record_buffer_length should be set to four (4) bytes.
In initializing the pick device I have used logical device 1 and prompt and echo type 1. Logical devices 1 through 4 should all be able to be used for the mouse. Prompt and echo type 1 highlights the extent rectangle of the picked primitive so long as the segment has been set detectable. Type 2 highlights the extent rectangle of all the primitives which share the pick identifier of the picked primitive. Type 3 highlights the extent rectangle of the picked segment.
The operating_mode may be any of the three listed above. The echo_flag determines whether the prompt and input values are echoed on the workstation surface.
If GKS$K_INPUT_MODE_REQUEST is selected as the operating_mode, information is returned via the gks$request_pick function. The application program is suspended until input is obtained. The input_status argument returns one of three values:
GKS$K_STATUS_NONE Break during inputGKS$K_STATUS_OK Input obtained
GKS$K_STATUS_NOPICK Input triggered without picking
If GKS$K_INPUT_MODE_EVENT is selected as the operating_mode, the application program continues to run and pick reports are queued up in a time-ordered FIFO. Since multiple input devices may be active simultaneously, the application program uses the gks$await_event function to find out if any event has taken place. The gks$get_pick function returns an input_status of either GKS$K_STATUS_OK if a segment has been picked or GKS$K_STATUS_NOPICK if a trigger was obtained without a segment being selected. If a detectable segment was picked, the function returns the segment picked and the identifier of the pick.
If the application only wishes to handle one event at a time, or the event queue has overflowed, all reports of a given input_class and device_number from a workstation can be flushed using the following function.
When inquiring the present state of a string device, three variables need to be initialized: workstation_id, device_number and record_buffer_length. The device_number is dependent on the application and the workstation type. The record_buffer_length should be initialized to eight (8) bytes.
Logical devices 1 and 4 use the keyboard to return a DEC multinational text string to the calling program. The string is terminated by a carriage return. Input editing includes the use of the following keys:
DELETE deletes the last characterLogical device 2 is used only on VAXstations and returns an SMG encoded key. Logical device 3 is supported on VT240, VT125 and TEKTRONIX 4107 and returns the ASCII value associated with the typed key. Only prompt and echo type 1 is supported, and it displays the current string in the echo area. The default_string is the equivalent of a prompt and may be a null string. The echo_area is an array of four real numbers containing the minimum and maximum x and y values of the echo rectangle. These are given in absolute device coordinates. The placement of the echo_area may be calculated by using the output from the gks$inq_text_extent function. The first word of the data_record is the size of the input buffer in character units; the second is the initial cursor position within that string.CTRL/H moves the cursor to the beginning of the string
CTRL/E moves the cursor to the end of the string
CTRL/B recalls only the initial (default) string
CTRL/A toggles between insert and overstrike modes
Left arrow moves the cursor left
Right arrow moves the cursor right
The operating modes for string devices correspond to those of pick devices (see above). The inputs string_buffer and string_size are the application program's input buffer and the length of the input string. For gks$get_string report_string_size is the length of the input string and may be larger than the size of the input buffer.
data_record[0] Number of choice strings.data_record[1] Address of array containing choice string lengths.
data_record[2] Address of array containing addresses of choice strings.
When two or more transforms map to the same workstation surface area, the application program must establish which transform is to be used to convert the device coordinates to world coordinates. The gks$set_viewport_priority function establishes the relative priority of transforms. This function should be called prior to initializing the locator input device.
The gks$inq_ws_category function returns one of the following constants provided the returned error_status is 0:
GKS$K_WSCAT_OUTPUT Output onlyGKS$K_WSCAT_INPUT Input only
GKS$K_WSCAT_OUTIN Output and input
GKS$K_WSCAT_WISS Workstation independent segment storage
GKS$K_WSCAT_MO Metafile output
GKS$K_WSCAT_MI Metafile input
The gks$inq_ws_classification function returns the type of display surface hardware for the specified workstation_type:
GKS$K_WSCLASS_VECTOR Vector deviceIf the particular workstation_type being used does not define pixel dimensions in raster units, then the gks$inq_max_ds_size function will not return valid values to the raster unit arguments.GKS$K_WSCLASS_RASTER Raster device
GKS$K_WSCLASS_OTHERD All other devices
The following is an example program which uses timed events to trigger AST's for user input and data output.
main() { setup_workstation(); /* set up the workstation ... */ setup_screen(); /* and the screen */ setup_pick(); /* set up pick device, event mode */ event_available = FALSE; /* no events initially */ status = SYS$SETIMR(gks_flag, gks_delay, gks_ast, 0); do { if (event_available) { /* if there's an event ... */ process_event(); /* do what's necessary */ event_available = FALSE; /* we're done for now */ } else status = SYS$HIBER(); /* wait for something to happen */ } while (forever); /* on a clear day ... */ cleanup_workstation(); /* forever has arrived */ } /* end main */gks_ast() { input_class = GKS$K_INPUT_CLASS_NONE; gks$await_event(&0.0, &workstation_id, &input_class, &device_number); if (input_class != GKS$K_INPUT_CLASS_NONE) { /* something to do? */ event_available = TRUE; /* Ah, yes */ status = SYS$WAKE(0,0); /* Let's go ... */ } else /* come back later */ status = SYS$SETIMR(gks_flag, &gks_delay, &gks_ast, 0); } /* end gks_ast */
Keywords: GKS, graphics, plotting
Distribution: normal