'\"!  eqn | tbl | mmdoc
'\"macro stdmacro
.if n .pH ref.transform @(#)transform	40.1 of 11/1/89

.ig
imagen 8/31/89
docformat -c -s4 -dqm4 -p1 transform
..
.SO mstr.hdr
.ds Lb Shapes
.BK "Shapes Reference Manual"
.\" turn off automatic hyphenation -- JHevelin (08-09-89)
.am RT
.nh
..
.CH "Transform Object" "15"
.H 1 "Transform Object" 
.H 2 "Introduction"
.P
.nh
.IX "transform object"
Transforms provide scaling, translation,
and rotation of images.
When you create a transform object,
it is automatically an identity transform.
Each subsequent transformation is concatenated to
the end of the previous transform,
so that transformation becomes a single operation performing all of
the requests in the order they were issued.
.H 4 "NAME"
.P
Copy_Transform \- Copies the source transform to the destination transform.
.IX "Copy_Transform"
.tm .CE U 3 "Copy_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Copy_Transform\f2(src, dst)\f1
.br
TRANSFORM src;
.br
TRANSFORM dst;
.H 4 "DESCRIPTION"
.P
Copies the source transform to the destination transform.
.P
\f2src\f1
Specifies the transform to be copied.
.P
\f2dst\f1
Specifies the transform to which the copy is made.
If this parameter is set to NULL,
a new transform is made that is a clone of the source
transform.
The new transform has a reference count of one.
.H 4 "RETURNED VALUE"
.P
TRANSFORM
.H 4 "SEE ALSO"
.P
Create_Transform
.br
Create_Context
.br
Copy_Context
.H 4 "NAME"
.P
Create_Transform \- Creates a transform object and initializes it as an
identity transform.
.IX "Create_Transform"
.tm .CE U 3 "Create_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Create_Transform\f2(type, root)\f1
.br
TRANS_type type;
.br
RASTER root;
.H 4 "DESCRIPTION"
.P
Creates a new transform object and initializes it
as an identity transform.
.P
\f2type\f1
Specifies the type of transform to create.
The transform type can be one of the following
(all of which may be ORed together to produce a
composite type):
.sp 1v
.TB "Transform Types"
.TS
box tab(/);
cf4I | cf4I
l | lw(3.5i).
Type/Description
=
TRANS_2D/2D transform.
_
TRANS_BIN/Fract (fixed-point binary) transform.
_
TRANS_FLT/Floating-point transform.
_
TRANS_GENERIC/T{
TRANS_2D|TRANS_BIN transform,
the most efficient transform for X11/NeWS.
It applies only to Create_Transform.
T}
.TE
.TT
.P
\f2root\f1
This argument is currently unused.
Specify NULL for all transforms.
.H 4 "RETURNED VALUE"
.P
TRANSFORM (a handle to the new transform)
.br
NULL is returned if a transform cannot be created.
.H 4 "SEE ALSO"
.P
TRANS_TYPE
.H 4 "NAME"
.P
Destroy_Transform \- Destroys the specified transform object.
.IX "Destroy_Transform"
.tm .CE U 3 "Destroy_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Destroy_Transform\f2(trans)\f1
.br
TRANSFORM trans;
.H 4 "DESCRIPTION"
.P
Destroys the specified transform object.
If other objects refer to the transform object,
the resources are not freed until all references are
removed.
.P
\f2trans\f1
Specifies the transform object to be destroyed.
It is an error to reference
an object once it has been destroyed.
.H 4 "RETURNED VALUE"
.P
[None]
.H 4 "SEE ALSO"
.P
Destroy_Obj
.br
Create_Transform
.H 4 "NAME"
.P
Get_Transform \- Returns the setting of the specified transform attribute.
.IX "Get_Transform"
.tm .CE U 3 "Get_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Get_Transform\f2(trans, attr)\f1
.br
TRANSFORM trans;
.br
TRANS_attr attr;
.H 4 "DESCRIPTION"
.P
Returns the setting of the specified transform attribute.
.P
\f2trans\f1
Specifies the transform object for which the attribute
setting is to be returned.
.P
\f2attr\f1
Specifies the attribute for which the setting is to be returned.
.H 4 "RETURNED VALUE"
.P
Attribute setting
.H 4 "SEE ALSO"
.P
Set_Transform
.br
TRANSFORM ATTRIBUTES
.H 4 "NAME"
.P
Identity_Transform \- Fills the transform object with the identity
transformation.
.IX "Identity_Transform"
.tm .CE U 3 "Identity_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Identity_Transform\f2(trans)\f1
.br
TRANSFORM trans;
.H 4 "DESCRIPTION"
.P
Fills the specified transform object with an identity transformation.
An identity transformation multiplied by another transform or
a point returns the same transform or point.
The type of the transform (TRANS_FLT/TRANS_BIN) remains the same.
.sp
.EQ
left [
matrix {
   ccol { 1 above 0 above 0 above 0 }
   ccol { 0 above 1 above 0 above 0 }
   ccol { 0 above 0 above 1 above 0 }
   ccol { 0 above 0 above 0 above 1 }
  }
right ]
.EN
.P
\f2trans\f1
Specifies the transform to be set to the identity matrix.
.H 4 "RETURNED VALUE"
.P
TRANSFORM
.H 4 "SEE ALSO"
.P
TRANS_TYPE
.br
Scale_Transform
.br
Rotate_Transform
.br
Translate_Transform
.H 4 "NAME"
.P
InversePoint_Transform \- Transforms the specified point by the inverse of the
designated transform.
.IX "InversePoint_Transform"
.tm .CE U 3 "InversePoint_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3InversePoint_Transform\f2(trans, p)\f1
.br
TRANSFORM trans;
.br
POINT *p;
.H 4 "DESCRIPTION"
.P
Transforms the specified point by the inverse of the designated transform.
The result is placed in point \f2p\f1\&.
.P
\f2trans\f1
Specifies the transform object.
.P
\f2p\f1
Specifies the point for which the inverse transform
operation is to be performed.
The point may be relative,
for example, MOVEREL or LINEREL.
If the point type is relative,
the translation factor of inverse transforms
is not applied.
This is useful when transforming distance
(as opposed to positions) and preserves the notion of
relative positioning.
.P
If the transform is not invertible,
the error code SH_TRANS_INV is set.
.H 4 "RETURNED VALUE"
.P
[None]
.H 4 "SEE ALSO"
.P
Point_Transform
.br
Invert_Transform
.H 4 "NAME"
.P
Invert_Transform \- Inverts the source transform object and stores it in the
destination transform object.
.IX "Invert_Transform"
.tm .CE U 3 "Invert_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Invert_Transform\f2(dst, src)\f1
.br
TRANSFORM dst;
.br
TRANSFORM src;
.H 4 "DESCRIPTION"
.P
Inverts the source transform object and stores it
in the destination transform object.
Only transforms that have unique inverses are
reversible.
.P
If the transform is not invertible,
the error code SH_TRANS_INV is set.
.P
\f2src\f1
Specifies the transform object to be inverted.
.P
\f2dst\f1
Specifies the transform object for storing the
inverted transform.
If the source and destination objects are the same,
the transform is replaced with its inverse.
.H 4 "RETURNED VALUE"
.P
Destination transform.
If the source transform is not reversible,
NULL is returned.
.H 4 "SEE ALSO"
.P
Inverse_Point
.H 4 "NAME"
.P
Mul_Transform \- Multiplies the first transform by
the second and stores the product in the
destination transform object.
.IX "Mul_Transform"
.tm .CE U 3 "Mul_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Mul_Transform\f2(dst, trans1, trans2)\f1
.br
TRANSFORM dst;
.br
TRANSFORM trans1;
.br
TRANSFORM trans2;
.H 4 "DESCRIPTION"
.P
Multiplies two transforms and stores the product
in the destination transform object.
The type of the destination transform after the multiplication
depends on the types of the two operands.
If either transform is float,
the destination is also float.
.P
Mul_Transform preconcatenates, that is to say,
the last argument to Mul_Transform is also the last
transform to take effect when multiplied with a point.
For example, destination transform,
produced by the following code,
scales then translates:
.SS
{
TRANSFORM trans1, trans2, trans3;
POINT p;
float sx, sy, tx, ty;
.
.
.
Translate_Transform(trans1, Point_F2D(&p, tx, ty));
Scale_Transform(trans2, Point_F2D(&p, sx, sy));
.sp 1v
Mul_Transform(dst, trans2, trans1); /* scale then translate */
}
.ft1
.SE
.P
\f2dst\f1
Specifies the transform object in which to store
the product of the multiplication.
.P
\f2trans1\f1
Specifies a transform to be multiplied.
.P
\f2trans2\f1
Specifies a transform multiplier.
Matrix multiplication is not commutative \(em
the matrices must be specified in the appropriate order.
.H 4 "RETURNED VALUE"
.P
Handle of destination TRANSFORM
.H 4 "SEE ALSO"
.P
Rotate_Transform
.br
Scale_Transform
.br
Translate_Transform
.H 4 "NAME"
.P
Point_Transform \- Transforms the specified point.
.IX "Point_Transform"
.tm .CE U 3 "Point_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Point_Transform\f2(trans, p)\f1
.br
TRANSFORM trans;
.br
POINT *p;
.H 4 "DESCRIPTION"
.P
Transforms the specified point.
.P
\f2trans\f1
Specifies the transform object to use.
.P
\f2p\f1
Specifies the point to be transformed.
The point may be relative,
e.g., MOVEREL or LINEREL.
If the point type is relative,
the translation factor of the
transform is not applied.
This is useful when transforming distance,
rather than positions,
and preserves the notion of relative positioning.
.H 4 "RETURNED VALUE"
.P
[None]
.H 4 "SEE ALSO"
.P
InversePoint_Transform
.H 4 "NAME"
.P
Read_Transform \- Reads transform data into a 4\|\(mu\|4 matrix and
converts the data to the specified type.
.IX "Read_Transform"
.tm .CE U 3 "Read_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Read_Transform\f2(trans, matrix, type)\f1
.br
TRANSFORM trans;
.br
MATRIX matrix;
.br
TRANS_type type;
.H 4 "DESCRIPTION"
.P
Reads transform data into a 4\|\(mu\|4 matrix and converts the data to the
specified type,
which is either TRANS_BIN or TRANS_FLT.
.P
\f2trans\f1
Specifies the transform object to be written.
.P
\f2matrix\f1
Specifies the matrix into which the transform object is to be read.
.P
\f2type\f1
Specifies the data type (TRANS_FLT or TRANS_BIN) of the matrix.
.H 4 "RETURNED VALUE"
.P
Integer,
representing the transform type.
.H 4 "SEE ALSO"
.P
Write_Transform
.H 4 "NAME"
.P
Rotate_Transform \-  Rotates the specified number of radians
around the designated axis.
.IX "Rotate_Transform"
.tm .CE U 3 "Rotate_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Rotate_Transform\f2(trans, axis, A)\f1
.br
TRANSFORM trans;
.br
TRANS_axis axis;
.br
float or fract angle A;
.H 4 "DESCRIPTION"
.P
Concatenates a transform to rotate the specified
number of radians about the specified axis,
storing the result in the designated transform object.
The result of the concatenation is the original matrix
multiplied by the matrix outlined below,
which is the equivalent of the following:
.sp 1v
	Mul_Transform(trans, rot_matrix, trans).
.sp 1v
.EQ
{
TRANS_AXIS_Z ~=~ left [
   matrix {
      ccol { cos (A) above - sin (A) above 0 above 0 }
      ccol { sin (A) above cos (A) above 0 above 0 }
      ccol { 0 above 0 above 1 above 0 }
      ccol { 0 above 0 above 0 above 1 }
  }
right ]
}
.EN
.P
The matrix specification is commutative \(em
the matrices must be specified in order.
The type of transformation is unchanged.
.P
For example,
each of the following calls to Rotate_Transform preconcatenates
in a rotation of 180 degrees around the z-axis.
.SS
#include <math.h>
 .
TRANSFORM trans1, trans2;
 .
 .
.sp 1v
Rotate_Transform(trans1, TRANS_AXIS_Z | TRANS_ANGLE_DEGREES |
        TRANS_ANGLE_FRACT, fracti(180));
		
Rotate_Transform(trans2, TRANS_AXIS_Z, M_PI);
.ft1
.SE		
.P
\f2trans\f1
Specifies the transform object to be concatenated.
.P
\f2axis\f1
Specifies the axis of the rotation,
TRANS_AXIS_Z
.P
You may also specify how the angle is interpreted
(float or fract) and the coordinate system for the angle
(degrees or radians).
The default is for radians in floating point.
Note that the type of the angle does
\f2not\f1
influence the type of the transform returned.
The angle will be converted to the type of the transform
if necessary.
.TB "Transform Angle Type"
.TS
box tab (/);
cf4I | cf4I
l | l.
Type/Description
=
TRANS_ANGLE_DEGREES/Angle data in degrees
.br
TRANS_ANGLE_FRACT/Angle data as a fract
.TE
.TT
.P
\f2angle\f1
Specifies the number of radians in the rotation.
You may choose to specify degrees if you set the
appropriate axis flags.
.H 4 "RETURNED VALUE"
.P
TRANSFORM
.H 4 "SEE ALSO"
.P
Scate_Transform
.br
Rotate_Transform
.br
Mul_Transform
.H 4 "NAME"
.P
Scale_Transform \- Concatenates the specified transform with scale factors
from the specified point.
.IX "Scale_Transform"
.tm .CE U 3 "Scale_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Scale_Transform\f2(trans, p)\f1
.br
TRANSFORM transform;
.br
POINT *p;
.H 4 "DESCRIPTION"
.P
Concatenates the specified transform with scale
factors from the specified point \f2p\f1\&.
The type of the resulting transform is the type of the point
\f2p\f1\&.
The result of the concatenation is the original matrix multiplied by
the matrix outlined below,
which is equivalent to:
.sp 1v
Mul_Transform(trans, scale_matrix, trans).
.sp 1v
.sp 1v
.EQ
left [
matrix {
   ccol { P sub x above 0 above 0 above 0 }
   ccol { 0 above P sub y above 0 above 0 }
   ccol { 0 above 0 above 0 above 0 }
   ccol { 0 above 0 above 0 above 1 }
  }
right ]
.EN
.P
The matrix specification is commutative \(em
the matrices must be specified in order.
.P
\f2trans\f1
Specifies the transform object to be concatenated.
.P
\f2p\f1
Specifies the amount of x- and y-scaling.
The type of the output transform is determined by
both the type of the point and the type of the input transform.
If either has any floating point,
the output transform will be floating point.
.H 4 "RETURNED VALUE"
.P
TRANSFORM
.H 4 "SEE ALSO"
.H 4 "NAME"
.P
Set_Transform \- Sets the specified transform attribute.
.IX "Set_Transform"
.tm .CE U 3 "Set_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Set_Transform\f2(trans, attr, setting)\f1
.br
TRANSFORM trans;
.br
TRANS_attr attr;
.br
<attribute type> setting;
.H 4 "DESCRIPTION"
.P
Sets the specified transform attribute to the designated setting.
Only the TRANS_TYPE attribute may be set,
and only into TRANS_FLT or TRANS_BIN.
Setting the type of a transform causes it to convert
from one numeric type to another.
.P
In setting the TRANS_TYPE from float to fract,
you can cause numeric overflow.
It is your responsibility to ensure that this
does not occur.
.P
\f2trans\f1
Specifies the transform for which the attribute is to be set.
.P
\f2attr\f1
Specifies the attribute that is to be set.
.P
\f2setting\f1
Specifies the attribute setting.
.H 4 "RETURNED VALUE"
.P
[None]
.H 4 "SEE ALSO"
.P
Get_Transform
.H 4 "NAME"
.P
Temp_Transform \- Creates a transform object with an initial reference count
of zero.
.IX "Temp_Transform"
.tm .CE U 3 "Temp_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Temp_Transform\f2(type, root)\f1
.br
TRANS_type type;
.br
RASTER root;
.H 4 "DESCRIPTION"
.P
Creates a transform object with no initial reference count.
This temporary object is useful for passing the transform
as an argument to another function.
.sp 1v
If the transform is associated with a context,
the transform object is destroyed when the context
object is destroyed.
.P
\f2type\f1
Specifies the type of transform to be created.
.br
.TB "Transform Types"
.TS H
box tab(/);
cf4I | cf4I
l | l.
Type/Description
=
.TH
TRANS_BIN/T{
Fract (fixed point binary) transform.
T}
_
TRANS_FLT/Floating point transform.
_
TRANS_GENERIC/T{
A combination of the above types that is efficient for this implementation.
.sp 1v
TRANS_GENERIC applies only to Create_Transform.
T}
.TE
.TT
.P
\f2root\f1
This argument is currently unused.
Specify NULL for all transforms.
.H 4 "RETURNED VALUE"
.P
TRANSFORM
.H 4 "SEE ALSO"
.P
Create_Transform
.br
Destroy_Transform
.H 4 "NAME"
.P
Translate_Transform \- Translates the designated
transform object by the specified amount.
.IX "Translate_Transform"
.tm .CE U 3 "Translate_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Translate_Transform\f2(trans, p)\f1
.br
TRANSFORM trans;
.br
POINT *p;
.H 4 "DESCRIPTION"
.P
Concatenates the specified transform object to
translation by \f2p\f1\&.
The type of the resulting transform reflects the
interaction between the type of
the point and the transform.
The result of the concatenation is the original
matrix multiplied by the matrix outlined below,
which is equivalent to:
.sp
Mul_Transform(trans, trans_matrix, trans).
.sp 1
.EQ
left [
matrix {
   ccol { 1 above 0 above 0 above P sub x }
   ccol { 0 above 1 above 0 above P sub y }
   ccol { 0 above 0 above 1 above 0 }
   ccol { 0 above 0 above 0 above 1 }
  }
right ]
.EN
.P
The matrix specification is commutative \(em
the matrices must be specified in
order.
.P
\f2trans\f1
Specifies the transform object to be concatenated.
.P
\f2p\f1
Specifies the amount of x- and y-scaling.
The type of the output transform is determined by
both the type of the point and the type of the input transform.
If either has any floating point,
the output transform will be floating point.
.H 4 "RETURNED VALUE"
.P
TRANSFORM,
which reflects the concatenated transform.
.H 4 "SEE ALSO"
.P
Rotate_Transform
.br
Scale_Transform
.br
Mul_Transform
.H 4 "NAME"
.P
Transpose_Transform \- Transposes the source transform and stores the
transposition in the destination transform.
.IX "Transpose_Transform"
.tm .CE U 3 "Transpose_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Transpose_Transform\f2(dst, src)\f1
.br
TRANSFORM dst;
.br
TRANSFORM src;
.H 4 "DESCRIPTION"
.P
Transposes the first transform and stores the
transposition in the second transform.
The rows of a transposed matrix are equivalent to the columns of
the original matrix;
that is, the first first column of the original
matrix becomes the first row of the transposed matrix.
The matrix diagonals remain the same.
For example:
.PC
	a  e  i  m              a  b  c  d
	b  f  j  n              e  f  g  h
	c  g  k  o   becomes    i  j  k  l
	d  h  l  p              m  n  o  p
.ft1
.SF
.P
\f2trans1\f1
Specifies the transform object in which the transposition is stored.
.P
\f2trans2\f1
Specifies the transform object to be transposed.
Both trans1 and trans2 may be the same transform.
.H 4 "RETURNED VALUE"
.P
Destination TRANSFORM
.H 4 "SEE ALSO"
.H 4 "NAME"
.P
Write_Transform \- Writes the data from the specified matrix into the
transform object.
.IX "Write_Transform"
.tm .CE U 3 "Write_Transform" \n(PN
.H 4 "SYNOPSIS"
.P
\f3Write_Transform\f2(trans, matrix, type)\f1
.br
TRANSFORM trans;
.br
MATRIX matrix
.br
TRANS_type type;
.H 4 "DESCRIPTION"
.P
Writes the data from the specified matrix into the
transform object.
The \f2type\fP argument specifies the type of the data.
.P
\f2trans\f1
Specifies the transform object into which the matrix is written.
.P
\f2matrix\f1
Specifies the matrix from which the data is read.
.P
\f2type\f1
Specifies the type of the data and the resulting transform object.
Informs Shapes whether the data is TRANS_BIN or TRANS_FLT,
where TRANS_BIN is a fract and TRANS_FLT is a float.
.\" BEGIN SHAPES-----------------------------------------------
.if !"\*(Lb"Paint" \{\
.br
Optionally, you may also logically OR in the optimization type,
if you have determined it.
Look at the discussion of attribute TRANS_TYPE for
a list of the optimization types.
.br \}
.\"  ENDIF SHAPES----------------------------------------------
.P
Matrix operations will not work if the parameter
type is described erroneously.
.H 4 "RETURNED VALUE"
.P
TRANSFORM, representing trans
.H 4 "SEE ALSO"
.P
Read_Transform
.H 2 "Transform Attribute"
.IX "Transform attribute"
.H 4 "NAME"
.P
TRANS_TYPE
.IX "TRANS_TYPE"
.tm .CE U 3 "TRANS_TYPE" \n(PN
.H 4 "DESCRIPTION"
.P
TRANS_TYPE indicates whether the matrix contains
float or fract data and whether the matrix is 2D or 3D.
.\" BEGIN SHAPES-----------------------------------------------
.if !"\*(Lb"Paint" \{\
.br
In addition, TRANS_TYPE, by means of the optimization type,
provides internal clues to Shapes as to the complexity of a matrix.
Your only opportunity to change the TRANS_TYPE is
when calling Create_Transform or Write_Transform.
The optimization type of TRANS_TYPE are changed
by matrix multiplication operations.
.br \}
.\"  ENDIF SHAPES----------------------------------------------
.SK
.TB "Trans Types"
.TS
box tab(/);
cf4I | cf4I
l | lw(4.5i).
Type/Description
=
.\" BEGIN Paint------------------------------------------------
.if "\*(Lb"Paint" \{\
.br
TRANS_2D/T{
Only six elements in 4\|\(mu\|4 matrix represent a 2D transform.
These elements are comprised of the 2\|\(mu\|2 matrix in
the upper-left corner and the first two
elements of the bottom row.
Specifying a 2D transform when appropriate
optimizes performance.
T}
.br \}
_
.\"  ENDIF Paint------------------------------------------------
TRANS_BIN/T{
Handles transform numerical data as fixed-point integers (fracts).
T}
_
TRANS_FLT/T{
Handles transform numerical data as floating-point numbers.
When you set
TRANS_TYPE to TRANS_FLT,
you convert the matrix data to float.
T}
.TE
.TT
.\" BEGIN SHAPES-----------------------------------------------
.if !"\*(Lb"Paint" \{\
.br
.P
.TB "Transform Optimization Types"
.TS
box tab(/);
cf4I | cf4I
l | lw(4.5i).
Optimization Types/Description
=
TRANS_IDENTITY/T{
Identity matrix.
There is no reason to OR any other optimization types
with this type.
T}
_
TRANS_TRANSLATE/T{
Translation matrix.
The matrix has been acted upon by Translate_Transform
or contains translation data in the bottom row.
T}
_
TRANS_SCALE/T{
Scaling matrix.
Components of diagonal are not equal to one.
The matrix has been acted upon by Scale_Transform
or contains scaling data.
T}
_
TRANS_ROTATE/T{
Rotation matrix.
The matrix has been acted upon by Rotate_Transform
or the non-diagonal components of the upper 3\|\(mu\|3 matrix are
non-zero.
T}
_
TRANS_GEN/T{
General matrix.
It may have perspective (last row and last column
contain non-identity data.)
T}
_
TRANS_ALL/T{
TRANS_GEN|TRANS_ROTATE|TRANS_SCALE|TRANS_TRANSLATE
T}
.TE
.TT
.br \}
.\"  ENDIF SHAPES----------------------------------------------
.H 4 "RETURNED VALUE"
.P
TRANS_type
.H 4 "SEE ALSO"
.P
