/*.......................................................................
 * Implement the demo "redraw_slice" command.
 *
 * Input:
 *  demo       Pgdemo *   The demo being serviced.
 *  interp Tcl_Interp *   The TCL interpreter of the demo.
 *  argc          int     The number of TCL arguments in argv[].
 *  argv         char **  An array of 'argc' TCL arguments. No arguments
 *                        are expected.
 * Output:
 *  return        int     TCL_OK    - Normal completion.
 *                        TCL_ERROR - The interpreter result will contain
 *                                    the error message.
 */


/*.......................................................................
 * Implement the demo "recolor_image" command. This takes one of a set of
 * supported color-table names and redisplays the current image with the
 * specified color table.
 *
 * Input:
 *  demo       Pgdemo *   The demo being serviced.
 *  interp Tcl_Interp *   The TCL interpreter of the demo.
 *  argc          int     The number of TCL arguments in argv[].
 *  argv         char **  An array of 'argc' TCL arguments.
 *                        argv[0] - A color table name chosen from:
 *                                   "aips"    -  AIPS tvfiddle color table.
 *                                   "blue"    -  A blue color table.
 *                                   "green"   -  A green color table.
 *                                   "grey"    -  A grey-scale color table.
 *                                   "heat"    -  The IRAF "heat" color table.
 *                                   "rainbow" -  A red color table.
 *                                   "red"     -  A red color table.
 * Output:
 *  return        int     TCL_OK    - Normal completion.
 *                        TCL_ERROR - The interpreter result will contain
 *                                    the error message.
 */


/*.......................................................................
 * Display a new function in the image window.
 *
 * Input:
 *  demo       Pgdemo *   The demo instance object.
 *  interp Tcl_Interp *   The TCL interpreter of the demo.
 *  fn       IMAGE_FN(*)  The function to be displayed.
 * Output:
 *  return        int     TCL_OK    - Normal completion.
 *                        TCL_ERROR - The interpreter result will contain
 *                                    the error message.
 */


/*.......................................................................
 * Display the current image function in a specified PGPLOT device.
 *
 *
 * Input:
 *  demo  Pgdemo *   The demo instance object.
 *  id       int     The id of the PGPLOT device to display.
 * Output:
 *  return   int     TCL_OK    - Normal completion.
 *                   TCL_ERROR - The interpreter result will contain
 *                               the error message.
 */


/*.......................................................................
 * Display a new slice in the slice window.
 *
 * Input:
 *  demo  Pgdemo *   The demo instance object.
 *  va    Vertex *   The vertex of one end of the slice line.
 *  vb    Vertex *   The vertex of the opposite end of the slice line.
 * Output:
 *  return   int     TCL_OK    - Normal completion.
 *                   TCL_ERROR - The interpreter result will contain
 *                               the error message.
 */


/*.......................................................................
 * Display usage instructions in the slice window.
 *
 * Input:
 *  demo     Pgdemo *   The demo instance object.
 */


/*.......................................................................
 * Display a "Please wait" message in the slice window.
 *
 * Input:
 *  demo     Pgdemo *   The demo instance object.
 */


/*.......................................................................
 * Check that the specified command-line argument names a pgtkdemo
 * script file. A pgtkdemo script file is defined as being a readable
 * text file that contains the string "#!pgtkdemo.tcl" at its start.
 *
 * Input:
 *  name    char *   The command-line argument to be checked.
 * Output:
 *  return   int     0 - Not valid.
 *                   1 - Valid.
 */


/*.......................................................................
 * This is a private cleanup-return function of tkpg_InstanceCommand().
 * It should be used to return from said function after Tcl_Preserve() has
 * been called. It calls Tcl_Release() on the widget to unblock deletion
 * and returns the specified error code.
 *
 * Input:
 *  context   ClientData    The tkpg widget cast to (ClientData).
 *  iret             int    TCL_OK or TCL_ERROR.
 * Output:
 *  return           int    The value of iret.
 */


/* cadd2 adds twice its second argument to its first. */


/*
 * pbits: given an integer i, put the rightmost n bits of the integer
 * expressed in binary, into the string s.
 */


/* Given a float, return a (static) string holding its bit pattern */


/* Returns non-zero if argument is a NaN -- all bits in exponent set,
   and mantissa non-zero. */


/* returns non-zero if argument is infinity -- all bits in exponent
   set, and mantissa zero. */


/* returns non-zero if argument is finite (normal, subnormal or zero)
   -- not all bits in exponent set. */


/* Returns non-zero if argument is normal -- exponent is not all-ones
 * nor all-zeros.
 *
 * Note that this refers to the argument as a _double_, and might not
 * give the expected results if it's applied to a single which is
 * promoted to a double when given as a parameter.
 */


/* returns a NaN.  Argument is ignored */


/* returns positive or negative infinity, depending on the sign of darg */


/*
 * pbits: given an integer i (assumed 32 bits),
 * return the rightmost n (<=32) bits of the integer expressed in binary.
 */


/* Take a string of (up to) 16 hex digits, remove leading '0x', and
 * any spaces, and convert the first 8 into i[0], and the second 8 into
 * i[1].  If the string is shorter than 16 digits, pad the remainder
 * with '0'.
 *
 * Only need this for converting 16-digit strings to d-p floats.
 *
 * Return non-zero on error.
 */


/* same, but simpler for single precision */


/*
 * Convert string to number and display in various formats.
 * If s is NULL, then use the number farg instead.  If the input
 * string cannot be interpreted, return non-zero, or zero on success.
 */


/* Calculate Rayleigh-Jeans corrected brightness temperature
   C implementation of SCULIB_JNU
 */


/* Helper routine to extract the current etal, b and tau
   values from the two fit structures. covar can be null
   if we are not interested in error information. */


/* Skydip function calculator */


/* Function to be fitted is the function - the measured data divided
   by the error in the measured data. */


/* Calculate the jacobian */


/* Routine to print iteration status */


/* C API - keep it private for now */


/*
 *  Look up convertor function from a class 'from' to a class 'to'
 */


/*
 *  Convert REF -> REF
 */


/*
 *  Convert CHAR -> CHAR
 */


/*
 * Adjust name length variable to ignore trailing white space
 */


/*
 *  Allocate a block of objects.
 *  Unless action is taken by the caller invalid
 *  data can be created if (for example) the data object is primitive and
 *  contains pointers. If however the type is primitive, and a data
 *  initialiser has been supplied, then that will be copied.
 */


/* Create a new external procedure object
 */


/*
 * Define a primitive class
 *
 */


/* A bunch of functions which help to create the class precedence list */


/*
 * Construct a list of those classes which do *not* appear as the second
 * element in any of the precedence pairs
 */


/*
 * Establish the precedence order of a set of classes. The classes to
 * be ordered form the first argument. The second is the list of all
 * direct superclass relationships, ie. for each class a list of that
 * classes direct superclasses.
 */


/*
 * Parse function/method/generic definition. Simple expression parse, then take head
 * and arguments from expression node
 */


/*
 *  Locate the allocator block for the named class
 */


/*
 * Locate class for external language interface. This forbids kernel objects
 */


/*
 * Allocate object(s) of user named class
 */


/*
 *  Locate insertion point for named item in a property list
 */


/*
 *  Get property data value if the property exists
 */


/* Reference count manipulation
 *
 *  Internal:
 *
 *    adix_refcnt       - retrieve count
 *    adix_refadj       - add offset to reference count
 */


/*
 * Locate a component
 */


/* Get value of object, or object component
 */


/*
 * Get object(s) of user named class
 */


/* Look for map control object with specified mapping type. Return insertion
 * point for new list element if not present, otherwise the the address of
 * of an ADIobj pointing to the list node containing the amp control object */


/* Map value of object, or object component
 */


/* Write data to a slot address. If the address is NULL, create a new object
 * otherwise write the data.
 *
 *   Method :
 *
 *    IF (object address holds null) THEN
 *      create object with dimensions from <mta>
 *    ENDIF
 *    IF (constructor defined and object data unset) THEN
 *      invoke constructor
 *      set dataset bit if <mta> data defined
 *    ENDIF
 *
 */


/* Put value of object, or object component
 */


/*
 *  Compare objects - doesn't handle arrays
 */


/*
 * Copy an object component to another object component
 */


/*
 * Output streamer. Operates in two modes. In calculate mode only the length of
 * the output data packet is computed. In non-calculate mode the data is written
 * as well.
 */


/*
 * Calculate total space required to stream the specified objects
 */


/*
 * Stream objects to a stream
 */


/*
 *  C generic dispatch for methods of form void xx(ADIobj,ADIobj,status)
 *  Used for SetLink
 */


/*
 *  Fortran generic dispatch for methods of form void xx(ADIobj,ADIobj,status)
 *  Used for SetLink
 */


/* Delete an object component. The component is always removed from its parent's */
/* structure, although the object data will not itself be deleted unless it */
/* reference count is already one */


/* Generic and method handling
 *
 *  adix_locmco         - find method combination given name
 *  adix_newmco         - fill out a new method combination structure
 *  adix_defmco         - high level method combination definition
 *  adix_delmco         - destroy method combination object
 *  adix_stdmcf         - "Standard" method combination
 */


/*  Rank a list of methods in descending priority order given a bunch of
 *  arguments */


/*  Gather applicable methods for the given generic function, given
 *  arguments and the allowable method forms specified. Each method
 *  is processed as follows,
 *
 *  - for each method
 *    - Is the name the same as the generic?
 *      N: next method
 *    - Is the number of arguments the same as the generic?
 *      N: next method
 *    - Are we collecting this method form?
 *      N: next method
 *    - for each argument
 *      - is user arg the same class as the method arg, or a derived
 *        class of the method arg?
 *        N: next method
 *      - add to method list of each form
 *      end for each
 *    end for each
 *  - for each method form
 *    - add the method arg class to the list for this form, and the
 *      direct superclass list for this arg to the list of such for
 *      this form UNLESS the arg is already present in the former list
 *    end for each
 */


/*  Implements "Standard" method combination. The method forms "Around",
 *  "Before" , "Primary" and "After" are all used.
 *
 */


/* Execute an external procedure. If the first argument is non-null then
 * the procedure is assumed to be a generic method, and a test is performed
 * to see if generic dispatch is defined. If no dispatch is specified, or
 * if the first argument is null, then the method is invoked with standard
 * argument form for the particular language of the method. Note that
 * methods are never invoked with bad status.
 */


/*
 * Execute a void function with a single ADIobj argument
 */


/*
 * Execute a void function with two ADIobj arguments
 */


/*
 *  Report an error and append a description of the stream position
 */


/*
 * Parse a constant value
 */


/*
 * Parse identifier=value pairs until no more. Values are written as
 * components of the structure object 'id'
 */


/*
 * Construct a new stream of undefined type
 */


/*
 * Flush a device
 */


/*
 * Flush a stream
 */


/*  ADIparseComDelList - Parses a comma separated list of expressions
 *
 *  Parses a list of expressions separated by commas, and terminated by
 *  'endtok'. The list may be empty.
 */


/*
 *  System interface functions
 */


/*
 *  General purpose functions
 */


/*
 *  Functions on INTEGER's
 */


/*
 *  Functions on List's
 */


/*
 *  Functions on Array's
 */


/*
 * Calculate number of elements in a dimensions array
 */


/*
 * Convert an offset in elements from the first array element to
 * array indices assuming Fortran indexing
 */


/*
 *  Given an array object and index array, return the base index,
 *  address of the base dimensions and the base data object
 */


/*
 * Index an array assuming Fortran indexing
 */


/*
 *  Set the contextual message string
 */


/*
 *  Set the error and contextual message string
 */


/* -------------------------------------------------------------------------
 * Data system definitions
 * -------------------------------------------------------------------------
 */


/* -------------------------------------------------------------------------
 * System method interfaces
 * -------------------------------------------------------------------------
 */


/* -------------------------------------------------------------------------
 * Component data creation
 * -------------------------------------------------------------------------
 */


/* -------------------------------------------------------------------------
 * Component data access
 * -------------------------------------------------------------------------
 */


/* -------------------------------------------------------------------------
 * Changing object attributes
 * -------------------------------------------------------------------------
 */


/* Frame stack top */


/*
 * Raise an ADI exception with an ADI name, a status code and error message
 */


/*
 * Raise an ADI exception with native name, a status code and error message
 */


/*
 *  Test a method/function definition against values on the stack. Method
 *  arguments positions define slots - each slot may map on to zero or more
 *  values on the stack. If the binding matches the arguments on the stack
 *  the location of the first stack value, and the number of subsequent
 *  values is stored for each slot. If arguments have names then entries in
 *  the local symbol table are made.
 */


/*
 * Locate symbol binding(s) with specified name. If the 2nd argument is
 * true the first binding in the symbol search tree is taken, otherwise
 * a list is returned of all the collected bindings. This list should be
 * be destroyed using lstx_sperase
 */


/*
 * Construct a new expression tree node
 */


/* The expression evaluator.
 *
 *  Step 1 :
 *
 *    Evaluate the head of the expression
 *
 *
 */


/*
 *  Evaluate list of expressions, returning value of last one evaluated
 */


/* _List object allocator */


/*
 *  In situ list reversal
 */


/* Append an item on to a list held at some address
 */


/*
 * Create a list cell updating an object point to point to the address of
 * _CDR cell.
 */


/*
 * Special list erase where only list cells are deleted
 */


/*
 * Parse a single statement. The token which signifies the end of valid statement
 * (an end-of-line or semicolon) is not matched by this routine. Null statements
 * are ignored, and the null identifier returned.
 *
 */


/*
 *  Parse and execute commands appearing on an input stream, sending output
 *  to the output stream if specified
 */


/* Number of allocations */


/*
 * Finds the offset from id1 to id2 in elements of the blocks they reference
 * If the block id of id2 is different from that of id1, then the former
 * must be a slave block of the latter
 */


/*
 * Add an offset to a block/slot identifier. If the offset takes the
 * routine past the end of the block's allocated data, then the
 * block must be part of a master/slave grouping.
 */


/* Set up a basic block control structure */


/* Initialise a new basic block, allowing the caller to override the
 * default cluster size
 */


/*
 * Pass down the object chain, committing changes and closing if required
 */


/*
 * Construct an object chain with the named class at the head, and the
 * input object specified by the first argument at the tail. Build any
 * intervening links required to construct the chain.
 */


/*  Locate a file representation object by name
 *
 */


/*  Define a new file representation object
 *
 */


/* Define a FileRepresentation callback function
 *
 */


/* List inseration point */


/*
 *  Erase string data
 */


/* adix_str_hash - case sensitive string hash
 *
 */


/*
 * Scan a (name,value) list for a specified string. This procedure takes
 * a char * and a string length. If the name string is an ADI string then
 * the tblx_scani routine should be used as it offers efficiency gains.
 *
 *  head	- head of a (name,value) list
 *  str,slen	- the query name
 *  *sptr	- address of variable pointing the (name,value) pair if
 *		  found, otherwise the insertion point
 */


/*
 * Add a cell to a hash table/association list
 */


/*  tblx_sadd - Add entry to table if not already present
 */


/*  tblx_saddi - Add entry to table if not already present
 */


/*  tblx_add - Add entry to table, report error if already present
 */


/*FUNCTION critchi: compute critical chi square value to produce given p */


/*FUNCTION critf: compute critical F value t produce given probability */
/*ALGORITHM
	Begin with upper and lower limits for F values (maxf and minf)
	set to extremes.  Choose an f value (fval) between the extremes.
	Compute the probability of the f value.  Set minf or maxf, based
	on whether the probability is less than or greater than the
	desired p.  Continue adjusting the extremes until they are
	within F_EPSILON of each other.
*/


/*FUNCTION critz: compute critical z value to produce given probability */
/*ALGORITHM
	Begin with upper and lower limits for z values (maxz and minz)
	set to extremes.  Choose a z value (zval) between the extremes.
	Compute the probability of the z value.  Set minz or maxz, based
	on whether the probability is less than or greater than the
	desired p.  Continue adjusting the extremes until they are
	within Z_EPSILON of each other.
*/


/* Transfer data from socket to standard output
 */


/*
 * Drop one file off the end of a stream
 */


/*
 * Destroy a stream
 */


/*
 * Add a directory name to a path chain
 */


/*
 * Add an environment variable value to a path structure
 */


/*
 * Add a file to a stream
 */


/*
 * Create a new stream
 */


/*
 * Read a line from a stream into a buffer
 */


/*
 *----------------------------------------------------------------------
 *
 * Tcl_AppInit --
 *
 *	This procedure performs application-specific initialization.
 *	Most applications, especially those that incorporate additional
 *	packages, will have their own version of this procedure.
 *
 * Results:
 *	Returns a standard Tcl completion code, and leaves an error
 *	message in interp->result if an error occurs.
 *
 * Side effects:
 *	Depends on the startup script.
 *
 *----------------------------------------------------------------------
 */


/* Pid of slave process */


/*
*att++
*  Name:
*     Naxes

*  Purpose:
*     Number of Frame axes.

*  Type:
*     Public attribute.

*  Synopsis:
*     Integer, read-only.

*  Description:
*     This is a read-only attribute giving the number of axes in a
*     Frame (i.e. the number of dimensions of the coordinate space
*     which the Frame describes). This value is determined when the
*     Frame is created.

*  Applicability:
*     Frame
*        All Frames have this attribute.
*     FrameSet
*        The Naxes attribute of a FrameSet is the same as that of its
*        current Frame (as specified by the Current attribute).
*     CmpFrame
*        The Naxes attribute of a CmpFrame is equal to the sum of the
*        Naxes values of its two component Frames.
*att--
*/


/* Virtual function interfaces. */
/* ============================ */
/* These provide the external interface to the virtual functions defined by
   this class. Each simply checks the global error status and then locates and
   executes the appropriate member function, using the function pointer stored
   in the object's virtual function table (this pointer is located using the
   astMEMBER macro defined in "object.h").

   Note that the member function may not be the one defined here, as it may
   have been over-ridden by a derived class. However, it should still have the
   same interface. */


/* Special interface function implementations. */
/* ------------------------------------------- */


/**************************************************************
    DSXC_PUTIM -- Put an image (XWindows)

    alan penny           ral                       1990-02-01
  pat morris             leeds        1992 jan
*/


/*
 * resolve - check for specified file in specified directory. sets up dir,
 * following symlinks. returns zero for success, or -1 for error (with
 * errno set properly)
 */


/*  The following is my (KS) wrap-up of findx(), producing the UNIX version of
 *  GEN_EXEDIR. This is a Fortran-callable routine which a) sets up a call to
 *  findx() to get the name of the 'exe' directory, b) manipulates the result
 *  slightly for aesthetic reasons and to make sure the result ends with a
 *  '/' character, and c) returns it in the Fortran character string
 *  DIRECTORY. The manipulation of the string returned by findx() is because
 *  the findx() algorithm tends to produce strings such as '/home/aatssb/ks/.'
 *  or '/home/aatssb/ks/work/../scrap/.' which are valid but messy if the
 *  result is ever to be output.
 */


/* int
 * inet_pton(af, src, dst)
 *	convert from presentation format (which usually means ASCII printable)
 *	to network format (which is usually some kind of binary format).
 * return:
 *	1 if the address was valid for the specified address family
 *	0 if the address wasn't valid (`dst' is untouched in this case)
 *	-1 if some other error occurred (`dst' is untouched in this case, too)
 * author:
 *	Paul Vixie, 1996.
 */


/* int
 * inet_pton4(src, dst)
 *	like inet_aton() but without all the hexadecimal and shorthand.
 * return:
 *	1 if `src' is a valid dotted quad, else 0.
 * notice:
 *	does not touch `dst' unless it's returning 1.
 * author:
 *	Paul Vixie, 1996.
 */


/* int
 * inet_pton6(src, dst)
 *	convert presentation level address to network order binary form.
 * return:
 *	1 if `src' is a valid [RFC1884 2.2] address, else 0.
 * notice:
 *	(1) does not touch `dst' unless it's returning 1.
 *	(2) :: in a full address is silently ignored.
 * credit:
 *	inspired by Mark Andrews.
 * author:
 *	Paul Vixie, 1996.
 */


/*
 * Find out whether we have extra header info that should be concatenated
 * with the VMS error code information. This is important for automatically
 * generating some historical error include files that mix messgen
 * error codes with other error codes. (see e.g. CHR and IDI that have
 * __OK constants set to 0, and GWM that mixes internal C error codes with
 * public messgen codes.
 *
 * MESSGEN will look for a file in the current directory with the
 * same name as the new output file but with the string _ext suffix
 * (to indicate external data). ie CHR_ERR will look for CHR_ERR_ext
 * and chr_err.h will look for chr_err.h_ext.

 *  write_external( char * file_name, FILE * fileptr )

*/


/* Old version of slaDcmpf, priort to Pat's fix (here to allow me to
** check test cases that used to fail)
*/


/* Do the forward transformation that slaDcmpf inverts.
**
** Arg vector is xz, yz, xs, ys, perp, orient.
** Replace with a, b, c, d, e, f.
*/


/* Externally visible functions. */
/* ============================= */
/* These implement the "grf" interface in terms of the local C interface
   to PGPLOT. */


/* Local Functions. */
/* ================ */
/* These implement the local C interface to PGPLOT in terms of its
   native Fortran interface. Only those PGPLOT functions used within
   this module are included. */


/* Handle SIGCHLD signals. */
/* ----------------------- */
/* N.B. SIGCHLD signals must be blocked during execution of this function. */


/* Look up a task in the active task list. */
/* --------------------------------------- */


/* Create a new task entry in the active task list. */
/* ------------------------------------------------ */


/* Remove a task from the active task list. */
/* ---------------------------------------- */


/* Kill a task and return immediately (without waiting). */
/* ----------------------------------------------------- */


/* Wait for a killed task to terminate. */
/* ------------------------------------ */


/* Initialise facilities to handle task termination and closedown. */
/* --------------------------------------------------------------- */


/* Initialise the ADAM message system. */
/* ----------------------------------- */


/* Load a slave task and wait for loading to complete. */
/* --------------------------------------------------- */


/* Close down attached tasks as part of master process termination. */
/* ---------------------------------------------------------------- */


/* Kill a slave task and wait (indefinitely) for it to terminate. */
/* -------------------------------------------------------------- */


/* Flush pending error messages. */
/* ----------------------------- */


/************************************************************************/
/* C  version of Clive Page's SUBROUTINE GRXHSV, to convert red, green, */
/* blue to hue, sat, val (from algorithm in Foley & van Dam's           */
/* "Fundamentals of Interactive Graphics", p615).                       */
/************************************************************************/


/************************************************************************/
/*  returns max of three reals                                          */
/************************************************************************/


/************************************************************************/
/*  returns min of three reals                                          */
/************************************************************************/


/************************************************************************/
/*  Get various parameters, including number of output pixels per row,  */
/*  which is then output.                                               */
/************************************************************************/


/************************************************************************/
/* Generates the LJ250 representation of a row of pixels from the screen*/
/************************************************************************/


/************************************************************************/
/* just resets the plane0/1/2 arrays to zero                            */
/************************************************************************/


/************************************************************************/
/*  Get run-length-encoded plane, and output whichever is most compact. */
/************************************************************************/


/************************************************************************/
/* create the run-length-encoded version of array plane                 */
/************************************************************************/


/************************************************************************/
/*  Output plane i (bit i of every pixel in a given row).               */
/************************************************************************/


/*+   TKADAM_PROCESSMESSAGE - process a message */


/*+   TKADAM_GETREPLY - receive a message on specified path and messid */


/*+   TCLADAM_INIT - initialise tcladam */


/*+   TKADAM_RECEIVE - receive an adam message */


/*+   TKADAM_REPLY - send an adam reply message */


/*+   TKADAM_SEND - send an adam message */


/*+   TKADAM_START - initialise tkadam */


/*+   TKADAM_PATH - get a path to a task */


/*+   TKADAM_STRTOCONT - convert a string to a context number */


/*+   TCLADAM_STRTOSTATUS - convert a string to a status number */


/*+   TKNBS_INIT - initialise nbs commands */


/*=   TKNBS_CMD - execute the tclnbs command */


/*=  TKNBS_FINDNBS - find an item in a noticeboard */


/*=   TKNBS_GET - copy data from NBS to tcl string */


/*=  TKNBS_GETNBS - get a value from NBS */


/*=  TKNBS_MAPNBS - map a noticeboard */


/*=   TKNBS_PUT - copy data into NBS */


/*=  TKNBS_PUTNBS - put a value into NBS */


/*=   TKNBS_INFO - get info on nbs item */


/*=   TKNBS_CLEAR - clear the monitor list */


/*=   TKNBS_MONITOR - add an item to the monitor list */


/*=   TKNBS_MONINFO - return the monitor list */


/*=   TKNBS_SCAN - copy data from NBS to tcl variables */


/*
 *--------------------------------------------------------------
 *
 * GwmWidgetCmd --
 *
 *	This procedure is invoked to process the Tcl command
 *	that corresponds to a widget managed by this module.
 *	See the user documentation for details on what it does.
 *
 * Results:
 *	A standard Tcl result.
 *
 * Side effects:
 *	See the user documentation.
 *
 *--------------------------------------------------------------
 */


/*
 *----------------------------------------------------------------------
 *
 * GwmConfigure --
 *
 *	This procedure is called to process an argv/argc list in
 *	conjunction with the Tk option database to configure (or
 *	reconfigure) a gwm widget.
 *
 * Results:
 *	The return value is a standard Tcl result.  If TCL_ERROR is
 *	returned, then interp->result contains an error message.
 *
 * Side effects:
 *	Configuration information, such as colors, border width,
 *	etc. get set for gwPtr;  old resources get freed,
 *	if there were any.
 *
 *----------------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * GwmEventProc --
 *
 *	This procedure is invoked by the Tk dispatcher for various
 *	events on gwm widgets.
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	When the window gets deleted, internal structures get
 *	cleaned up.  When it gets exposed, it is redisplayed.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * GwmDisplay --
 *
 *	This procedure redraws the contents of a gwm window.
 *	It is invoked as a do-when-idle handler, so it only runs
 *	when there's nothing else for the application to do.
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	Information appears on the screen.
 *
 *--------------------------------------------------------------
 */


/*
 *----------------------------------------------------------------------
 *
 * GwmDestroy --
 *
 *	This procedure is invoked by Tcl_EventuallyFree or Tcl_Release
 *	to clean up the internal structure of a gwm at a safe time
 *	(when no-one is using it anymore).
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	Everything associated with the gwm is freed up.
 *
 *----------------------------------------------------------------------
 */


/*
 *----------------------------------------------------------------------
 *
 * Clear --
 *
 *	This procedure clears the gwm window. It is called by the
 *      widget clear command
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	The Gwm window is cleared
 *
 *----------------------------------------------------------------------
 */


/*
 *----------------------------------------------------------------------
 *
 * OvClear --
 *
 *	This procedure clears the gwm window overlay plane. It is
 *      called by the widget ovclear command
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	The Gwm overlay is cleared
 *
 *----------------------------------------------------------------------
 */


/* Issue a helpful message if required. Used when getting the details of
 * a custom filter.
 */


/*+
* retstringarray
*
* Purpose:
*    To return space allocated by getstringarray.
*
* Invovcation:
*    Call from C
*       retstringarray( carr );
*
* Arguments:
*    carr = **char
*       A pointer to an array of pointers to char
*
* Description:
*    Frees the memory pointed at by the first element of the given array,
*    carr, then frees the array itself.
*-
*/


/* Private functions to print a report line to standard output, and also
   store it in a KeyMap. */


/* Compare two character attributes of a Frame. */


/* Get a string from the environment, and extract a numerical value
   and qualifying character (V, R or A) from it. */


/* Find the number of bad values in an array component of an NDF. */


/* Return a KeyMap containing the QUality Names found in an NDF. */


/* Return a KeyMap containing the root ancestors of an NDF. */


/* Return the number of pixels that have different Quality values in the
   two NDFs. "*nel" is returned holding the total number of pixels in the
   second NDF. */


/* Find the largest difference in pixel value. */


/*
 * Process an NDF history element and construct a KeyMay.
 *
 * This is intended as a handler routine for use with ndfHout,
 * it reads the supplied text and sets the global historyConfig
 * variable.
 */


/*
** Return a pointer to the Nth HtmlElement in the list.  If there
** is no Nth element, return 0 if flag==0 and return either the first
** or last element (whichever is closest) if flag!=0
*/


/*
** Return the token number for the given HtmlElement
*/


/*
** Find the maximum index for the given token
*/


/*
** Given a Block and an x coordinate, find the Index of the character
** that is closest to the given x coordinate.
**
** The x-coordinate might specify a point to the left of the block,
** in which case the procedure returns the first token and a character
** index of 0.  Or the x-coordinate might specify a point to the right
** of the block, in which case the last token is returned with an index
** equal to its last character.
*/


/*
** Convert an Element-based index into a Block-based index.
**
** In other words, given a pointer to an element and an index
** of a particular character within that element, compute a
** pointer to the HtmlBlock used to display that character and
** the index in the HtmlBlock of the character.
*/


/*
** Given a base index name (without any modifiers) return a pointer
** to the token described, and the character within that token.
**
** Valid input forms include:
**
**       N.M          Token number N (with numbering starting at 1) and
**                    character number M (with numbering starting at 0).
**
**       end          The end of all text
**
**       N.last       Last character of token number N.
**
**       sel.first    First character of the selection.
**
**       sel.last     Last character of the selection.
**
**       ins          The character holding the insertion cursor.
**
**       @X,Y         The character a location X,Y of the clipping window.
**
** Zero is returned if we are successful and non-zero if there is
** any kind of error.
**
** If the given token doesn't exist (for example if there are only 10
** tokens and 11.5 is requested) then *ppToken is left pointing to NULL.
** But the function still returns 0 for success.
*/


/*
** This routine decodes a complete index specification.  A complete
** index consists of the base specification followed by modifiers.
*/


/* Hash a escape sequence name.  The value returned is an integer
** between 0 and ESC_HASH_SIZE-1, inclusive.
*/


/*
** Compute the longest and average collision chain length for the
** escape sequence hash table
*/


/* Initialize the escape sequence hash table
*/


/* Hash a markup name
**
** HTML markup is case insensitive, so this function will give the
** same hash regardless of the case of the markup name.
**
** The value returned is an integer between 0 and HTML_MARKUP_HASH_SIZE-1,
** inclusive.
*/


/*
** Compute the longest and average collision chain length for the
** markup hash table
*/


/*
** Append the given HtmlElement to the tokenizers list of elements
*/


/*
** Compute the new column index following the given character.
*/


/*
** Convert a string to all lower-case letters.
*/


/* Process as much of the input HTML as possible.  Construct new
** HtmlElement structures and appended them to the list.  Return
** the number of characters actually processed.
**
** This routine may invoke a callback procedure which could delete
** the HTML widget.
**
** This routine is not reentrant for the same HTML widget.  To
** prevent reentrancy (during a callback), the p->iCol field is
** set to a negative number.  This is a flag to future invocations
** not to reentry this routine.  The p->iCol field is restored
** before exiting, of course.
*/


/*
** Append text to the tokenizer engine.
**
** This routine (actually the Tokenize() subroutine that is called
** by this routine) may invoke a callback procedure which could delete
** the HTML widget.
*/


/*
** This routine takes a text representation of a token, converts
** it into an HtmlElement structure and inserts it immediately
** prior to pToken.  If pToken==0, then the newly created HtmlElement
** is appended.
**
** This routine does nothing to resize, restyle, relayout or redisplay
** the HTML.  That is the calling routines responsibility.
**
** Return 0 if successful.  Return non-zero if zType is not a known
** markup name.
*/


/*
** Convert a markup name into a type integer
*/


/*
** Convert a type into a symbolic name
*/


/*
** For debugging purposes, print information about a token
*/


/*
** Return all tokens between the two elements as a Tcl list.
*/


/*
** Find the alignment for an image
*/


/*
** This routine is called when an image changes.  If the size of the
** images changes, then we need to completely redo the layout.  If
** only the appearance changes, then this works like an expose event.
*/


/*
** Append all the arguments of the given markup to the given
** DString.
**
** Example:  If the markup is <IMG SRC=image.gif ALT="hello!">
** then the following text is appended to the DString:
**
**       "src image.gif alt hello!"
**
** Notice how all attribute names are converted to lower case.
** This conversion happens in the parser.
*/


/*
** Given an <IMG> markup, find or create an appropriate HtmlImage
** structure and return a pointer to that structure.  NULL might
** be returned.
**
** This routine may invoke a callback procedure which could delete
** the HTML widget.  Use HtmlLock() if necessary to preserve the
** widget structure.
*/


/*
** Get the current rendering style.  In other words, get the style
** that is currently on the top of the style stack.
*/


/*
** Push a new rendering style onto the stack.
*/


/*
** Pop a rendering style off of the stack.
**
** The top-most style on the stack should have a tag equal to "tag".
** If not, then we have an HTML coding error.  Perhaps something
** like this:  "Some text Enphasized more text".  It is an
** interesting problem to figure out how to respond sanely to this
** kind of error.  Our solution it to keep popping the stack until
** we find the correct tag, or until the stack is empty.
*/


/*
** Change the font size on the given style by the delta-amount given
*/


/*
** Lookup an argument in the given markup with the name given.
** Return a pointer to its value, or the given default
** value if it doesn't appear.
*/


/*
** Return an alignment or justification flag associated with the
** given markup.  The given default value is returned if no alignment is
** specified.
*/


/*
** The "type" argument to the given element might describe the type
** for an ordered list.  Return the corresponding LI_TYPE_* entry
** if this is the case, or the default value if it isn't.
*/


/*
** The "type" argument to the given element might describe a type
** for an unordered list.  Return the corresponding LI_TYPE entry
** if this is the case, or the default value if it isn't.
*/


/*
** Add the STY_Invisible style to every token between pFirst and pLast.
*/


/*
** For the markup <a href=XXX>, find out if the URL has been visited
** before or not.  Return COLOR_Visited or COLOR_Unvisited, as
** appropriate.
**
** This routine may invoke a callback procedure which could delete
** the HTML widget.  The calling function should call HtmlLock()
** if it needs the widget structure to be preserved.
*/


/*
** This routine adds information to the input texts that doesn't change
** when the display is resized or when new fonts are selected, etc.
** Mostly this means adding style attributes.  But other constant
** information (such as numbering on <li> and images used for <IMG>)
** is also obtained.  The key is that this routine is only called
** once, where the sizer and layout routines can be called many times.
**
** This routine is called whenever the list of elements grows.  The
** style stack is stored as part of the HTML widget so that we can
** always continue where we left off the last time.
**
** In addition to adding style, this routine will invoke callbacks
** needed to acquire information about a markup.  The htmlPtr->zIsVisitied
** callback is called for each <a> and the htmlPtr->zGetImage is called
** for each <IMG> or for each <LI> that has a SRC= field.
**
** This routine may invoke a callback procedure which could delete
** the HTML widget.
**
** When a markup is inserted or deleted from the token list, the
** style routine must be completely rerun from the beginning.  So
** what we said above, that this routine is only run once, is not
** strictly true.
*/


/*
** Compute the size of all elements in the widget.  Assume that a
** style has already been assigned to all elements.
**
** Some of the elements might have already been sized.  Refer to the
** htmlPtr->lastSized and only compute sizes for elements that follow
** this one.  If htmlPtr->lastSized==0, then size everything.
**
** This routine only computes the sizes of individual elements.  The
** size of aggregate elements (like tables) are computed separately.
**
** The HTML_Visible flag is also set on every element that results
** in ink on the page.
**
** This routine may invoke a callback procedure which could delete
** the HTML widget.
*/


/*
** Unmap any input control that is currently mapped.
*/


/*
** Map any control that should be visible according to the
** current scroll position.  At the same time, if any controls that
** should not be visible are mapped, unmap them.  After this routine
** finishes, all <INPUT> controls should be in their proper places
** regardless of where they might have been before.
**
** Return the number of controls that are currently visible.
*/


/*
** Delete all input controls.  This happens when the HTML widget
** is cleared.
**
** When the TCL "exit" command is invoked, the order of operations
** here is very touchy.
*/


/*
** Return an appropriate type value for the given <INPUT> markup.
*/


/*
** Create the window name for a child widget.  Space to hold the name
** is obtained from HtmlAlloc() and must be freed by the calling function.
*/


/*
** A Input element is the input.  Mark this element as being
** empty.  It has no widget and doesn't appear on the screen.
**
** This is called for HIDDEN inputs or when the -formcommand
** callback doesn't create the widget.
*/


/*
** This routine is called when one of the child windows for a form
** wants to change its size.
*/


/*
** This routine is called when another entity takes over geometry
** management for a widget corresponding to an input element.
*/


/*
** This routine catches DestroyNotify events on a INPUT window so
** that we will know the window is been deleted.
*/


/*
** zWin is the name of a child widget that is used to implement an
** input element.  Query Tk for information about this widget (such
** as its size) and put that information in the pElem structure
** that represents the input.
*/


/* Append all text and space tokens between pStart and pEnd to
** the given Tcl_DString.
*/


/*
** The "p" argument points to a <select>.  This routine scans all
** subsequent elements (up to the next </select>) looking for
** <option> tags.  For each option tag, it appends three elements
** to the "str" DString:
**
**     *        1 or 0 to indicated whether or not the element is
**              selected.
**
**     *        The value returned if this element is selected.
**
**     *        The text displayed for this element.
*/


/*
** This routine implements the Sizer() function for <INPUT>,
** <SELECT> and <TEXTAREA> markup.
**
** A side effect of sizing these markups is that widgets are
** created to represent the corresponding input controls.
**
** The function normally returns 0.  But if it is dealing with
** a <SELECT> or <TEXTAREA> that is incomplete, 1 is returned.
** In that case, the sizer will be called again at some point in
** the future when more information is available.
*/


/*
** Append to the given DString, an encoded version of the given
** text.
*/


/*
** Allocate a new HtmlBlock structure.
*/


/*
** Free an HtmlBlock structure.  Assume that it is already unlinked
** from the element list and the block list.
*/


/*
** Destroy the given Block after first unlinking it from the
** element list.  Note that this unlinks the block from the
** element list only -- not from the block list.
*/


/*
** Append a block to the block list and insert the block into the
** element list immediately prior to the element given.
*/


/*
** Print an ordered list index into the given buffer.  Use numbering
** like this:
**
**     A  B  C ... Y Z AA BB CC ... ZZ
**
** Revert to decimal for indices greater than 52.
*/


/*
** Print an ordered list index into the given buffer.  Use roman
** numerals.  For indices greater than a few thousand, revert to
** decimal.
*/


/* Draw the selection background for the given block
*/


/*
** Draw a rectangle.  The rectangle will have a 3-D appearance if
** flat==0 and a flat appearance if flat==1.
**
** We don't use Tk_Draw3DRectangle() because it doesn't work well
** when the background color is close to pure white or pure black.
*/


/*
** Display a single HtmlBlock.  This is where all the drawing
** happens.
*/


/*
** Draw all or part of an image.
*/


/*
** Recompute the following fields of the given block structure:
**
**    base.count         The number of elements described by this
**                       block structure.
**
**    n                  The number of characters of text output
**                       associated with this block.  If the block
**                       renders something other than text (ex: <IMG>)
**                       then set n to 0.
**
**    z                  Pointer to malloced memory containing the
**                       text associated with this block.  NULL if
**                       n is 0.
**
** Return a pointer to the first HtmlElement not covered by the
** block.
*/


/*
** Scan ahead looking for a place to put a block.  Return a pointer
** to the element which should come immediately after the block.
**
** if pCnt!=0, then put the number of elements skipped in *pCnt.
*/


/*
** Add additional blocks to the block list in order to cover
** all elements on the element list.
**
** If any old blocks are found on the element list, they must
** be left over from a prior rendering.  Unlink and delete them.
*/


/*
** Find the width of the usable drawing area in pixels.  If the window isn't
** mapped, use the size requested by the user.
**
** The usable drawing area is the area available for displaying rendered
** HTML.  The usable drawing area does not include the 3D border or the
** padx and pady boundry within the 3D border.  The usable drawing area
** is the size of the clipping window.
*/


/*
** Find the height of the usable drawing area in pixels.  If the window isn't
** mapped, use the size requested by the user.
**
** The usable drawing area is the area available for displaying rendered
** HTML.  The usable drawing area does not include the 3D border or the
** padx and pady boundry within the 3D border.  The usable drawing area
** is the size of the clipping window.
*/


/*
** Compute a pair of floating point numbers that describe the current
** vertical scroll position.  The first number is the fraction of
** the document that is off the top of the visible region and the second
** number is the fraction that is beyond the end of the visible region.
*/


/*
** Do the same thing for the horizontal direction
*/


/*
** Clear the cache of GCs
*/


/*
** This routine is called when the widget command is deleted.  If the
** widget isn't already in the process of being destroyed, this command
** starts that process rolling.
**
** This routine can be called in two ways.
**
**   (1) The window is destroyed, which causes the command to be deleted.
**       In this case, we don't have to do anything.
**
**   (2) The command only is deleted (ex: "rename .html {}").  In that
**       case we need to destroy the window.
*/


/*
** Reset the main layout context in the main widget.  This happens
** before we redo the layout, or just before deleting the widget.
*/


/*
** This routine is invoked in order to redraw all or part of the HTML
** widget.  This might happen because the display has changed, or in
** response to an expose event.  In all cases, though, this routine
** is called by an idle callback.
*/


/*
** Make sure that a call to the HtmlRedrawCallback() routine has been
** queued.
*/


/*
** If any part of the screen needs to be redrawn, Then call this routine
** with the values of a box (in window coordinates) that needs to be
** redrawn.  This routine will make sure an idle callback is scheduled
** to do the redraw.
**
** The box coordinates are relative to the clipping window (clipwin),
** not the main window (tkwin).
*/


/* Redraw the HtmlBlock given.
*/


/*
** Call this routine to force the entire widget to be redrawn.
*/


/*
** Call this routine to cause all of the rendered HTML at the
** virtual canvas coordinate of Y and beyond to be redrawn.
*/


/*
** Recalculate the preferred size of the html widget and pass this
** along to the geometry manager.
*/


/*
** This routine is called in order to process a "configure" subcommand
** on the given html widget.
*/


/*
** Delete a single HtmlElement
*/


/*
** Erase all data from the HTML widget.  Bring it back to an
** empty screen.
**
** This happens (for example) when the "clear" method is invoked
** on the widget, or just before the widget is deleted.
*/


/*
** This routine attempts to delete the widget structure.  But it won't
** do it if the widget structure is locked.  If the widget structure is
** locked, then when HtmlUnlock() is called and the lock count reaches
** zero, this routine will be called to finish the job.
*/


/*
** Remove a lock from the HTML widget.  If the widget has been
** deleted, then delete the widget structure.  Return 1 if the
** widget has been deleted.  Return 0 if it still exists.
**
** Normal Tk code (that is to say, code in the Tk core) uses
** Tcl_Preserve() and Tcl_Release() to accomplish what this
** function does.  But preserving and releasing are much more
** common in this code than in regular widgets, so this routine
** was invented to do the same thing easier and faster.
*/


/*
** This routine checks to see if an HTML widget has been
** destroyed.  It is always called after calling HtmlLock().
**
** If the widget has been destroyed, then the structure
** is unlocked and the function returns 1.  If the widget
** has not been destroyed, then the structure is not unlocked
** and the routine returns 0.
**
** This routine is intended for use in code like the following:
**
**     HtmlLock(htmlPtr);
**     // Do something that might destroy the widget
**     if( HtmlIsDead(htmlPtr) ) return;
**     // Do something that might destroy the widget
**     if( HtmlIsDead(htmlPtr) ) return;
**     // Do something that might destroy the widget
**     if( HtmlUnlock(htmlPtr) ) return;
*/


/*
** Flash the insertion cursor.
*/


/*
** Return a GC from the cache.  As many as N_CACHE_GCs are kept valid
** at any one time.  They are replaced using an LRU algorithm.
**
** A value of FONT_Any (-1) for the font means "don't care".
*/


/*
** Retrieve any valid GC.  The font and color don't matter since the
** GC will only be used for copying.
*/


/*
** All window events (for both tkwin and clipwin) are
** sent to this routine.
*/


/*
** The rendering and layout routines should call this routine in order to get
** a font structure.  The iFont parameter specifies which of the N_FONT
** fonts should be obtained.  The font is allocated if necessary.
**
** Because the -fontcommand callback can be invoked, this function can
** (in theory) cause the HTML widget to be changed arbitrarily or even
** deleted.  Callers of this function much be prepared to be called
** recursively and/or to have the HTML widget deleted out from under
** them.  This routine will return NULL if the HTML widget is deleted.
*/


/*
** Compute the squared distance between two colors
*/


/*
** This routine returns an index between 0 and N_COLOR-1 which indicates
** which XColor structure in the apColor[] array of htmlPtr should be
** used to describe the color specified by the given name.
*/


/*
** Check to see if the given color is too dark to be easily distinguished
** from black.
*/


/*
** Given that the background color is iBgColor, figure out an
** appropriate color for the dark part of a 3D shadow.
*/


/*
** Given that the background color is iBgColor, figure out an
** appropriate color for the bright part of the 3D shadow.
*/


/*
** This routine searchs for a hyperlink beneath the coordinates x,y
** and returns a pointer to the HREF for that hyperlink.  The text
** is held one of the markup.argv[] fields of the <a> markup.
*/


/*
** Change the "yOffset" field from its current value to the value given.
** This has the effect of scrolling the widget vertically.
*/


/*
** Change the "xOffset" field from its current value to the value given.
** This has the effect of scrolling the widget horizontally.
*/


/*
** This routine implements the command used by individual HTML widgets.
*/


/*
** The following routine implements the Tcl "html" command.  This command
** is used to create new HTML widgets only.  After the widget has been
** created, it is manipulated using the widget command defined above.
*/


/*
** WIDGET resolve ?URI ...?
**
** Call the TCL command specified by the -resolvercommand option
** to resolve the URL.
*/


/*
** WIDGET cget CONFIG-OPTION
**
** Retrieve the value of a configuration option
*/


/*
** WIDGET clear
**
** Erase all HTML from this widget and clear the screen.  This is
** typically done before loading a new document.
*/


/*
** WIDGET configure ?OPTIONS?
**
** The standard Tk configure command.
*/


/*
** WIDGET href X Y
**
** Returns the URL on the hyperlink that is beneath the position X,Y.
** Returns {} if there is no hyperlink beneath X,Y.
*/


/*
** WIDGET names
**
** Returns a list of names associated with <a name=...> tags.
*/


/*
** WIDGET parse HTML
**
** Appends the given HTML text to the end of any HTML text that may have
** been inserted by prior calls to this command.  Then it runs the
** tokenizer, parser and layout engine as far as possible with the
** text that is available.  The display is updated appropriately.
*/


/*
** WIDGET xview ?SCROLL-OPTIONS...?
**
** Implements horizontal scrolling in the usual Tk way.
*/


/*
** WIDGET yview ?SCROLL-OPTIONS...?
**
** Implements vertical scrolling in the usual Tk way, but with one
** enhancement.  If the argument is a single word, the widget looks
** for a <a name=...> tag with that word as the "name" and scrolls
** to the position of that tag.
*/


/*
** WIDGET index INDEX
*/


/* The pSelStartBlock and pSelEndBlock values have been changed.
** This routine's job is to loop over all HtmlBlocks and either
** set or clear the HTML_Selected bits in the .base.flags field
** as appropriate.  For every HtmlBlock where the bit changes,
** mark that block for redrawing.
*/


/* Given the selection end-points in htmlPtr->selBegin
** and htmlPtr->selEnd, recompute pSelBeginBlock and
** pSelEndBlock, then call UpdateSelection to update the
** display.
**
** This routine should be called whenever the selection
** changes or whenever the set of HtmlBlock structures
** change.
*/


/*
** WIDGET selection set INDEX INDEX
*/


/*
** WIDGET selection clear
*/


/*
** Recompute the position of the insertion cursor based on the
** position in htmlPtr->ins.
*/


/*
** WIDGET insert INDEX
*/


/*
** WIDGET token list START END
*/


/*
** WIDGET debug dump START END
*/


/*
** WIDGET debug testpt FILENAME
*/


/* This function is called to print the values of all elements of the
** TP_Array to the given file.  Values are printed in decimal, one per line.
*/


/* This function reports an error to stderr when code that is marked
** UNTESTED gets executed.
*/


/* This function reports an error to stderr when safety code that should
** never execute is called.
*/


/*
** Push a new margin onto the given margin stack.
**
** If the "bottom" parameter is non-negative, then this margin will
** automatically expire for all text that is placed below the y-coordinate
** given by "bottom".  This feature is used for
** and  kinds of markup.  It allows text to flow around
** an image.
**
** If "bottom" is negative, then the margin stays in force until
** it is explicitly canceled by a call to HtmlPopMargin().
*/


/*
** Pop one margin off of the given margin stack.
*/


/*
** Pop as many margins as necessary until the margin that was
** created with "tag" is popped off.  Update the layout context
** to move past obsticles, if necessary.
**
** If there are some margins on the stack that contain non-negative
** bottom fields, that means there are some obsticles that we have
** not yet cleared.  If these margins get popped off the stack,
** then we have to be careful to advance the pLC->bottom value so
** that the next line of text will clear the obsticle.
*/


/*
** Pop all expired margins from the stack.
**
** An expired margin is one with a non-negative bottom parameter
** that is less than the value "y".  "y" is the Y-coordinate of
** the top edge the next line of text to by positioned.  What this
** function does is check to see if we have cleared any obsticles
** (an obsticle is an  or ) and
** expands the margins if we have.
*/


/*
** Clear a margin stack to reclaim memory.  This routine just blindly
** pops everything off the stack.  Typically used when the screen is
** cleared or the widget is deleted, etc.
*/


/*
** This routine gathers as many tokens as will fit on one line.
**
** The candidate tokens begin with pStart and go thru the end of
** the list or to pEnd, whichever comes first.  The first token
** at the start of the next line is returned.  NULL is returned if
** we exhaust data.
**
** "width" is the maximum allowed width of the line.  The actual
** width is returned in *actualWidth.  The actual width does not
** include any trailing spaces.  Sometimes the actual width will
** be greater than the maximum width.  This will happen, for example,
** for text enclosed in
..
 that has lines longer than
** the width of the page.
**
** If the list begins with text, at least one token is returned,
** even if that one token is longer than the allowed line length.
** But if the list begins with some kind of break markup (possibly
** preceded by white space) then the returned list may be empty.
**
** The "x" coordinates of all elements are set assuming that the line
** begins at 0.  The calling routine should adjust these coordinates
** to position the line horizontally.  (The FixLine() procedure does
** this.)  Note that the "x" coordinate of
 elements will be negative.
** Text within
..
 might also have a negative "x" coordinate.
** But in no case will the x coordinate every be less than "minX".
*/


/*
** Set the y coordinate for every anchor in the given list
*/


/*
** This routine computes the X and Y coordinates for all elements of
** a line that has been gathered using GetLine() above.   It also figures
** the ascent and descent for in-line images.
**
** The value returned is the Y coordinate of the bottom edge of the
** new line.  The X coordinates are computed by adding the left margin
** plus any extra space needed for centering or right-justification.
*/


/*
** Increase the headroom to create a paragraph break at the current token
*/


/*
** Compute the current margins for layout.  Three values are returned:
**
**    *pY       The top edge of the area in which we can put ink.  This
**              takes into account any requested headroom.
**
**    *pX       The left edge of the inkable area.  The takes into account
**              any margin requests active at vertical position specified
**              in pLC->bottom.
**
**    *pW       The width of the inkable area.  This takes into account
**              an margin requests that are active at the vertical position
**              pLC->bottom.
**
*/


/*
** Break markup is any kind of markup that might force a line-break. This
** routine handles a single element of break markup and returns a pointer
** to the first element past that markup.  If p doesn't point to break
** markup, then p is returned.  If p is an incomplete table (a <TABLE>
** that lacks a </TABLE>), then NULL is returned.
*/


/*
** Return TRUE (non-zero) if we are currently wrapping text around
** one or more images.
*/


/*
** Move past obsticles until a linewidth of reqWidth is obtained,
** or until all obsticles are cleared.
*/


/*
** Do as much layout as possible on the block of text defined by
** the HtmlLayoutContext.
*/


/*
** Advance the layout as far as possible
*/


/*
** Return the appropriate cell spacing for the given table.
*/


/* pStart points to a <table>.  Compute the number of columns, the
** minimum and maximum size for each column and the overall minimum
** and maximum size for this table and store these value in the
** pStart structure.  Return a pointer to the </table> element,
** or to NULL if there is no </table>.
**
** The min and max size for column N (where the leftmost column has
** N==1) is pStart->minW[1] and pStart->maxW[1].  The pStart->minW[0]
** and pStart->maxW[0] entries contain the minimum and maximum widths
** of the whole table, including any cell padding, cell spacing,
** border width and "hspace".  The values of pStart->minW[I] for I>=1
** do not contain any cell padding, cell spacing or border width.
** Only pStart->minW[0] contains these extra spaces.
**
** The back references from </table>, </tr>, </td> and </th> back to
** the <table> markup are also filled in.  And for each <td> and <th>
** markup, the pTable and pEnd fields are set to their proper values.
*/


/*
** Given a list of elements, compute the minimum and maximum width needed
** to render the list.  Stop the search at the first element seen that is
** in the following set:
**
**       <tr>  <td>  <th>  </tr>  </td>  </th>  </table>
**
** Return a pointer to the element that stopped the search, or to NULL
** if we ran out of data.
**
** Sometimes the value returned for both min and max will be larger than
** the true minimum and maximum.  This is rare, and only occurs if the
** element string contains figures with flow-around text.
*/


/*
** Return the vertical alignment specified by the given element.
*/


/* Do all layout for a single table.  Return the </table> element or
** NULL if the table is unterminated.
*/


/*
** Move all elements in the given list vertically by the amount dy
*/


/*
** Return the length of the next component of the URL in z[] given
** that the component starts at z[0].  The initial sequence of the
** component must be zInit[].  The component is terminated by any
** character in zTerm[].  The length returned is 0 if the component
** doesn't exist.  The length includes the zInit[] string, but not
** the termination character.
**
**        Component        zInit      zTerm
**        ----------       -------    -------
**        scheme           ""         ":/?#"
**        authority        "//"       "/?#"
**        path             "/"        "?#"
**        query            "?"        "#"
**        fragment         "#"        ""
*/


/*
** Duplicate a string of length n.
*/


/*
** Parse a text URI into an HtmlUri structure.
*/


/*
** Delete an HtmlUri structure.
*/


/*
** Create a string to hold the given URI.  Memory to hold the string
** is obtained from HtmlAlloc() and must be freed by the calling
** function.
*/


/*
** Replace the string in *pzDest with the string in zSrc
*/


/*
** Remove leading and trailing spaces from the given string.  Return
** a new string obtained from HtmlAlloc().
*/


/*
** The input azSeries[] is a sequence of URIs.  This command must
** resolve them all and put the result in the interp->result field
** of the interpreter associated with the HTML widget.  Return
** TCL_OK on success and TCL_ERROR if there is a failure.
**
** This function can cause the HTML widget to be deleted or changed
** arbitrarily.
*/


/*
** This is a convenient wrapper routine for HtmlCallResolver.
** It makes a copy of the result into memory obtained from HtmlAlloc()
** and invokes Tcl_ResetResult().
*/


/* External interface functions. */
/* ============================= */
/* These implement the "grf" interface in terms of Tk canvas
   primitives and add the necessary initialisation functions. */


/*
 *+
 *  Name:
 *     astTk_SetCanvas

 *  Purpose:
 *     Re-establishes the canvas used to draw the graphics.

 *  Synopsis:
 *     #include "grf_tkcan.h"
 *     int astTk_SetCanvas( const char *thecanvas )

 *  Description:
 *      This routine sets the name of the canvas used to draw and
 *      display the graphics. It may be invoked after astTk_Init
 *      to change the canvas used to draw graphics.

 *  Parameters:
 *     const char *thecanvas
 *        The Tk name of the canvas (i.e. that returned by the
 *        "canvas" command).

 *  Returned Value:
 *     A value of 0 is returned if an error occurs, and 1 is returned
 *     otherwise.

 *-
 */


/*  Graphics buffering is not supported. */


/**
 * Register all the array commands.
 */


/*
 *  Copy a part of an image into workspace
 */


/*
 *  Copy workspace back into an image.
 */


//  Clear the cached STC mapping. Do this for new catalogues.


/*
 *--------------------------------------------------------------
 * RtdSegmentCreate --
 *
 *    Create an "instance" for indirect use.
 *
 *    Returns a Tk_Item pointer, which can then be used in
 *    conjunction with another item that is directly managed
 *    by a canvas. All arguments except itemPtr are as passed to the
 *    CreateLine function.
 *
 *--------------------------------------------------------------
 *
 */


/*
 *--------------------------------------------------------------
 * RtdSegmentDelete --
 *
 *    Delete an "instance" created for indirect use.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * CreateLine --
 *
 *      This procedure is invoked to create a new line item in
 *      a canvas.
 *
 * Results:
 *      A standard Tcl return value.  If an error occurred in
 *      creating the item, then an error message is left in
 *      interp->result;  in this case itemPtr is left uninitialized,
 *      so it can be safely freed by the caller.
 *
 * Side effects:
 *      A new line item is created.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * LineCoords --
 *
 *      This procedure is invoked to process the "coords" widget
 *      command on lines.  See the user documentation for details
 *      on what it does.
 *
 * Results:
 *      Returns TCL_OK or TCL_ERROR, and sets interp->result.
 *
 * Side effects:
 *      The coordinates for the given item may be changed.
 *
 * Notes:
 *      This procedure is extended from the usual canvas coords
 *      command. If the first word is "add" then the list of
 *      coordinates that follow are added to the current list rather
 *      than replacing them as usual. This allows new segments to be
 *      added to an existing canvas item.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ConfigureLine --
 *
 *      This procedure is invoked to configure various aspects
 *      of a line item such as its background color.
 *
 * Results:
 *      A standard Tcl result code.  If an error occurs, then
 *      an error message is left in interp->result.
 *
 * Side effects:
 *      Configuration information, such as colors and stipple
 *      patterns, may be set for itemPtr.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DeleteLine --
 *
 *      This procedure is called to clean up the data structure
 *      associated with a line item.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      Resources associated with itemPtr are released.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ComputeLineBbox --
 *
 *      This procedure is invoked to compute the bounding box of
 *      all the pixels that may be drawn as part of a line.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The fields x1, y1, x2, and y2 are updated in the header
 *      for itemPtr.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdSegmentDisplay --
 *
 *      This procedure is invoked to draw a line item in a given
 *      drawable.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      ItemPtr is drawn in drawable using the transformation
 *      information in canvas.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ScaleLine --
 *
 *      This procedure is invoked to rescale a line item.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The line referred to by itemPtr is rescaled so that the
 *      following transformation is applied to all point
 *      coordinates:
 *              x' = originX + scaleX*(x-originX)
 *              y' = originY + scaleY*(y-originY)
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * TranslateLine --
 *
 *      This procedure is called to move a line by a given amount.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The position of the line is offset by (xDelta, yDelta), and
 *      the bounding box is updated in the generic part of the item
 *      structure.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdSegmentToPostscript --
 *
 *      This procedure is called to generate Postscript for
 *      line items.
 *
 * Results:
 *      The return value is a standard Tcl result.  If an error
 *      occurs in generating Postscript then an error message is
 *      left in interp->result, replacing whatever used
 *      to be there.  If no error occurs, then Postscript for the
 *      item is appended to the result.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ArrowheadPostscript --
 *
 *      This procedure is called to generate Postscript for
 *      an arrowhead for a line item.
 *
 * Results:
 *      The return value is a standard Tcl result.  If an error
 *      occurs in generating Postscript then an error message is
 *      left in interp->result, replacing whatever used
 *      to be there.  If no error occurs, then Postscript for the
 *      arrowhead is appended to the result.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdSegmentSetCoords --
 *
 *      This procedure is called to set and reset the item coordinates,
 *      without the need to parse a string.
 *
 * Side effects:
 *      The coordinates for the given item will be changed.
 *
 * Notes:
 *      This procedure is non-standard. It provides a speedy way to
 *      set the coordinates of this item. The problems are that the
 *      canvas name and item are not available and are recorded from
 *      the last create command, so this should be called immediately
 *      after the create command and at no other time.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdSegmentQuickSetCoords --
 *
 *      This procedure is called to set the item coordinates,
 *      without the need to parse a string.
 *
 * Side effects:
 *      The coordinates for the given item will be changed.
 *
 * Notes:
 *      Version of RtdSegmentSetCoords, if you have the item
 *      and canvas.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DashParseProc --
 *
 *      This procedure is called back during option parsing to
 *      parse the -dash option.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DashPrintProc --
 *
 *      This procedure is a callback invoked by the configuration
 *      code to return a printable value describing a dash.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/* Register functions that will be called, note only one set allowed */


/**
 * Register all the NDF access commands.
 */


/*
 * Import an NDF back from a Tcl_Obj. Returns TCL_ERROR if fails.
 */


/**
 * Export an NDF identifier and return an NDFinfo struct.
 */


/**
 * Query the equivalent world coordinate of a pixel coordinate along the given
 * axis. Selects the PIXEL domain from the frameSet (which must therefore be
 * from an NDF) and works with that as the BASE domain.
 */


/**
 * Write a keyword value comment set into a FITS channel. The type
 * string should start with one of "c" or "n", for character or numeric.
 */


/**
 * SpectralPlot_Init --
 *
 *   This procedure initialises the spectral_plot canvas item.
 */


/**
 * SPDelete --
 *
 *      This procedure is called to clean up the data structure
 *      associated with an item.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      Resources associated with itemPtr are released.
 */


/**
 * SPDisplay --
 *
 *      This procedure is invoked to draw an item in a given drawable.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      ItemPtr is drawn in drawable, or not if an error occurs.
 */


/**
 * SPToPoint --
 *
 *      Computes the distance from a given point to the plot.
 *
 * Results:
 *      The return value is 0 if the point whose x and y coordinates
 *      are pointPtr[0] and pointPtr[1] is inside the plot.  If the
 *      point isn't inside the plot then the return value is the
 *      distance from the point to the item.
 *
 * Side effects:
 *      None.
 */


/**
 * SPToArea --
 *
 *      This procedure is called to determine whether an item
 *      lies entirely inside, entirely outside, or overlapping
 *      a given rectangular area.
 *
 * Results:
 *      -1 is returned if the item is entirely outside the area
 *      given by areaPtr, 0 if it overlaps, and 1 if it is entirely
 *      inside the given area.
 *
 * Side effects:
 *      None.
 */


/**
 * SPScale --
 *
 *      This procedure is invoked to scale an item. If the arguments are
 *      set to -1, then factors that fill the canvas will be used. Scaling
 *      can also be inhibited by setting the fixedscale option to 1.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The item referred to by itemPtr is rescaled
 *              x' = originX + scaleX*(x-originX)
 *              y' = originY + scaleY*(y-originY)
 *      This just moves the origin wrt to the scale.
 */


/**
 * SPTranslate --
 *
 *      This procedure is called to move an item by a given amount.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The position of the item is offset by (xDelta, yDelta), and
 *      the bounding box is updated in the generic part of the item structure.
 */


/**
 * SPToPostscript --
 *
 *      This procedure is called to generate Postscript for the item.
 *
 * Results:
 *      Most of the drawing will be done by the AST components which the
 *      canvas should manage. We need to get the polylines to draw themselves.
 *
 * Side effects:
 *      None.
 */


/**
 * ComputeBBox --
 *
 *      This procedure is invoked to compute the bounding box of
 *      all the pixels that may be drawn.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The fields x1, y1, x2, and y2 are updated in the header
 *      for itemPtr.
 */


/*
 *--------------------------------------------------------------
 *
 * CorrectAnchor--
 *
 *      This procedure is called to shift the x,y position to
 *      correct for any requested anchors. Note this doesn't
 *      correct for any scale factors.
 *
 *--------------------------------------------------------------
 */


/**
 * FrameSetPrintProc --
 *
 *      Return -frameset option as string.
 */


/**
 * MappingPrintProc --
 *
 *      Return -mapping option as string.
 */


/**
 * ClearSubItems --
 *
 *     Clear any items we've already drawn (before refresh or when we're being
 *     deleted).
 */


/**
 * GeneratePlotFrameSet --
 *
 *     Generate a FrameSet suitable for drawing a 2D data plot using our data
 *     values and 1D frameset. Also creates the coordinate positions array.
 */


/**
 * MakeSpectral --
 *
 *     Generate a FrameSet suitable for drawing a 2D data plot.
 */


/*
 *--------------------------------------------------------------
 *
 * CreateBoxEll --
 *
 *      This procedure is invoked to create a new ellipse or rotbox.
 *
 * Results:
 *      A standard Tcl return value.  If an error occurred in
 *      creating the item, then an error message is left in
 *      interp->result;  in this case itemPtr is left uninitialized,
 *      so it can be safely freed by the caller.
 *
 * Side effects:
 *      A new ellipse or rotbox is created.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * BoxEllCoords --
 *
 *   This procedure is invoked to process the "coords" widget command
 *   for ellipses and rotboxes. See the user documentation for details
 *   on what it does.
 *
 * Results:
 *      Returns TCL_OK or TCL_ERROR, and sets interp->result.
 *
 * Side effects:
 *      The coordinates for the given item may be changed.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ConfigureBoxEll --
 *
 *      This procedure is invoked to configure various aspects of an
 *      ellipse or rotbox, such as its border and background colors.
 *
 * Results:
 *      A standard Tcl result code.  If an error occurs, then
 *      an error message is left in interp->result.
 *
 * Side effects:
 *      Configuration information, such as colors and stipple
 *      patterns, may be set for itemPtr.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DeleteBoxEll --
 *
 *      This procedure is called to clean up the data structure
 *      associated with an ellipse or rotbox.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      Resources associated with itemPtr are released.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DisplayBoxEll --
 *
 *      This procedure is invoked to draw a rotbox or ellipse
 *      item in a given drawable.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      ItemPtr is drawn in drawable using the transformation
 *      information in canvas.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * EllipseToPoint --
 *
 *      Computes the distance from a given point to a given
 *      ellipse or rotbox, in canvas units.
 *
 * Results:
 *      The return value is 0 if the point whose x and y coordinates
 *      are coordPtr[0] and coordPtr[1] is inside the ellipse.  If the
 *      point isn't inside the ellipse then the return value is the
 *      distance from the point to the item.  If itemPtr is filled,
 *      then anywhere in the interior is considered "inside"; if
 *      itemPtr isn't filled, then "inside" means only the area
 *      occupied by the outline.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * EllipseToArea --
 *
 *      This procedure is called to determine whether an item
 *      lies entirely inside, entirely outside, or overlapping
 *      a given rectangular area.
 *
 * Results:
 *      -1 is returned if the item is entirely outside the area
 *      given by rectPtr, 0 if it overlaps, and 1 if it is entirely
 *      inside the given area.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ScaleBoxEll --
 *
 *      This procedure is invoked to rescale an ellipse or rotbox.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The item referred to by itemPtr is rescaled
 *      so that the following transformation is applied to all
 *      point coordinates:
 *              x' = originX + scaleX*(x-originX)
 *              y' = originY + scaleY*(y-originY)
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * TranslateBoxEll --
 *
 *      This procedure is called to move an ellipse by a given amount.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The position of the ellipse is offset by (xDelta, yDelta), and
 *      the bounding box is updated in the generic part of the item structure.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * EllipseToPostscript --
 *
 *      This procedure is called to generate Postscript for
 *      an ellipse item.
 *
 * Results:
 *      The return value is a standard Tcl result.  If an error
 *      occurs in generating Postscript then an error message is
 *      left in interp->result, replacing whatever used to be there.
 *      If no error occurs, then Postscript for the rectangle is
 *      appended to the result.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RotBoxToPostscript --
 *
 *      This procedure is called to generate Postscript for
 *      a rotbox items.
 *
 * Results:
 *      The return value is a standard Tcl result.  If an error
 *      occurs in generating Postscript then an error message is
 *      left in interp->result, replacing whatever used
 *      to be there.  If no error occurs, then Postscript for the
 *      item is appended to the result.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * GenEllipse --
 *
 *    Generates a list of coordinates that describe an ellipse
 *
 * Results:
 *      Returns the number of points generated.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * GenRotBox --
 *
 *    Generates a list of coordinates that describe a rotbox.
 *
 * Results:
 *      Returns the number of points generated.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 *  ComputeBoxEllGeom --
 *
 *    Computes the geometry given certain changes.
 *
 * Results:
 *      None
 *
 * Side effects:
 *      Changes the item description.
 *
 *--------------------------------------------------------------
 */


/**
 * Set a HDS tuning parameter.
 */


/**
 * Get a HDS tuning parameter.
 */


/* Float data: Prevent auto conversions.
 * No speed hits if this is compiled with gcc -O.
 * Need static functions for C99 compliance (previously just used from C++).
 */


/*
 *--------------------------------------------------------------
 * Polyline_Init --
 *
 *   This procedure initialises the rtd_polyline canvas item.
 *
 *--------------------------------------------------------------
 *
 */


/*
 *--------------------------------------------------------------
 * RtdLineDelete --
 *
 *    Delete an "instance" created for indirect use.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * LineToPoint --
 *
 *      Computes the distance from a given point to a given
 *      line, in canvas units.
 *
 * Results:
 *      The return value is 0 if the point whose x and y coordinates
 *      are pointPtr[0] and pointPtr[1] is inside the line.  If the
 *      point isn't inside the line then the return value is the
 *      distance from the point to the line.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * LineToArea --
 *
 *      This procedure is called to determine whether an item
 *      lies entirely inside, entirely outside, or overlapping
 *      a given rectangular area.
 *
 * Results:
 *      -1 is returned if the item is entirely outside the
 *      area, 0 if it overlaps, and 1 if it is entirely
 *      inside the given area.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ParseArrowShape --
 *
 *      This procedure is called back during option parsing to
 *      parse arrow shape information.
 *
 * Results:
 *      The return value is a standard Tcl result:  TCL_OK means
 *      that the arrow shape information was parsed ok, and
 *      TCL_ERROR means it couldn't be parsed.
 *
 * Side effects:
 *      Arrow information in recordPtr is updated.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * PrintArrowShape --
 *
 *      This procedure is a callback invoked by the configuration
 *      code to return a printable value describing an arrow shape.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ConfigureArrows --
 *
 *      If arrowheads have been requested for a line, this
 *      procedure makes arrangements for the arrowheads.
 *
 * Results:
 *      Always returns TCL_OK.
 *
 * Side effects:
 *      Information in linePtr is set up for one or two arrowheads.
 *      the firstArrowPtr and lastArrowPtr polygons are allocated
 *      and initialized, if need be, and the end points of the line
 *      are adjusted so that a thick line doesn't stick out past
 *      the arrowheads.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdLineToPostscript --
 *
 *      This procedure is called to generate Postscript for
 *      line items.
 *
 * Results:
 *      The return value is a standard Tcl result.  If an error
 *      occurs in generating Postscript then an error message is
 *      left in interp->result, replacing whatever used
 *      to be there.  If no error occurs, then Postscript for the
 *      item is appended to the result.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdLineSetLastCoords --
 *
 *      This procedure is called to reset the item coordinates,
 *      without the need to parse a string.
 *
 * Side effects:
 *      The coordinates for the given item will be changed.
 *
 * Notes:
 *      This procedure is non-standard. It provides a speedy way to
 *      set the coordinates of this item. The problems are that the
 *      canvas name and item are not available and are recorded from
 *      the last create command, so this should be called immediately
 *      after the create command and at no other time.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * RtdQuickSetLineCoords --
 *
 *      This procedure is called to set the item coordinates,
 *      without the need to parse a string.
 *
 * Side effects:
 *      The coordinates for the given item will be changed.
 *
 * Notes:
 *      Version of RtdLineSetLastCoords, if you have the item
 *      and canvas (see Polyline_Create()).
 *
 *--------------------------------------------------------------
 */


/*
 *+
 *  Name:
 *     errTcl_Inhibit

 *  Purpose:
 *     Controls whether error reports are actually made.

 *  Synopsis:
 *     #include "tcl_err.h"
 *     int errTcl_Init( int report )

 *  Description:
 *     This function allows the suppression of error messages. It also
 *     returns the current status of error reporting.

 *  Parameters:
 *     int report
 *        If 1 then error messages will be reported. Otherwise they
 *        will be inhibitied, until this routine is called to enable
 *        them.

 *-
 */


/*
 *+
 *  Name:
 *     errTcl_LastError

 *  Purpose:
 *     Returns the last error message and status.

 *  Synopsis:
 *     #include "tcl_err.h"
 *     void errTcl_LastError( int *status, const char **message )

 *  Description:
 *     This function returns the last error status seen and the associated
 *     message. The message is volatile and should be copied if kept.

 *  Parameters:
 *     int *status
 *        The status value;
 *     const char **message
 *        The message.

 *-
 */


/*
 *+
 *  Name:
 *     astPutErr

 *  Purpose:
 *     Deliver an error message.

 *  Type:
 *     Protected function.

 *  Synopsis:
 *     #include "asttcl_err.h"
 *     void astPutErr( int status, const char *message )

 *  Description:
 *     This function delivers an error message and (optionally) an
 *     accompanying status value to the user. It may be re-implemented
 *     in order to deliver error messages in different ways, according
 *     to the environment in which the AST library is being used.

 *  Parameters:
 *     status
 *        The error status value.
 *     message
 *        A pointer to a null-terminated character string containing
 *        the error message to be delivered. This should not contain
 *        newline characters.

 *  Notes:
 *     - This function is documented as "protected" but, in fact, is
 *     publicly accessible so that it may be re-implemented as
 *     required.
 *-
 */


/**************************************************************************/
/* Routine to mimic `strdup()' (some machines don't have it)              */
/**************************************************************************/


/**************************************************************************/
/* Routine to replace `strtok' : this one returns a zero length string if */
/* it encounters two consecutive delimiters                               */
/**************************************************************************/


/**************************************************************************/
/* Return version/copyright information                                   */
/**************************************************************************/


/**************************************************************************/
/* Set the font magnification factor for all subsequent operations        */
/**************************************************************************/


/**************************************************************************/
/* Set the padding used when calculating bounding boxes                   */
/**************************************************************************/


/**************************************************************************/
/*  Create an XImage structure and allocate memory for it                 */
/**************************************************************************/


/**************************************************************************/
/*  A front end to XRotPaintAlignedString:                                */
/*      -no alignment, no background                                      */
/**************************************************************************/


/**************************************************************************/
/*  A front end to XRotPaintAlignedString:                                */
/*      -no alignment, paints background                                  */
/**************************************************************************/


/**************************************************************************/
/*  A front end to XRotPaintAlignedString:                                */
/*      -does alignment, no background                                    */
/**************************************************************************/


/**************************************************************************/
/*  A front end to XRotPaintAlignedString:                                */
/*      -does alignment, paints background                                */
/**************************************************************************/


/**************************************************************************/
/*  Aligns and paints a rotated string                                    */
/**************************************************************************/


/**************************************************************************/
/*  Draw a horizontal string in a quick fashion                           */
/**************************************************************************/


/**************************************************************************/
/*  Create a rotated text item                                            */
/**************************************************************************/


/**************************************************************************/
/*  Adds a text item to the end of the cache, removing as many items      */
/*      from the front as required to keep cache size below limit         */
/**************************************************************************/


/**************************************************************************/
/*  Free the resources used by a text item                                */
/**************************************************************************/


/**************************************************************************/
/* Magnify an XImage using bilinear interpolation                         */
/**************************************************************************/


/**************************************************************************/
/* Calculate the bounding box some text will have when painted            */
/**************************************************************************/


/*
 *--------------------------------------------------------------
 * Mark_Init --
 *
 *   This procedure initialises the rtd_mark canvas item.
 *
  *--------------------------------------------------------------
 *
 */


/*
 *--------------------------------------------------------------
 *
 * DeleteMark --
 *
 *      This procedure is called to clean up the data structure
 *      associated with a marker.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      Resources associated with itemPtr are released.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * ComputeMarkBbox --
 *
 *      This procedure is invoked to compute the bounding box of
 *      all the pixels that may be drawn as part of a marker.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      The fields x1, y1, x2, and y2 are updated in the header
 *      for itemPtr.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * DisplayMark --
 *
 *      This procedure is invoked to draw a marker item in a given drawable.
 *
 * Results:
 *      None.
 *
 * Side effects:
 *      ItemPtr is drawn in drawable using the transformation
 *      information in canvas.
 *
 *--------------------------------------------------------------
 */


/*
 *--------------------------------------------------------------
 *
 * MarkToPoint --
 *
 *      Computes the distance from a given point to the marker.
 *
 * Results:
 *      The return value is 0 if the point whose x and y coordinates
 *      are coordPtr[0] and coordPtr[1] is inside the marker.  If the
 *      point isn't inside the marker then the return value is the
 *      distance from the point to the item.
 *
 * Side effects:
 *      None.
 *
 *--------------------------------------------------------------
 */