Go to the previous, next section.

Matrices and Cubes

A limited number of verbs exist for handling two-dimensional matrices (images) and three-dimensional cubes. This limited set permit the user to take a "quick-look" at such data and perform a number of useful, frequently-requested operations on them. The direct input data for both types of multi-dimensional structure is in the form of standard FITS-image files (i.e. FITS files using none of the FITS extensions) located on the computer disk. Matrices can also be created by either "collapsing" cubes to a single plane, or building a two-dimensional distribution from one-dimensional spectra or scans. For more sophisticated analysis and manipulation of multi-dimensional data, you will need to use a package such as AIPS on your FITS images and cubes.

NOTE : The cube and matrix operations do not participate in the UNDO (see Section 15.4) or RECOVER (see Section 2.2) facilities.

Data Storage

Matrices

UniPOPS has 4 "matrices" available in its memory to hold two-dimensional data arrays. These are designated Matrix (0) to Matrix (3). Each matrix contains a header and a data section, and these can be interrogated and used in exactly analogous way to the nine UniPOPS data arrays described in Section 5.6. The maximum number of data elements that can be contained in the data section of a matrix is 102400 (i.e. arrays such as 1024 x 100, 256 x 400, etc.)

The header can be accessed through the verbs MH0 - MH3, which use the following adverb pointers,

MNAXIS1, MNAXIS2	No. of pixels in x and y.
MTYPE1,  MTYPE2		Strings containing the x and y axis
			    definitions, (i.e. GALLONG, VELO, etc.)
MPIX1,   MPIX2		The x - y pixel numbers at the reference
			    pixel.
MRVAL1,  MRVAL2		The x and y values at the reference pixel.
MDELT1,  MDELT2		The sampling intervals in x and y.
MEQUINOX		The equinox of the coordinate system of the
			    matrix.
MDATE			A date associated with the matrix.
MCOMMENT		A comment string.
MUNDEF			The blanking (dummy) value for undefined data.
MBUNIT                  The units for the data values (i.e. COUNTS,
			    DEG K, etc.)
MOBJECT			A string containing the title of the matrix.
MORIGIN                 A string describing the place of origin of the
			   data in the Matrix.

The functions MH0 - MH3 return the header parameters. Thus, if you want to find to which celestial source the current data in Matrix (2) applies, try typing,

	>PRINT MH2(MOBJECT)

Similarly, if you are going to collapse this matrix on to the y-axis, and place the result into one-dimensional Array (3), prepare Array (3) by typing,

	>H3(NOINT) = MH2(MNAXIS2)

The data in a matrix can be read and reset using the verbs MD0 - MD3, which take as their arguments the (x,y) pixel position values. Thus to collapse the data of Matrix (2) on to the y-axis, placing the result in Array (3), you can use the following procedure,

	>PROCEDURE COLLAPSE
	:SCALAR I_1
	:SCALAR I_2
	:H3(NOINT) = MH2(MNAXIS2)
	:FOR I_1 = 1 TO MH2(MNAXIS2)
	:	D3(I_1) = 0.
	:	FOR I_2 = 1 TO MH2(MNAXIS1)
	:		D3(I_1) = D3(I_1) + MD2(I_2,I_1)
	:	END
	:END
	:RETURN
	:FINISH

Cubes

UniPOPS can consider just a single data cube at a time. At present only a very limited range of operations are available for cubes. The cube header can be interrogated as for Arrays (0) - (9), and Matrices (0) - (3), only here you use the verb CH0. The pointer adverbs for using this verb are similar to those described for matrices in Section 16.1.1, except that the first letter of the pointer names is C, rather than M. The full list of cube pointer adverbs is as follows,

CNAXIS1, CNAXIS2, CNAXIS3  No. of pixels in x, y and z.
CTYPE1,  CTYPE2,  CTYPE3   Strings containing the x, y and z axis
			   definitions, (i.e. GALLONG, VELO, etc.)
CPIX1,   CPIX2,   CPIX3    The (x,y,z) pixel numbers at the reference
			   pixel.
CRVAL1,  CRVAL2,  CRVAL3   The x, y and z values at the reference
			   pixel.
CDELT1,  CDELT2, CDELT3    The sampling intervals in x, y and z.
CDATE			   A date associated with the matrix.
CEQUINOX		   The equinox of the coordinate system of the
			   cube.
CCOMMENT		   A comment string.
CUNDEF                     The blanking (dummy) value for undefined
			   data.
CBUNIT                     The units for the data values (i.e. COUNTS,
			   DEG K, etc.)
COBJECT                    A string containing the title of the
			   matrix.
CORIGIN                    Character string describing place of origin
			   of the data in the Cube.
CTMAX                      The maximum data value in the original
			   (unscaled) Cube.
CTMIN                      The minimum data value in the original
			   (unscaled) Cube.
CTSCALE                    Scale factor by which to multiply numbers in
			   the FITS Cube to return them to original
			   scale.
CTZERO                     Value subtracted from the original numbers
			   in the Cube before they were divided by
			   CTSCALE.

For example, if you wish to know what source the current data cube applies to, try typing,

	>PRINT CH0(COBJECT)

You can read the data in a cube by using the verb CD0, which takes as its three arguments the (x,y,z) pixel position values. Thus, to find the largest value in a cube, you could use the procedure,

	>PROCEDURE CUBE_MAX
	:ARRAY POSN(1 TO 3)
	:SCALAR MAX_VAL
	:SCALAR I_1
	:SCALAR I_2
	:SCALAR I_3
	:MAX_VAL = -1.E34
	:FOR I_1 = 1 TO CH0(CNAXIS3)
	:  FOR I_2 = 1 TO CH0(CNAXIS2)
	:    FOR I_3 = 1 TO CH0(CNAXIS1)
	:      IF(CD0(I_3, I_2, I_1) > MAX_VAL)THEN
	:        MAX_VAL = CD0(I_3, I_2, I_1)
	:        POSN(1) = I_3
	:        POSN(2) = I_2
	:        POSN(3) = I_1
	:      END
	:    END
	:  END
	:END
	:PRINT 'MAX VALUE = ',MAX_VAL,' AT PIXEL (',POSN,')'
	:RETURN
	:END

WARNING : Note that, unlike the Arrays and Matrices, the data values in a cube CANNOT be replaced or otherwise modified ! This is essentially a consequence of the data in the cube not being present as an entity in memory.

Summarizing the Header Parameters of a Matrix or Cube

Rather full documentation on the parameters of the data in Matrix (0), or the data in a UniPOPS cube, can be obtained using the verbs MHEADER and CHEADER, respectively. Thus, to obtain a listing of the parameters of the contents of Matrix (0), type,

	>MHEADER

While to do the same for a cube, type,

	>CHEADER

Listing the Data in a Matrix

All, or part, of the data values in Matrix (0) can be listed using the verb MTABLE. The grid of numbers displayed have their x and y axes labeled by the pixel coordinates in the full matrix to aid identification of the individual elements.

The section of the matrix to be displayed is selected via the two adverb pairs, MXMIN, MXMAX and MYMIN, MYMAX which set the lower and upper pixel limits to be displayed for each axis, i.e. define an area in the matrix with bottom left-hand corner (MXMIN, MYMIN), and top right-hand corner (MXMAX, MYMAX). If the contents of Matrix (0) are produced from a cube via the SLICE verb (Section 16.4), then these adverbs are set to the x and y limits of the resultant matrix. If set to their default values of 0, then these adverbs are interpreted as the x and y limits of the contents of Matrix (0), if it exists. To make the setting of these four adverbs as simple as possible for the user, a verb MRANGE is provided, which takes as its arguments the limits you require in units of the x and y axes (MH0(MTYPE1) and MH0(MTYPE2)). These values are converted into nearest pixel numbers, and placed in MXMIN, MXMAX, MYMIN and MYMAX.

For example, suppose that you wish to list on the screen the values at pixels lying between galactic longitudes 10.5 and 11.0 deg, and radial velocities -90 and +30 km/sec (where these are the appropriate units for the matrix axes), from an l-v grid contained in Matrix(0). Then type,

	>MRANGE(10.5, 11.0, -90, 30)
	>MTABLE

NOTE : To set the adverbs MXMIN, MXMAX, MYMIN and MXMAX such that the whole map will be processed, you can type,

	>MRANGE(-DEFAULT, DEFAULT, -DEFAULT, DEFAULT)

or set values outside the limits of the matrix, i.e.,

	>MRANGE(-1E34, 1E34, -1E34, 1E34)

As a final example, suppose that you wish to obtain a hard-copy of the data values in the "sub-matrix" of Matrix (0) defined by bottom-left and top-right pixel coordinates of (50,39) and (53,44), then type,

	>MXMIN = 50; MXMAX = 53; MYMIN = 39; MYMAX = 44
	>PRINTER MTABLE CRT

Reading in and Processing a Cube

As described in Section 16.1.2, UniPOPS can read a FITS cube from disk. This FITS cube could have been prepared via the UniPOPS utility, cube.exe, described in detail in Appendix D-11, or imported from another source, such as AIPS or IRAF. The data cube is "read in" using the verb READCUBE, which takes the pathname of the FITS file on disk as its single argument. For example, if the FITS file is called W49A.FITS and is held in your present directory, then you can "read in" the cube to UniPOPS by typing,

	>READCUBE("W49A.FITS")

At present, only one operation is permitted on a cube in UniPOPS. This is to integrate (not average) the pixel values in a set of contiguous planes parallel to one of the faces of the cube, such as to produce a two-dimensional array in Matrix (0). This is achieved via the verb SLICE, which takes three arguments; the axis number (defined by the n of its CNAXISn) at right-angles to the contiguous planes, and the first and last of these contiguous planes as pixel values along that axis.

For example, suppose that the cube currently in UniPOPS is a pulsar database, where the CNAXIS1 axis is a complete 1-hour sequence of 1-minute integrations of pulse phase (CNAXIS2) versus radio frequency (CNAXIS3). Then to collapse the cube along CNAXIS1 to get the dynamic spectrum of the pulsar over the last half-an-hour of the observations, type,

	>SLICE(1, 31, 60)

which will leave the required dynamic spectrum in Matrix(0), with MNAXIS1 representing pulse phase, and MNAXIS2 representing radio frequency.

As a second example, suppose that the current UniPOPS cube is a spectral-line database, where the CNAXIS1 axis is radial velocity, CNAXIS2 is galactic longitude, and CNAXIS3 is galactic latitude. Further, let us imagine that CH0(CPIX3) = 1, CH0(CRVAL3) = -5., and CH0(CDELT3) = 0.5. If you would like to obtain a v-l matrix in Matrix (0), averaging over -1.25 < b < +1.25, then type,

	>SLICE(3, 9, 13)

SLICE sets the values of the adverbs MXMIN, MXMAX, MYMIN and MYMAX to the x and y pixel limits of the resultant array in Matrix (0).

Reading, Writing and Filling a Matrix

Section 16.4 has described one way of filling Matrix (0) from a UniPOPS cube using the verb SLICE. Alternatively, a two-dimensional FITS file on disk can be read into Matrix (0) using the verb MREAD. This takes the name of the FITS file on disk as its single argument. Thus, suppose that you want to read the two-dimensional FITS file M17.FITS from the subdirectory /g/jastrono/maps into Matrix (0), enter,

	>MREAD("/g/jastrono/maps/M17.FITS")

MREAD sets the values of the adverbs MXMIN, MXMAX, MYMIN and MYMAX to the x and y pixel limits of the resultant array in Matrix (0).

A further way of filling a Matrix is to create it from scans available in either the on-line or off-line data files. For example, suppose that you have accumulated a set of scans numbers on the stack (Chapter 11), representing a continuum raster coverage in the order of increasing declination. You could then prepare an RA - Dec map in Matrix (2) to look at the results as follows,

	>PROCEDURE MAKEMAP
	:SCALAR I_1
	:SCALAR I_2
	:GET(ASTACK(1))
	:MH1(NAXIS1) = H0(NOINT)
	:MH2(NAXIS2) = ACOUNT
	:FOR I_1 1 TO ACOUNT
	:   GET(ASTACK(I_1)
	:   FOR I_2 1 TO H0(NOINT)
	:      MD2(I_1,I_2) = D0(I_2)
	:   END
	:   END
	:RETURN
	:FINISH

Four verbs exist to help you put entire rows and columns into a matrix or retrieve entire rows and columns from a matrix. These verbs are PUTROW, PUTCOL, GETROW and GETCOL. They transfer all or as many of the elements as will fit of a row or column either into a matrix or from a matrix. For example, the inner loop in the above procedure, where all of the values from each scan are placed into a single column, could be replaced by a single call to PUTCOL. Since these four verbs operate on an entire row or column, they are significantly faster than relying on the POPS interpretor to work on each element in a row or column. Using PUTCOL, the above procedure would be written as:

	>PROCEDURE MAKEMAP
	:SCALAR I_1
	:GET(ASTACK(1))
	:MH1(NAXIS1) = H0(NOINT)
	:MH2(NAXIS2) = ACOUNT
	:FOR I_1 1 TO ACOUNT
	:   GET(ASTACK(I_1)
	:   PUTCOL(I_1)
	:END
	:RETURN
	:FINISH

In this example, the entire contents of Array 0 would be copied to column I_1 in Matrix (0). See the documentation on these four verbs for more details (EXPLAIN PUTCOL).

Should you wish to add more complete header information to the matrix, including things not derivable from the single scans, then the verb MINIT can be used. This will initiate a question-and-answer session with you, that will fill in the required values. The verb takes a single argument, this being the number of the Matrix, (i.e. the n in Matrix (n)). Thus, to fill in the header of the above map in Matrix (2) and look at the results, type,

	>MINIT(2)
	 ......
	 Answer the questions posed by MINIT
	 ......
	>MHEADER

The contents of Matrix (0) can be written out to disk as a FITS file using the verb MWRITE. MWRITE takes a single argument, this being the name you wish to give the FITS file on disk, including the necessary path information of where to put the file should this not be the present directory. Thus to write a FITS image of the continuum map in Matrix (0) in the home directory of user jastrono with the filename CTA1.FITS, type,

	>MWRITE("/g/jastrono/CTA1.FITS")

Later, the FITS file can be read into another analysis system, or back into UniPOPS using the verb MREAD, as described above.

Operations on UniPOPS Matrices

Moving Data between Different UniPOPS Matrices

In analogy with the verbs COPY and MOVE for UniPOPS one-dimensional data arrays, (see Section 5.11), the verbs MCOPY and MMOVE will allow you to transfer your two-dimensional data arrays from one Matrix to another. Both verbs take two arguments, namely the Matrix the data is currently in, and the Matrix it is to be moved to. MCOPY leaves the original Matrix untouched by the operation, while MMOVE clears the original Matrix. The whole matrix is transferred by both verbs, and the adverbs MXMIN, MXMAX, MYMIN and MYMAX are set to the appropriate values for the data copied.

As an example, suppose that you wish to copy the data in Matrix (0) into Matrices (1) and (3), leaving Matrix (0) cleared, then type,

	>MCOPY(0,1)
	>MMOVE(0,3)

General Data Processing of Matrices

Currently, four verbs exist for general processing operations on data held in UniPOPS Matrices, and these are described in this subsection.

MLIMITS

To find the maximum and minimum values in a sub-area of Matrix (0), use the verb MLIMITS. The sub-area is defined by the adverbs MXMIN, MXMAX, MYMIN and MYMAX. The verb will print the maximum and minimum values within the defined sub-area on your screen.

Suppose that you have a discrete source near the middle of your 256 x 128 map, and wish to obtain the brightness at the pixel of the peak, then try typing the following,

	>MXMIN = 120; MXMAX = 136; MYMIN = 56; MYMAX = 72
	>MLIMITS

MLIMITS can be useful in finding the range of values in your data to help you set up levels for a contour plot.

ROTATE

The verb ROTATE offers various possibilities for rotating and flipping Matrix (0). The original data in Matrix (0) is copied to Matrix(1), so before invoking ROTATE, make sure that anything you wish to keep in Matrix (1) has been copied to Matrix (2) or (3) ! ROTATE takes three arguments, all taking the values TRUE (+1), or FALSE (-1). The first argument decrees whether the matrix is to be rotated about the "bottom-left to top-right" diagonal of the map (i.e. the x and y axes are to be interchanged). If this is what you want, set it TRUE, if not, set it FALSE. The second argument, if set TRUE, will reverse the sense of the x-axis (i.e. rotate the data about a vertical axis), but make no change about this axis if the argument is FALSE. The third argument does the same for the y-axis (i.e. if TRUE, the verb will rotate the data about a horizontal axis). The "instructions" of the first argument are acted upon before those of the other two arguments.

Suppose you wish to rotate Matrix (0) about the "top-left to bottom-right" diagonal, this can be achieved by typing the following, (think about it !),

	>ROTATE(TRUE, TRUE, TRUE)

MPLUS, MMINUS, MMULTIPLY, MDIVIDE

These verbs combine the data in Matrix (1) with that in Matrix (0) and place the result in Matrix (0). Each of these verbs operate element by element (i.e. element (i,j) in Matrix (1) is combined with element (i,j) in Matrix (0) and the result placed in element (i,j) of Matrix (0)) as opposed to true matrix math operations.

All four verbs use the value of the adverb DEFMODE to determine how they treat undefined values (data values equal to the value of the MUNDEF header word). When DEFMODE is FALSE, the result will have an undefined data value at any element where either of the input values at that location were undefined. When DEFMODE is TRUE, the result will have an undefined data value only at those locations where both the input values were undefined. If only one value is undefined, the value of the results depends on the specific verb. The default value for DEFMODE is FALSE.

For all four verbs, the original contents of Matrix (0) are replaced by the result.

The MPLUS verb adds the data in Matrix (0) to the data in Matrix (1) element by element. If DEFMODE is TRUE and only one value is undefined at a location, the result at that location will be as if the undefined value were zero.

The MMINUS verb subtracts the data in Matrix (0) from the data in Matrix (1) element by element. If DEFMODE is TRUE and only one value is undefined at a location, the result at that location will be as if the undefined value were zero.

The MMULTIPLY verb multiplies the data in Matrix (1) by the data in Matrix (0) element by element. If DEFMODE is TRUE and only one value is undefined at a location, the result at that location will be as if the undefined value were one.

The MDIVIDE verb divides the data in Matrix (0) by the data in Matrix (1) element by element. If DEFMODE is TRUE and only one value is undefined at a location, the result at that location will be as if the undefined value were one.

Suppose you wish to do the following:

	(Matrix(0) - Matrix(1)) / Matrix(1)

or subtract each element of Matrix (1) from the corresponding element of Matrix (0) and divide the result by the element of Matrix (1), type,

	> MMINUS; MDIVIDE

The verb MSCALE allows you to multiply the values in Matrix (0) by a constant factor, while the verb MBIAS will add a constant value to each element of Matrix (0). These verbs both require one argument, the value to use for scaling or offset.

Suppose you wish to multiply all of the values in Matrix (0) by 3.2, type,

	> MSCALE(3.2)

Suppose you want to add the value -10.0 to all the values in Matrix (0), type,

	> MBIAS(-10.0)

You may need to use MCOPY and Matrix (2) or Matrix (3) since MSCALE and MBIAS only work on Matrix (0). For example, suppose you want to subtract from each element of Matrix(1) before subtracting each element of Matrix(1) from each element of Matrix (0), type,

	> MCOPY(0,2); MCOPY(1,0)
	> MBIAS(-10)
	> MCOPY(0,1); MCOPY(2,0)
	> MMINUS

MSMOOTH

The verb MSMOOTH will provide two-dimensional smoothing of the data in Matrix (0). The original data in Matrix (0) is copied to Matrix(1), so before invoking MSMOOTH, make sure that anything you wish to keep in Matrix (1) has been copied to Matrix (2) or (3) ! MSMOOTH takes two arguments. The first is a value, c (0 < c < 1), which defines the "severity" of the smoothing as detailed below. The second argument can take the values of TRUE or FALSE, such that if it is TRUE, and the array is defined as z(i,j), the smoothing includes only horizontal and vertical nearest neighbors according to,

        z(i,j) = c*z(i,j) + (1-c) * (z(i-1,j)+z(i+1,j)+z(i,j-1)+z(i,j+1)) / 4

While, if the second argument is FALSE, then the smoothing includes horizontal, vertical and diagonal nearest neighbors, according to,

        z(i,j) = c*z(i,j) + (1-c) * (z(i-1,j-1)+z(i-1,j)+z(i-1,j+1)+z(i,j-1)
	         +z(i,j+1)+z(i+1,j-1)+z(i+1,j)+z(i+1,j+1)) / 8

With MSMOOTH, the area smoothed within the matrix is defined by setting MXMIN, MXMAX, MYMIN and MYMAX appropriately. If any of the z's in the above definitions are undefined (i.e. if MD0(x,y) = MH0(MUNDEF)), then no smoothing is made for that (i,j). Similarly, no smoothing is made for the border cells in the matrix.

Suppose that you wish to do a "quasi pill-box" smooth of the map in Matrix (0), but you already have a valuable map in Matrix (1), although Matrix (2) is empty, try typing,

	>MMOVE(1,2)
	>C = 0.5
	>MSMOOTH(C, FALSE)

MFILL

Often a matrix will contain "holes" where data do not exist, those pixels containing just the blanking (dummy) value, MH0(MUNDEF). For example, interference may have been present at those points in a continuum raster and you have edited it out, or a few grid points in a spectral coverage may have been omitted due to time constraints during observations. MFILL is a verb that will try to interpolate the most-probable values at these positions of undefined brightness for the array in Matrix (0). The original data in Matrix (0) is copied to Matrix(1), so before invoking MFILL, make sure that anything you wish to keep in Matrix (1) has been copied to Matrix (2) or (3) !

The verb MFILL takes a single argument which defines the RADIUS, in units of grid cells, within which the interpolation will consider nearest-neighbor points. Of course, RADIUS must be greater than, or equal to, one pixel width. For each undefined point, the algorithm searches along both the x- and y-axes, and the diagonals, through the point and finds the nearest neighbor pairs (if any) possessing valid data at distances of less than or equal to RADIUS for each of these directions. An approximate value at the undefined point is computed via linear interpolation for any of the four directions having a valid data pair. Then the weighted mean of the interpolated values is taken, with weights assigned proportional to the distances between the "nearest neighbor pairs". If no valid "adjacent pairs" are found, the undefined point is left undefined.

While a large value of RADIUS will fill in more holes, a smaller value gives greater assurance that the filled-in value bears a reasonable relation to reality. The interpolated values themselves are not used in filling in other undefined points. The area over which the operation is applied is defined by the adverbs MXMIN, MXMAX, MYMIN and MYMAX, but no values are filled in for the border cells of the matrix.

Suppose that you have a few "data holes" in Matrix (0) due to editing-out interference. Further, suppose that these holes lie within the region with bottom left-hand, and top right-hand, corners given by pixels (27,35), (93,117). If the largest holes occupy only two "adjacent" undefined points, you can interpolate their values by typing,

	>MXMIN = 27; MYMIN = 35; MXMAX = 93; MYMAX = 117
	>RADIUS = 2
	>MFILL(RADIUS)

MFFT, MIFFT and Holographic Data Reduction

A few verbs have been added to UniPOPS that were meant for the reduction of holographic data.

The verbs MFFT and MIFFT take the complex fast-Fourier transform or inverse transform of the contents of Matrices (0) and (1) and return their results to the same matrices. The input Matrix (0) and (1) are assumed to contain real and imaginary data. Both matrices must have the same dimensions -- you will get faster response if the dimensions are a power of two.

Two other verbs, HOLWINDOW and HOLFITFOC, are meant only for holographic data reduction and probably would have no other uses. They are presented here solely for the sake of completeness.

HOLWINDOW convolve the data in Matrices (0) and (1) with various functions and stores the results back in the same matrices. Both matrices should have the same dimensions. HOLWINDOW takes a single argument which indicates what convolution function you want to use. The values of the possible arguments and their corresponding functions are:

    Arg   Function                                  Name
    --------------------------------------------------------------------
     1      1.                             Rectangular [No convolution]
     2      G/pi                                     Bartlet
     3      [ 1 - cos(G) ] / 2                       Hanning
     4      0.54 - 0.46*cos(G)                       Hamming
     5      0.42 - .5*cos(G) + 0.08*cos(2*G)         Blackman
    --------------------------------------------------------------------
    where G = pi*(r-1)/(R-1); r = radius of a pixel from center of matrix,
    R = radius of corner pixel from center.

HOLFITFOC assumes that Matrix (0) represents the surface errors of a telescope and fits to the data an error pattern due to offsets in radial and lateral focus or pointing. HOLFITFOC removes the error pattern from the data and places the results back into Matrix (0). It also places the fitted error pattern into Matrix (1) and uses data Array(1) for temporary storage.

Clearing a Matrix

The verbs MBLANK and MREMOVE should be used to clear a UniPOPS Matrix. MBLANK takes the Matrix number as its single argument, and erases all data values from that Matrix. The header of the Matrix is left untouched, while the date values are all set to the undefined (dummy) value. Suppose that you wish to retain the header of the array in Matrix (2), but set the data values to the number 1.0E10. Then type,

	>MH2(MUNDEF) = 1.0E10
	>MBLANK(2)

MREMOVE goes one step further. If you want to remove both header and data, say to create your own two-dimensional array, then this can be achieved with the verb MREMOVE. It takes a single argument which is the number of the Matrix (n) to be left void. This is exactly like the operation of the verb REMOVE for the one-dimensional UniPOPS data Arrays (see Section 5.12). Note that the verb MMOVE(m,n) is equivalent to,

	>MCOPY(m,n)
	>MREMOVE(m)

Display of Two-Dimensional Data

A data array held in Matrix (0) can be displayed on your workstation screen in a number of different and complimentary ways. These are,

Common Adverbs to All Two-Dimensional Plots

Certain adverbs are used by all of these dispay options. These are,

Preparing to Display Two-Dimensional Data

The more complicated two-dimensional displays that you may wish to produce often require an element of "prototyping" to get things just right. You can reduce the computing time for these iterations by using the COPYOFF/COPYON facility (see Section 15. ). Thus, when initiating "prototyping", type (say),

	>COPYOFF
	>Your plotting commands

When you are satisfied with your latest version and wish to take a hard copy, type,

	>COPYON
	>Your plotting commands
	>GCOPY

Setting the LEVS Array

The following verbs are available to help you set LEVS using different criteria: AUTOLEV, SETLEV, EQHISTLEV, and FUNCLEV.

The verb AUTOLEV can be invoked to help you set up the LEVS array. It takes a single argument defining the number of levels to be set. AUTOLEV finds the maximum and minimum data values within the specified region of the matrix, and assigns the values of LEVS such as to give equal increments between levels. Thus, if you wish to plot 10 levels in your display, type the following to set the levels and inspect them,

	>AUTOLEV(10)
	>PRINT LEVS

An alternative, and more general, way in which you can set LEVS is with the verb SETLEV. This verb takes 4 arguments. The first two are a starting level, and an increment between levels. The third argument (0 < arg_3 < 33) is the number of levels to be set. If the fourth argument equals TRUE (+1), then the levels are linear (equally spaced in value). If this argument is FALSE (-1), then the levels are logarithmic. The increment (arg_2) must always be positive. The starting level (arg_1) can take any value for linear levels, irrespective of the value of arg_2. For logarithmic levels,

	1) If arg_1 < 0., then arg_2 must be < 1.

	2) If arg_1 > 0., then arg_2 must be > 1.

	3) Arg_1 must never equal 0., and arg_2 must never
	   equal 1.

Suppose that you wish to set 10 levels, starting at 1.0, and going up in steps of 3 dB. Then type,

	>SETLEV(1.0, 10.**0.3, 10, FALSE)

The EQHISTLEV verb sets the values of LEVS so that an equal number of the data points in the specified region of Matrix (0) occur between each level (i.e. an equal histogram). EQHISTLEV takes three arguments. You specify the mimimum and maximum data values over which you want to have an equal histogram and the number of levels in LEVS that you wish to use. If you use the adverb DEFAULT for either of the minimum or maximum data values then EQHISTLEV will use the corresponding value from the data.

Suppose that you wish to have 15 levels in the equal histogram covering the range from 10.0 to the maximum value in the data. Then type,

	>EQHISTLEV(10.0, DEFAULT, 15)

Finally, FUNCLEV sets LEVS such that there are a certain fraction of data points in the specified region of Matrix (0) between each level. The relative number of data points between each level is given by the array adverb FLEVS, which you must set prior to using FUNCLEV. FUNCLEV takes two arguments, the minimum and maximum data values in Matrix (0) that are used in setting LEVS.

Suppose that you want 10 levels with the relative number of data points between each level having the following ratio:

	1:2:3:4:5:6:6:7:4:2

(i.e. twice as many data points between levels two and three as between levels one and two, 1.5 times as many data points between levels three and four as between levels two and three, etc).

First, assign to FLEVS the appropriate values:

	> FLEVS = 1,2,3,4,5,6,6,7,4,2,DEFAULT

(the use of DEFAULT assigns a default value to the eleventh element which guarantees that only the 10 elements you set will be used)

Note that what counts is the ratio of FLEVS values and not the individual values. That is, FLEVS=1,2,3,DEFAULT is equivalent to FLEVS=5,10,15,DEFAULT.

Next, run FUNCLEV to set LEVS based on FLEVS and the actual data in Matrix (0),

	> FUNCLEV(min, max)

For color intensity maps, something like the following produces pleasing displays:

	> { FLEVS@ = 32-@ }
	> FUNCLEV(DEFAULT, DEFAULT)

Contour Plots

The simplest contour plots are obtained using the verb QCONTOUR. This differs from the verb CONTOUR (see below) in that you can specify neither the line type nor the labeling used for each contour level. If working on a color screen, you can, however, chose the color for all contours via a call to COLOR or RSTCOLOR (see Section ) before plotting.

Suppose that you want to plot 10 contours with QCONTOUR, starting at 1.0 with intervals of 2.0, for the area of Matrix (0) defined by bottom left-hand corner (1, 10), top right-hand corner (10, 20). Then type,

	>MXMIN = 1; MXMAX = 10; MYMIN = 10; MYMAX = 20
	>SETLEV(1.0, 2.0, 10, TRUE)
	>QCONTOUR

The verb CONTOUR is somewhat more complicated to use than QCONTOUR, but allows you the flexibility to specify the line types and labeling used for each contour level. The line types that can be used (as for PLOT, SHOW, VCTR and RESHOW) are detailed in Appendix I. , and are specified using the array adverb CONLINE, which should contain as many entries as there are in the array adverb LEVS (see Section 16.7.1). The absolute value of the n-th entry in CONLINE defines the line type for the n-th contour level and is effectively the argument of a call to the verb LINETYPE, (see Section 6.6 and Appendix I). The sign of an entry in CONLINE determines whether the contour line is to be labeled. If the n-th entry is < 0, the n-th level will be labeled, while if the entry is >= 0, it will not be labeled. Contour labeling is affected by the current character size (see CHARSIZE in Section 6.4, and STATUS in Appendix H). On a color screen, the color for all contours can be set via a call to the verbs COLOR or RSTCOLOR (see Section 6.6).

If you wish to repeat the plot made above with QCONTOUR, but with every other level ticked and thick, and every fourth level labeled, then type,

	>MXMIN = 1; MXMAX = 10; MYMIN = 10; MYMAX = 20
	>SETLEV(1.0, 2.0, 10, TRUE)
	>CONLINE = 0, 103, 0, -103, 0, 103, 0, -103, 0, 103
	>CONTOUR LABEL

Half-Tone Displays

To obtain a half-tone display of the data in Matrix (0), you set up the adverbs MXMIN, etc., and LEVS exactly as for QCONTOUR and CONTOUR (see Section 16.7.3).

Thus, suppose that you wanted to make a half-tone displays with 10 levels starting at 1.0 with intervals of 2.0, for the area of Matrix (0) defined by bottom left corner (1, 10), top right corner (10, 20). Then type,

	>MXMIN = 1; MXMAX = 10; MYMIN = 10; MYMAX = 20
	>SETLEV(1.0, 2.0, 10, TRUE)
	>HLFTNE

Color and Gray-Scale Displays

To make a color or gray-scale display of the data in Matrix (0), you should use the verb RASTER. If your workstation cannot handle color graphics, RASTER makes an attempt to arrange its levels of gray-scale shading to "mimic" color.

The colors to be used are specified in the 3 x 32 element, two-dimensional adverb array CLUT, where the second index corresponds to the index in the array adverb LEVS used by RASTER. The first index provides three elements into which you encode the color for a particular level using the coding described for the verb COLOR in Section 6.6 and Appendix I. Thus, for the n-th level in LEVS(n) you must specify the red value or the hue in CLUT(1,n), the green value or the intensity in CLUT(2,n), and the blue value or the saturation in CLUT(3,n).

select one of six color tables, these being as follows,

	1	Gray-scale (White to Black)
	2	Gray-scale (Black to White)
	3	Blue through Green to Red
	4	Red through Green to Blue
	5	Blue through Purple to Brown
	6	Brown through Purple to Blue

SETCLUT has two arguments. The first is the identification number of the chosen color table, while the second is the number of levels (0 < arg_2 < 33).

Suppose that you want to make a color display with 10 levels starting at 1.0 with intervals of 2.0, for the area of Matrix (0) defined by bottom left-hand corner (1, 10), top right-hand corner (10, 20). Further you want the color sequence to pass from red through green to blue. Then type,

	>MXMIN = 1; MXMAX = 10; MYMIN = 10; MYMAX = 20
	>SETLEV(1.0, 2.0, 10, TRUE)
	>SETCLUT(4,10)
	>RASTER

Finishing and Annotating the Display

There are two further operations that can be applied to your plot once the basic display has been made. Firstly, you will almost certainly want to draw and label the axes, add documentary annotations, and label the levels. This is achieved by invoking the verb LABEL. Before calling LABEL, you will have to set up the adverbs you need to tailor the operation to your requirements. The array adverb LEVS should be left as it was for the display verb, as should the array adverb CLUT (for a RASTER plot). If the adverb SLABEL is set to 1 or 2, documentary annotations will be added to the display and the tick marks on the axes will be labeled. If SLABEL = 0, then no documentation will be generated, and the tick marks will remain unlabeled.

A series of adverbs allow the user of LABEL to draw lines across the display. These are ZLINE, CMARK, FMARK, TMARK and VMARK, which (as detailed in Section 6.2) have other significances for one-dimensional display. Setting ZLINE to TRUE will draw a horizontal line representing the x-axis, i.e. at a y-value of y = 0. Each of the adverb quartet CMARK, FMARK, TMARK, and VMARK is a 12-element array adverb. They allow you to draw n lines of a specific type, as detailed immediately below. To use these, fill the first n elements of the relevant adverb, setting the (n+1)-th element to DEFAULT. The lines will be drawn on calling LABEL. The meanings of these four array adverbs here are,

	CMARK	--  A vertical line is drawn through pixels whose x
		    pixel (cell) number is CMARK(i).

	TMARK   --  A horizontal line is drawn through pixels whose y
		    pixel (cell) number is TMARK(i).

	VMARK   --  A vertical line is drawn  at the true x-value of
		    VMARK(i).

	FMARK   --  A horizontal line is drawn at the true y-value of
		    FMARK(i).

The verb FLAG will also draw and label a vertical line through the x value given as its single argument. Thus if the x-axis of your present two-dimensional plot represents galactic longitude, and you wish to draw a vertical, labeled line at x = -10.0 deg, type,

	>FLAG(-10.0)

A further way to annotate your display is provided by the verb PLOTDOTS. This verb will draw dots or plusses wherever in Matrix (0) a defined or undefined data value exists. It takes one argument that controls its mode of operation as follows,

   0 or 1 = Plot dots at the positions of all undefined data.
   2      = Plot plus-signs at the positions of all undefined data.
  -1      = Plot dots at the positions of all defined data.
  -2      = Plot plus-signs at the positions of all defined data.

Thus, suppose that you have produced a two-dimensional contour plot, and now wish to label the axes, add documentation and a contour look-up table, draw horizontal lines at y grid points 23 and 57 and vertical lines at x grid points 5, 26 and 134, plus putting plus-signs wherever there is dummy data. Then type,

	>SLABEL = 1
	>CMARK = 5 26 134 DEFAULT
	>TMARK = 23 57 DEFAULT
	>ZLINE = FALSE
	>FMARK = DEFAULT; VMARK = DEFAULT
	>LABEL
	>PLOTDOTS(2)

The Cross hairs (Cursors) and Two-Dimensional Displays

As with other UniPOPS displays (see Section 6.3), the cross hairs (cursors) can be activated and used to determine positions and brightnesses at any point on two-dimensional displays and feed values into UniPOPS adverbs. The mouse is used to control the operation of these verbs, as detailed in Section 6.3. However, their meanings and results are somewhat different to the one-dimensional case, as follows,

	CROSSHAIR  - Prints on the screen the (x,y) pixel coordinates,
		     the x and y values, and the brightness (z-value)
		     at the cursor position.  Which of these values are
		     displayed is determined by the value of the adverb
		     CROSSFLG.
	CCUR	   - This function returns a value equal to the x pixel
		     coordinate of the vertical cursor.
	TCUR       - This function returns a value equal to the y pixel
		     coordinate of the horizontal cursor.	
	VCUR 	   - This function returns a value equal to the x value
		     of the vertical cursor.
	FCUR 	   - This function returns a value equal to the y value
		     of the horizontal cursor.
	CLICK	   - Allows you to set adverbs to the values that would
		     have been returned by all of the cursor function
		     verbs with a single verb using a single click of a
		     mouse button.

Thus, suppose for your plotted image you wished to put the x pixel coordinate and the x value (might be galactic longitude) at the point of peak brightness into into the already-declared adverbs X_PIX and X_LONG, then type,

	>X_PIX = CCUR; X_LONG = VCUR

Move the cross hairs to the brightness peak, and then click left or right twice. Or alternatively, the following would achieve the same result with a single click of a mouse button:

	> CLICK; X_PIX = XCLICK; X_LONG = VCLICK

and move the cross hairs to the brightness peak and click left or right once.

A further cursor function verb, MCUR, has been created specifically for two-dimensional image plots and returns the value of the brightness underneath the cross hairs. MCUR activates the cross hairs, and these can be moved to the required position on the display, where clicking either of the mouse buttons 1 or 3 will return the value of brightness at the nearest pixel. For example, if you wish to know the brightness at the peak position in your display, type,

	>PRINT MCUR

and move the cross hairs that then appear to the peak, clicking left or right once there.

Go to the previous, next section.



Webmaster: Ronald J. Maddalena
Send questions or comments to


Cookbook table of contents               NRAO information