MFB(3)

NAME
mfb - model frame buffer interface

SYNOPSIS
#include <~cad/include/mfb.h> in the program source.
cc [ flags ] files ~cad/lib/mfb.a -lm [ libraries ]

DESCRIPTION

These routines provide the user with a virtual graphics interface. They perform the terminal dependent task of encodingdecoding graphics code, thereby allowing the user to write graphics programs to run on almost any graphics device.

The user opens and initializes a graphics device by calling the MFBOpen routine that returns a pointer to that device's MFB data structure defined at the end of this manual. By maintaining several MFB data structures, an application program can drive several graphics devices simultaneously. Once opened, MFB graphics routines can be called to draw geometries, draw graphics text, set device parameters, or receive keyboard input. An application program can also use any of the several utility routines that perform line clipping, polygon clipping, or windowviewport transformations. Control of the graphics device is released by calling the MFBClose routine.

All programs that use MFB routines must include the file mfb.h that defines the MFB data structure to contain the information provided by MFBCAP(5).

INITIALIZATION ROUTINES

MFB *MFBOpen(TerminalName, DeviceName, errorcode)
char *TerminalName, *DeviceName;
int *errorcode;
    MFBOpen initializes the graphics device and fills the MFB data structure with information found in MFBCAP(5). TerminalName is a pointer to a null terminated string containing the name of the graphics device as defined in the mfbcap database file. This argument has no default and can never be null. DeviceName is a pointer to a null terminated string containing the full path name to the respective graphics device. If null, stdin and stdout are used by default. errorcode is a diagnostic integer returned by MFBOpen. The possible returned values for errorcode are defined in the mfb.h file as follows:

    #define	MFBOK	 1	/* successful return */
    #define	MFBBADENT	-10	/* Unknown terminal type */
    #define	MFBBADMCF 	-20	/* Can't open MFBCAP file */
    #define	MFBMCELNG 	-30	/* MFBCAP entry too long */
    #define	MFBBADMCE 	-40	/* Bad MFBCAP entry */
    #define	MFBINFMCE 	-50	/* infinite loop in MFBCAP entry */
    #define	MFBBADTTY 	-60	/* stdout not in /dev */
    #define	MFBBADDEV	-180	/* Can't open or close device */
    #define	MFBBADOPT	-190	/* Can't access or set device stat */
    #define	MFBBADWRT 	-220	/* Error during write */

    Only MFBOK is not a fatal error.

void SetCurrentMFB(mfb)
MFB *mfb;
    SetCurrentMFB allows the application program to define the current graphics device. All subsequent calls to MFB routines will affect the specified device. Because each MFB data structure contains a separate output buffer, it is not necessary to flush the output before resetting the current output device. MFBOpen returns with the opened graphics device defined as the current output device.

int MFBInitialize()
    MFBInitialize will flush the output buffer and (re)initialize the device for graphics input. The graphics device or standard input will be placed in CBREAK mode. See the manual tty(4). MFBOK is returned if the device was successfully initialized; MFBBADOPT is returned if an error was encountered while attempting to access or set the device status, and MFBBADTTY is returned if standard output can bot be found or accessed.

int MFBClose()
    MFBClose will flush the output buffer and release control of the graphics device driver. If the graphics device is a tty, it is returned to the state that existed prior to the respective MFBOpen call. MFBOK is returned if the device was successfully closed; MFBBADOPT is returned if an error was encountered while attempting to access or set the device status, and MFBBADDEV is returned if the output device could not be closed.

int MFBHalt()
    MFBHalt will flush the output buffer and release control of the graphics device driver. If the graphics device is a tty, it is returned to the state that existed prior to the respective MFBOpen call. MFBHalt differs from MFBClose in that the memory occupied by the respective, current MFB data structure is not freed. By calling MFBInitialize, the graphics device will be reinitialized. This routine is typically used by an application program for handling the SIGTSTP signal (the keyboard stop signal, usually control-Z ). MFBOK is returned if the device was successfully returned to its initial state; MFBBADOPT is returned if an error was encountered while attempting to access or set the device status.

SETTING DEVICE PARAMETERS

Each of the following routines for setting device parameters returns a diagnostice integer that is defined in the mfb.h file as follows:

#define	MFBOK	 1	/* successful return */
#define	MFBBADLST 	-70	/* Illegal line style */
#define	MFBBADFST 	-80	/* Illegal fill style */
#define	MFBBADCST	-90	/* Illegal color style */
#define	MFBBADTM1	-100	/* No destructive text mode */
#define	MFBBADTM2	-110	/* No overstriking text mode */
#define	MFBNOBLNK 	-150	/* No definable blinkers */
#define	MFBTMBLNK 	-160	/* Too many blinkers */
#define	MFBNOMASK	-170	/* No definable read or write mask */
#define	MFBBADALU	-250	/* Cannot set ALU mode */

int MFBSetLineStyle(styleId)
int styleId;
    MFBSetLineStyle sets the current line style to that identified by the integer styleId that is greater than or equal to zero and less than the value of maxLineStyles in the MFB data structure. The value of maxLineStyles can be obtained from the MFBInfo routine defined below. Zero is always the styleId for solid lines. Except for the solid line style, MFB assumes no default set of lines styles. MFBOK is returned if the line style was successfully set to that specified by styleId or if styleId was already the current line style; MFBBADLST is returned if styleId has an illegal value.

int MFBSetFillPattern(styleId)
int styleId;
    MFBSetFillPattern sets the current fill pattern to that identified by the integer styleId that is greater than or equal to zero and less than the value of maxFillPatterns in the MFB data structure. The value of maxFillPatterns can be obtained from the MFBInfo routine defined below. Solid fill is always defined by styleId equal to zero. Other than solid fill, MFB assumes no default set of fill patterns. MFBOK is returned if the fill style was successfully set to that specified by styleId or if styleId was already the current fill style; MFBBADFST is returned if styleId has an illegal value.

int MFBSetChannelMask(channelMask)
int channelMask;
    MFBSetChannelMask defines the current write mask to be the value of channelMask. The channel mask allows specific memory planes to be written and erased without disturbing other memory planes. The least significant bit of channelMask corresponds to the masked value of the first memory plane, etc. If the corresponding bit is zero, the memory plane is write-protected. The number of memory planes can be obtained from the MFBInfo routine defined below. MFBOK is returned if the write mask was successfully set to channelMask or if channelMask was already the current write mask; MFBNOMASK is returned if the graphics device does not have a definable write mask.

int MFBSetReadMask(readmask)
int readmask;
    MFBSetReadMask defines the current read mask to be the value of readmask. The read mask allows only specific memory planes to be read. MFBOK is returned if the read mask was successfully set to readMask or if readMask was already the current read mask; MFBNOMASK is returned if the graphics device does not have a definable read mask.

int MFBSetColor(colorId)
int colorId;
    MFBSetColor sets the current foreground color to that identified by the integer colorId that is greater than or equal to zero and less than the value of maxColors in the MFB data structure. The value of maxColors can be obtained from the MFBInfo routine defined below. There is no default color map in MFB. MFBOK is returned if the foreground color was successfully set to that specified by colorId or if colorId was already the current foreground color; MFBBADCST is returned if colorId has an illegal value.

int MFBSetTextMode(destructiveBool)
Bool destructiveBool;
    MFBSetTextMode defines whether subsequent graphics text will overstrike or replace previous text. If destructiveBool is true, the text mode is set to destructive which means that graphic text will set the background color of the font grid to the color that is specified by color style zero depending on the currently defined ALU operation. Overstriking mode will only set the pixels of the character font to the current foreground color. MFBOK is returned if the graphic text writing mode was successfully set to that specified by destructiveBool or if destructiveBool was already the current graphic text writing mode; MFBBADTM1 is returned if the graphics device does not have a destructive graphic text mode, and MFBBADTM2 is returned if the graphics device does not have an overstriking graphic text mode.

int MFBSetALUMode(alumode)
int alumode;
    MFBSetALUMode changes the mode by which the graphics display is changed when an area of the display is over-written. The four possible modes are JAM (replace mode), OR, EOR (exclusive OR), and NOR. The four valid arguments to MFBSetALUMode are defined in mfb.h as follows:

    #define	MFBALUJAM 	0	/* set ALU mode to JAM */
    #define	MFBALUOR	1	/* set ALU mode to OR */
    #define	MFBALUNOR	2	/* set ALU mode to NOR */
    #define	MFBALUEOR	3	/* set ALU mode to EOR */

    MFBOK is returned if the ALU mode was successfully set to that specified by alumode or if alumode was already the current ALU operation; MFBBADALU is returned if the graphics device does not have the ALU mode specified by alumode or if alumode is an invalid or illegal argument.

int MFBSetCursorColor(colorId1, colorId2)
int colorId1, colorId2;
    MFBSetCursorColor sets the graphics cursor to blink between the two colors identified by colorId1 and colorId2. The constraints on the values for colorId1 and colorId2 are the same as for MFBSetColor defined above. The frequency of the blinking cursor is fixed and can be changed only by modifying the mfbcap database file. MFBOK is returned if the blinking cursor colors were successfully set to the specified colors.

int MFBSetRubberBanding(onFlag, X, Y)
int X, Y;
Bool onFlag;
    MFBSetRubberBanding enables/disables rubber banding of the pointing device. If onFlag is false, then rubber banding is disabled. When enabled, the center of rubber banding is at X, Y. Rubber banding is always disabled immediately after the pointing device has been used. MFBOK is returned if the rubberbanding mode was successfully set to that specified by onFlag; MFBNORBND is returned if the graphics device does not have rubberbanding in the pointing device.

int MFBSetBlinker(colorId, red, green, blue, onFlag)
int colorId;
int red, green, blue;
int onFlag;
    MFBSetBlinker enables the color identified by colorId to blink between its currently defined color and the color defined by the red, green, blue combination. The values of red, green, and blue are normalized to 1000. If onFlag is zero, the blinking is disabled. The number of colors that may be defined as blinkers at any given time must be less than the value of maxBlinkers in the MFB data structure. The frequency of the blinking colors is fixed and can be changed only by modifying the mfbcap database file. MFBOK is returned if the color specified by colorId was successfully set to the desired blinking mode; MFBNOBLNK is returned if the graphics device does not have blinking VLT layers, and MFBTMBLNK is returned if there are already too many active blinking layers.

DEFINING DEVICE PARAMETERS

Each of the following routines for defining device parameters returns a negative value if any difficulty is encountered. The possible returned integers are defined in mfb.h as follows:

#define	MFBOK	 1	/* successful return */
#define	MFBNODFLP 	-120	/* No definable line patterns */
#define	MFBNODFFP 	-130	/* No definable fill patterns */
#define	MFBNODFCO 	-140	/* No definable colors */

int MFBDefineColor(colorId, red, green, blue)
int colorId;
int red, green, blue;
    MFBDefineColor redefines the VLT entry for the color identified by colorId to be the color represented by the red, green, blue combination where red, green, and blue are normalized to 1000. Once the color corresponding to colorId is redefined, all geometries that were written onto the display of a frame buffer with colorId as the current color will become the new color. MFBOK is returned if the VLT entry for colorId was successfully defined; MFBNODFCO is returned if the graphics device does not have a VLT.

int MFBDefineFillPattern(styleId, BitArray)
int styleId;
int *BitArray;
    MFBDefineFillPattern redefines the fill pattern identified by styleId and returns with styleId as the current fill style. BitArray is a pointer to an array of eight integers whose least significant eight bits represent individual rows in an eight by eight intensity array. For example, a fill pattern with an ascending diagonal line may be defined by the following eight (decimal) integers:

        1 2 4 8 16 32 64 128 256

    A diagonal-grid fill pattern can be defined with the following integer array:

        257 130 68 40 40 68 130 257

    MFBOK is returned if the new fill style for styleId was successfully defined; MFBNODFFP is returned if the graphics device does not have definable fill patterns.

int MFBDefineLineStyle(styleId, Mask)
int styleId;
int Mask;
    MFBDefineLineStyle defines the line style identified by styleId to be the pattern contained in the eight least significant bits of Mask and returns with styleId as the current line style. MFBOK is returned if the line style for styleId was successfully defined; MFBNODFFP is returned if the graphics device does not have definable line patterns.

INPUTOUTPUT ROUTINES

int MFBUpdate()
    MFBUpdate flushes the internal output buffer to the currently defined output device and will ignore any write error that may occur. A call to this routine is ABSOLUTELY necessary to complete any graphics display sequence. MFBUpdate returns the number of characters sent to the output graphics device or -1 if a write error occured.

int MFBPoint(X, Y, key, button)
int *X, *Y, *button;
char *key;
    MFBPoint enables the graphics pointing device and then waits for user input. If a keyboard key is pressed, MFBPoint returns with key containing the character that was pressed. If the pointing device is pressed, MFBPoint returns with the identified viewport coordinate X, Y, the contents of key equal to zero, and the button mask of the button that was pushed. The integer array buttonMask in the MFB data structure contains all possible button mask values that can be returned. MFBPoint returns one of the following values defined in the mfb.h file:

    #define	MFBOK	 1	/* successful return */
    #define	MFBPNTERR 	-230	/* Error in pointing device */
    #define	MFBNOPTFT 	-240	/* No pointing format */
    #define	MFBNOPNT	-260	/* No pointing device */

char *MFBKeyboard(X, Y, background, foreground)
int background;
int foreground;
int X, Y;
    MFBKeyboard enables the graphics keyboard and waits for user input. A pointer to a character buffer containing the keyboard input is returned by MFBKeyboard when the user presses the return or linefeed key. Backspace is control-H or the delete character, and control-X or control-U will kill the line. Pressing the ESCAPE key will cause MFBKeyboard to return with a null string in the input character buffer.

    All keyboard input is displayed in the viewport with the lower left corner at the viewport coordinate X, Y and is constrained to fit on one line. Background and foreground are the background and foreground color styles respectively in which the keyboard input will be displayed.

void MFBAudio()
    MFBAudio will ring the bell or alarm on the graphics device. If the graphics device does not have a bell, then a control-G will be sent to standard output.

int MFBPutchar(c)
char c;

int MFBPutstr(cp,nchars)
int nchars;
char *cp;

int MFBGetchar()
    These three routines are used internally by MFB and typically are not used within an application program. They are comparable to the stdio routines having similar names. MFBPutchar places a character c in the output buffer. MFBPutstr inserts a string pointed to by cp containing nchars characters into the output buffer. The nchars argument is necessary to permit embedded null characters in the output stream. The characters remain in the output buffer until the next call to MFBUpdate or until the contents of the output buffer exceed 4096 characters.

    MFBGetchar returns a single character from the graphics input device. If the graphics device does not have a keyboard, input is obtained from the terminal from which the application program was invoked. If the graphics device is a tty, it should be remembered that it is in CBREAK mode.

TWO DIMENSIONAL GEOMETRY ROUTINES

All coordinates that are passed to the following geometry routines are with respect to the display resolution of the graphics device. MFB assumes that the lower, left corner of the display is the origin with an absolute coordinate (0, 0). All coordinate values are positive integers.

void MFBMoveTo(X1, Y1)
int X1, Y1;
    MFBMoveTo sets the current graphics position to X1, Y1. No line will be drawn from the old graphics position.

void MFBDrawLineTo(X1, Y1)
int X1, Y1;
    MFBDrawLineTo draws a line from the current graphics position to X1, Y1 in the current line style and color. The current graphics position then becomes X1, Y1.

void MFBLine(X1, Y1, X2, Y2)
int X1, Y1, X2, Y2;
    MFBLine draws a line in the current line style and color from X1, Y1 to X2, Y2.

void MFBBox(left, bottom, right, top)
int left, bottom, right, top;
    MFBBox displays a rectangle in the current fill pattern and color with diagonal coordinates at left, bottom and right, top.

void MFBDrawPath(path)
MFBPATH *path;
    MFBDrawPath draws a path of vectors in the current line style and color. Path is a pointer to a data structure defined in the mfb.h file as follows:

    struct mfbpath {
    	int nvertices;	/* number of (x,y) coordinate pairs */
    	int *xy;	/* pointer to array of (x,y) coordinates */
    	};
    typedef struct mfbpath MFBPATH;

    The contents of the coordinate array are organized such that xy[0] is the x coordinate of the first vertex, xy[1] is the y coordinate of the first vertex, xy[2] is the x coordinate of the second vertex, etc.

void MFBFlood()
    MFBFlood erases a frame buffer display to the current color as previously defined by MFBSetColor. The result would be the same as drawing a solid box over the entire display.

void MFBPixel(X, Y)
int X, Y;
    MFBPixel sets the pixel at location X, Y on the display to the current color as previously defined by MFBSetColor.

void MFBCircle(X, Y, rad, nsides)
int X, Y, rad, nsides;
    MFBCircle draws the perimeter of a circle in the current line style and color with center at X, Y and with radius rad. The argument nsides is the number of line segments with which the circle will be drawn if the frame buffer does not have a circle primitive. The default value for nsides is twenty.

void MFBFlash(X, Y, rad, nsides)
int X, Y, rad, nsides;
    MFBFlash draws a round flash with the current fill pattern and color with center at X, Y and radius rad. The argument nsides is the number of line segments with which the flash will be drawn. The default value for nsides is twenty.

void MFBArc(X, Y, rad, angle1, angle2, nsides)
int X, Y, rad;
int angle1, angle2, nsides;
    MFBArc draws an arc in the current line style and color with center at X, Y and with radius rad beginning at angle1 with respect to the positive y-axis and ending at angle2 in a counter-clockwise direction. Both angles are in degrees and are greater than or equal to zero and less than or equal to 360. The argument nsides is the number of line segments with which a 360 degree arc will be drawn. The default value for nsides is twenty.

void MFBPolygon(poly)
MFBPOLYGON *poly;
    MFBPolygon draws a polygon with the current fill pattern and color. Poly is a pointer to a data structure defined in the mfb.h file as follows:

    struct mfbpolygon {
    	int nvertices;	/* number of (x,y) coordinate pairs */
    	int *xy;	/* pointer to array of (x,y) coordinates */
    	};
    typedef struct mfbpolygon MFBPOLYGON;

    The contents of the coordinate array are organized such that xy[0] is the x coordinate of the first vertex, xy[1] is the y coordinate of the first vertex, xy[2] is the x coordinate of the second vertex, etc. The difference between the MFBPOLYGON typedef and the MFBPATH typedef defined above is that the MFBPOLYGON struct is assumed to define a closed path of coordinates.

MFBPATH *MFBArcPath(X, Y, rad, angle1, angle2, nsides)
int X, Y, rad;
int angle1, angle2, nsides;
    MFBArcPath returns a pointer to a MFBPATH struct that contains an arc with center at X, Y and with radius rad beginning at angle1 with respect to the positive y-axis and ending at angle2 in a counter-clockwise direction. Both angles are in degrees and are greater than or equal to zero and less than or equal to 360. The argument nsides is the number of line segments with which the arc will be drawn. The default value for nsides is twenty.

MFBPOLYGON *MFBEllipse(X, Y, radx, rady, nsides)
int X, Y, rad, nsides;
    MFBEllipsePath returns a pointer to a MFBPOLYGON struct that contains an elliptical polygon with center at X, Y and with distance radx from the center to an edge along the x-axis and distance rady from the center to an edge along the y-axis. The argument nsides is the number of line segments with which the arc will be drawn. The default value for nsides is twenty.

void MFBText(text, X, Y, phi)
char *text;
int X, Y, phi;
    MFBText displays a null terminated string pointed to by text with the lower left corner at X, Y in the display viewport with the current color and rotated at the angle phi in degrees. The default value for phi is zero.

void MFBNaiveBoxFill(left, bottom, right, top)
int top, bottom, left, right;
    MFBNaiveBoxFill can be used to draw a filled rectangle on a graphics device that does not support fill patterns. The MFBLine routine is used to draw rectangles with eight different fixed fill styles. If the graphics device does not have a command primitive for drawing a box, then the MFBBox routine defined above defaults to MFBNaiveBoxFill.

RASTER ROUTINES

void MFBRasterCopy(X,Y,DX,DY,DestX,DestY);
int X,Y,DX,DY,DestX,DestY;
    MFBRasterCopy copies a rectangular area with the bottom, left corner at X,Y and with length DX in the X direcion and width DY in the Y direction to an area with the bottom, left corner at DestX,DestY. The mode of the copy operation was specified by the last call to MFBSetALUMode.

INFORMATION ACQUISITION

int MFBInfo(info);
int info;
    MFBInfo is a routine for obtaining device specific information. The possible values for info are defined in mfb.h as follows:

    #define	MAXX	1	/* max x coordinate */
    #define	MAXY	2	/* max y coordinate */
    #define	MAXCOLORS	3	/* max number of colors */
    #define	MAXINTENSITY	4	/* max color intensity */
    #define	MAXFILLPATTERNS	5	/* max number of fill patterns */
    #define	MAXLINESTYLES	6	/* max number of line styles */
    #define	MAXBLINKERS	7	/* max number of blinkers */
    #define	POINTINGDEVICE	8	/* terminal has pointing device */
    #define	POINTINGBUTTONS	9	/* pointing device has buttons */
    #define	NUMBUTTONS	10	/* num. of pointing dev. buttons */
    #define	BUTTON1	11	/* value returned by button 1 */
    #define	BUTTON2	12	/* value returned by button 2 */
    #define	BUTTON3	13	/* value returned by button 3 */
    #define	BUTTON4	14	/* value returned by button 4 */
    #define	BUTTON5	15	/* value returned by button 5 */
    #define	BUTTON6	16	/* value returned by button 6 */
    #define	BUTTON7	17	/* value returned by button 7 */
    #define	BUTTON8	18	/* value returned by button 8 */
    #define	BUTTON9	19	/* value returned by button 9 */
    #define	BUTTON10	20	/* value returned by button 10 */
    #define	BUTTON11	21	/* value returned by button 11 */
    #define	BUTTON12	22	/* value returned by button 12 */
    #define	TEXTPOSITIONALBE	30	/* Bool: positionable text */
    #define	TEXTROTATABLE	31	/* Bool: rotatable text */
    #define	FONTHEIGHT	32	/* font height in pixels */
    #define	FONTWIDTH	33	/* font width in pixels */
    #define	FONTXOFFSET	34 	/* font x offset in pixels */
    #define	FONTYOFFSET	35	/* font y offset in pixels */
    #define	DESTRUCTIVETEXT	36	/* Bool: text can be destructive */
    #define	OVERSTRIKETEXT	37	/* Bool: text can be overstrike */
    #define	VLT	38	/* Bool: terminal has VLT */
    #define	BLINKERS	39	/* Bool: terminal has blinkers */
    #define	FILLEDPOLYGONS	40	/* Bool: terminal can fill polygons */
    #define	DEFFILLPATTERNS	41	/* Bool: definable fill patterns */
    #define	DEFCHANNELMASK	42	/* Bool: definable write mask */
    #define	DEFLINEPATTERN	43	/* Bool: definable line styles */
    #define	CURFGCOLOR	44	/* current foreground color */
    #define	CURFILLPATTERN	45	/* current fill pattern */
    #define	CURLINESTYLE	46	/* current line style */
    #define	CURCHANNELMASK	47	/* current channel mask */
    #define	CURREADMASK	48	/* current read mask */
    #define	NUMBITPLANES	49	/* number of bit planes */
    #define	DEFREADMASK	50	/* Bool: definable read mask */
    #define	RASTERCOPY	51	/* Bool: term has raster copy */
    #define	OFFSCREENX	52	/* left of off screen memory */
    #define	OFFSCREENY	53	/* bottom of off screen memory */
    #define	OFFSCREENDX	54	/* length of off screen memory */
    #define	OFFSCREENDY	55	/* width of off screen memory */

    If an invalid argument is used, MFBInfo will return -1.

WINDOWVIEWPORT TRANSFORMATIONS

MFB provides a set of procedures for converting from window coordinates to viewport coordinates and vice versa. These transformation routines are NOT used by the MFB display routines and must be invoked separately by an application program.

void MFBSetViewport(left, bottom, right, top)
int left, bottom, right, top;

void MFBSetWindow(left, bottom, right, top)
int left, bottom, right, top;

int MFBScaleX(X)
int X;

int MFBScaleY(Y)
int Y;

int MFBDescaleX(X)
int X;

int MFBDescaleY(Y)
int Y;
    To use these routines, it is necessary to define both the viewport of the graphics display and the window in the working area by using MFBSetViewport and MFBSetWindow. The viewport must always be defined by non-negative integers that are within the resolution of the graphics display. Once defined, MFBScaleX and MFBScaleY will convert from window coordinate values to viewport coordinates. MFBDescaleX and MFBDescaleY will perform the inverse transformation. The transform routines return the scaled values.

GEOMETRY CLIPPING ROUTINES

MFB provides a set of routines for clipping lines and polygons to a given window.

void MFB_Y_Intercept(X1, Y1, X2, Y2, value, Yvalue)
int X1, Y1, X2, Y2;
int value;
int *Yvalue;
    MFB_Y_Intercept calculates the value Yvalue of the y coordinate at the point of intersection of a line defined by the two coordinates X1, Y1 and X2, Y2, and a vertical line with all x coordinates equal to value.

void MFB_X_Intercept(X1, Y1, X2, Y2, value, Xvalue)
int X1, Y1, X2, Y2;
int value;
int *Xvalue;
    MFB_X_Intercept calculates the value Xvalue of the x coordinate at the point of intersection of a line defined by X1, Y1 and X2, Y2, and a horizontal line with all y coordinates equal to value.

void MFBLineClip(X1, Y1, X2, Y2, left, bottom, right, top);
int *X1, *Y1, *X2, *Y2;
int left, bottom, right, top;
    The above clipping routines are used by MFBLineClip to clip the line segment defined by X1, Y1 and X2, Y2 to the window defined by left, bottom, right, and top.

void MFBPolygonClip(poly, top, bottom, left, right)
MFBPOLYGON *poly;
int top, bottom, left, right;
    MFBPolygonClip clips a polygon with less than 200 vertices defined by poly to the window defined by left, bottom, right, and top. poly is replaced by the clipped polygon.

MFBPATH *MFBArcClip(path, left, bottom, right, top)
MFBPATH *path;
int left, bottom, right, top;
    MFBArcClip clips an arc with less than 200 vertices defined by path to the window defined by left, bottom, right, and top. MFBClipArc returns a pointer to an array of five MFBPATH structs that define the clipped arc. The contents of several of these returned structs may define a null path.

SPECIAL VIEWPORT ROUTINES

void MFBMore(left, bottom, right, top, Textfile)
int left, bottom, right, top;
FILE *Textfile;
    MFBMore will display the contents of a file Textfile in a viewport defined by left, bottom, right, and top in a manner similar to the UCB program MORE(1).

void MFBScroll(left, bottom, right, top, Textfile)
int left, bottom, right, top;
FILE *Textfile;
    MFBScroll is an enhanced version of MFBMore defined above that allows you to scroll up or down through the contents of Textfile. The contents of Textfile are displayed in a viewport defined by left, bottom, right, and top.

DIAGNOSTICS

char *MFBError(errnum)
int errnum;
    MFBError can be used to obtain a null terminated string that describes the error associated with any of the above mentioned error codes. errnum is the error code returned by a MFB routine. MFBError returns a pointer to the error information string. The possible values for errnum are defined in mfb.h as follows:

    #define	MFBBADENT	-10	/* Unknown terminal type */
    #define	MFBBADMCF	-20	/* Can't open mfbcap file */
    #define	MFBMCELNG	-30	/* MFBCAP entry too long */
    #define	MFBBADMCE	-40	/* Bad mfbcap entry */
    #define	MFBINFMCE	-50	/* Infinite mfbcap entry */
    #define	MFBBADTTY	-60	/* stdout not in /dev */
    #define	MFBBADLST	-70	/* Illegal line style */
    #define	MFBBADFST	-80	/* Illegal fill style */
    #define	MFBBADCST	-90	/* Illegal color style */
    #define	MFBBADTM1	-100	/* No destructive text */
    #define	MFBBADTM2	-110	/* No overstriking text */
    #define	MFBNODFLP	-120	/* No definable line styles */
    #define	MFBNODFFP	-130	/* No definable fill styles */
    #define	MFBNODFCO	-140	/* No definable colors */
    #define	MFBNOBLNK	-150	/* No blinkers */
    #define	MFBTMBLNK	-160	/* Too many blinkers */
    #define	MFBBADDEV	-180	/* Can't open or close device */
    #define	MFBBADOPT	-190	/* Can't access or set device stat */
    #define	MFBNOMASK	-170	/* No definable read or write mask */
    #define	MFBBADWRT	-200	/* Error in write */
    #define	MFBPNTERR	-210	/* Error in pointing device */
    #define	MFBNOPTFT	-220	/* No format for pointing device */
    #define	MFBNOPNT	-230	/* No pointing device */
    #define	MFBNORBND	-240	/* No Rubberbanding */
    #define	MFBBADALU	-250	/* Cannot set ALU mode */

void MFBZeroCounters()

void MFBCounters(nCh,nBx,BxArea,nLn,LnLngth,nPxl)
int *nCh,*nBx,*BxArea,*nLn,*LnLngth,*nPxl;
    MFBCounters provides the ability to measure the communications bandwidth between the host and the graphics device. To use these routines, MFB must be compiled with the DEBUG flag defined in the mfb.h file.

    The procedure is initialized by invoking MFBZeroCounters after which the geometry display routines such as MFBBox or MFBLine may be called in any order. When MFBCounters is invoked, it will return the number of graphic text characters nCh that where displayed, the number of boxes nBx displayed, the number of lines nLn displayed, the average pixel area of a box BxArea, the average line length LnLngth in pixels, and the total number of pixels nPxl that where affected. Invocation of MFBCounters does not clear the the counters.

THE MFB DATA STRUCTURE

The MFB data structure is listed below.
#define	TTY	't'
#define	HCOPY	'r'
typedef enum {false, true} Bool;
struct mfb_window {
	int left;
	int right;
	int top;
	int bottom;
	double length,width;
	};
typedef struct mfb_window WINDOW;
typedef struct mfb_window VIEWPORT;
struct mfbpath {
	int nvertices;
	int *xy;
	};
typedef struct mfbpath MFBPOLYGON;
typedef struct mfbpath MFBPATH;
#ifndef vms
struct mfbremttyb {
	struct sgttyb oldttyb;
	struct sgttyb newttyb;
	};
struct mfbremstat {
	int graphttyw;	/* old mode bits of graphics device */
	int kybrdttyw;	/* old mode bits of standard I/O */
	struct stat graphstat;	/* old fstats of graphics device */
	struct stat kybrdstat;	/* old fstats of standard I/O */
	};
typedef struct mfbremttyb MFBSAVETTYB;
typedef struct mfbremstat MFBSAVESTAT;
#endif
struct mfbformatstrs {
	char *startSequence;	/* first transmitted sequence */
	char *endSequence;	/* last transmitted sequence */
	char *initLineStyles;	/* initialize line styles */
	char *initFillPatterns;	/* initialize fill styles */
	char *initColorStyles;	/* initialize color styles */
	char *vltEntry;	/* define color in VLT */
	char *setForegroundColor;	/* set current foreground color */
	char *screenFlood;	/* flood screen to current color */
	char *channelMaskSet;	/* set write mask */
	char *readMaskSet;	/* set read mask */
	char *enablePointingDevice;	/* initialize pointing device */
	char *enableRubberBanding;	/* turn on rubber banding */
	char *disablePointingDevice;	/* disable pointing device and cursor */
	char *disableRubberBanding;	/* turn off rubber banding */
	char *readPointingDevice;	/* wait and read pointing device */
	char *formatPointingDevice;	/* decode format for pointing device */
	char *keyboardStart;	/* initailize keyboard */
	char *keyboardEnd;	/* terminate keyboard input */
	char *keyboardBackspace;	/* keyboard backspace sequence */
	char *audio;	/* ring the terminals bell */
	char *lineDefineStart;	/* begin defining a line pattern */
	char *lineDefineFormat;	/* define bit array of line pattern */
	char *lineDefineEnd;	/* terminate line pattern definition */
	char *setLineStyle;	/* set current line style */
	char *setSolidLineStyle;	/* set current line style to solid */
	char *movePenSequence;	/* move current graphics position */
	char *drawLineSequence;	/* draw a line in current style */
	char *drawSolidLineSequence;	/* draw a solid line */
	char *drawLineToSequence;	/* move and draw current position */
	char *drawSolidLineToSequence;	/* move and draw solid line */
	char *drawBoxSequence;	/* draw box in current style */
	char *drawSolidBoxSequence;	/* draw a solid box */
	char *beginPlygnSequence;	/* begin polygon in cur. fill style */
	char *beginSolidPlygnSequence;	/* begin solid polygon */
	char *sendPlygnVertex;	/* define one point in polygon */
	char *endPlygnSequence;	/* terminate polygon sequence */
	char *drawCircleSequence;	/* draw a circle in solid line style */
	char *rotateTextSequence;	/* rotate graphic text */
	char *graphicsTextStart;	/* begin graphic text */
	char *graphicsTextEnd;	/* terminate graphic text */
	char *replaceON;	/* turn on destructive text mode */
	char *overstrikeON;	/* turn on overstriking text mode */
	char *writePixel;	/* write one pixel in current color */
	char *setALUEOR;	/* set ALU mode to EOR */
	char *setALUNOR;	/* set ALU mode to NOR */
	char *setALUOR;	/* set ALU mode to OR */
	char *setALUJAM;	/* set ALU mode to JAM or REPLACE */
	char *blinkerON;	/* make a color blink */
	char *blinkerOFF;	/* turn off a blinking layer */
	char *rastCopyStart;	/* begin raster copy sequence */
	char *rastCopyEnd;	/* terminate raster copy sequence */
	char *rastCopyDest;	/* define raster copy destionation */
	char *rastCopySource;	/* define raster copy source area */
	char *fillDefineStart;	/* begin defining a fill style */
	char *fillDefineFormat;	/* define bit array of row/column */
	char *fillDefineEnd;	/* terminate fill style definition */
	char *setFillPattern;	/* set current fill pattern */
	char *setSolidFillPattern;	/* set current fill pattern to solid */
	};
struct mfb {	/* MFB DATA STRUCT */
	/*
	* INTEGERS FIELDS
	*/
/* used for decode */	int lastX,lastY;	/* for Tektronix encoding */
	int X,Y,Z,T;	/* parameter list */
/* Resolution */	int maxX;	/* horizontal resolution */
	int maxY;	/* vertical resolution */
	int maxColors;	/* maximum number of colors */
	int minOffScreenX;	/* left of off screen memory */
	int minOffScreenY;	/* bottom of off screen mem. */
	int offScreenDX;	/* length of off screen mem. */
	int offScreenDY;	/* width of off screen mem. */
/* Video Layer Table */	int maxIntensity;	/* max RGB or LS intensity */
	int lengthOfVLT;	/* number of bit planes */
/* Pointing Device */	int buttonMask[12];	/* returned button masks */
	int numberOfButtons;	/* 12 maximum */
/* Keyboard Control */	int keyboardYOffset;
	int keyboardXOffset;
/* Line Drawing */	int lineDefineLength;	/* number of bytes in array */
	int maxLineStyles;	/* number of line styles */
/* Text font */	int fontHeight;	/* font height in pixels */
	int fontWidth;	/* font width in pixels */
	int fontXOffset;
	int fontYOffset;
/* Blinkers */	int maxBlinkers;	/* number of blinkers */
/* Fill Patterns */	int fillDefineHeight;	/* number of byte rows */
	int fillDefineWidth;	/* number of byte columns */
	int maxFillPatterns;	/* number of fill patterns */
/* Current variables */	int cursorColor1Id;	/* blinked cursor color ID */
	int cursorColor2Id;	/* unblinked cursor color ID */
	int fgColorId;	/* cur. foreground color ID */
	int fillPattern;	/* cur. fill pattern ID */
	int lineStyle;	/* cur. line style ID */
	int channelMask;	/* cur. write mask */
	int readMask;	/* cur. read mask */
	int numBlinkers;	/* cur. number of blinkers */
	int textMode;	/* text mode (1=dest, 0=rep) */
	int stipplePattern[8];	/* cur. stipple pattern */
	int fileDesc;	/* desc. for graphics device */
	int numTtyBuffer;	/* cur. chars in output queue */
	/*
	* POINTERS
	*/
/* for tty's only */	char *name;	/* device name */
	char *terminalName;	/* name of MFBCAP entry */
/* I/O routines */	int (*dsply_getchar)();
	int (*kybrd_getchar)();
	int (*dsply_ungetchar)();
	int (*kybrd_ungetchar)();
	int (*outchar)();
	int (*outstr)();
	/*
	* BOOLEANS
	*/
	Bool initializedBool;
/* Video Layer Table */	Bool vltBool;
	Bool vltUseHLSBool;
/* Channel Mask */	Bool channelMaskBool;
	Bool readMaskBool;
/* Pointing Device */	Bool PointingDeviceBool;
	Bool buttonsBool;
	Bool readImmediateBool;
/* Keyboard Control */	Bool keyboardBool;
/* Line Drawing */	Bool linePatternDefineBool;
	Bool reissueLineStyleBool;
/* Polygon Drawing */	Bool filledPlygnBool;
/* Text font */	Bool textPositionableBool;
	Bool textRotateBool;
	Bool replaceTextBool;
	Bool overstrikeTextBool;
/* Blinkers */	Bool blinkersBool;
/* Raster Copy */	Bool rastCopyBool;
	Bool rastRSCSFBool;
/* Fill Patterns */	Bool fillPtrnDefineBool;
	Bool fillDefineRowMajorBool;
/* for tty's only */	Bool litout;
	Bool raw;
	Bool ttyIsSet;
	/*
	* STRUCTURES
	*/
	struct mfbformatstrs strings;	/* format strings */
	WINDOW currentWindow;	/* current window */
	VIEWPORT currentViewport;	/* current viewport */
#ifndef vms
	/* graphics device ttyb struct */
	MFBSAVETTYB graphTtyb;
	/* keyboard ttyb struct if graphics device does not have a kybrd */
	MFBSAVETTYB kybrdTtyb;
	/* tty status ints */
	MFBSAVESTAT oldstat;
#endif
	/*
	* CHARACTERS
	*/
	char deviceType;	/* TTY=tty, HCOPY=hard copy */
	char strBuf[BUFSIZE];	/* storage for format strings */
	char ttyBuffer[TTYBUFSIZE];	/* tty output buffer */
	};
typedef struct mfb MFB;

EXAMPLE

The following C program is a simple example that uses several MFB routines. The terminal type is assumed to be the first command line argument. This program will display several triangles in different line styles, display at four angles of rotation the text that is returned from MFBKeyboard, draw a solid line between two points, and draw an arc clipped to a rectangle.

    #include <cad/mfb.h>
    main(argc, argv)
    	int argc;
    	char *argv[];
    	{
    	int i, j, k, m;
    	int X1, X2, Y1, Y2;
    	int numcolors;
    	int numlinestyles;
    	int button;
    	int error;
    	MFB *mfb, *MFBOpen();
    	MFBPATH *pp;
    	char key;
    	char *TypeIn;
    	/* open graphics device */
    	mfb = MFBOpen(argv[1], NULL, &error);
    	/* exit on any error */
    	if(error < 0) {
    		fprintf(stderr, "error:  %s\n", MFBError(error));
    		exit(0);
    		}
    	/* get device information */
    	X1 = MFBInfo(MAXX)/2;
    	X2 = X1/2;
    	Y1 = MFBInfo(MAXY)/30;
    	numcolors = MFBInfo(MAXCOLORS);
    	numlinestyles = MFBInfo(MAXLINESTYLES);
    	if(numcolors > 7)
    		numcolors = 7;
    	if(numlinestyles > 7)
    		numlinestyles = 7;
    	/* draw pyramid of lines in different line styles */
    	for(j=0; j<28; ++j) {
    		/* set color (increment by one to prevent 'invisible' lines) */
    		k = j % (numcolors - 1);
    		MFBSetColor(k + 1);
    		/* define and set line style */
    		m = j % numlinestyles;
    		MFBDefineLineStyle(m, j * 6);
    		MFBSetLineStyle(m);
    		/* draw pyramid */
    		MFBLine(0, 0, X2, Y1*j + 2*j);
    		MFBLine(X1, 0, X2, Y1*j + 2*j);
    		}
    	/* flush output */
    	MFBUpdate();
    	/* test of MFBKeyboard */
    	MFBText("Test of MFBKeyboard.", X2, Y1*28, 0);
    	TypeIn = MFBKeyboard(X1, 5, 0, 1);
    	MFBText(TypeIn, X1, 70, 0);
    	MFBText(TypeIn, X1, 70, 90);
    	MFBText(TypeIn, X1, 70, 180);
    	MFBText(TypeIn, X1, 70, 270);
    	MFBUpdate();
    	sleep(3);
    	/* test of MFBPoint */
    	MFBSetColor(1);
    	MFBFlood();
    	MFBSetColor(0);
    	MFBText("Test of MFBPoint.", X2, Y1*28, 0);
    	MFBPoint(&X1, &Y1, &key, &button);
    	MFBPoint(&X2, &Y2, &key, &button);
    	MFBSetLineStyle(0);
    	MFBLine(X1, Y1, X2, Y2);
    	/* draw outline of box to contain arc */
    	MFBLine(100, 100, 100, 350);
    	MFBLine(100, 100, 370, 100);
    	MFBLine(370, 100, 370, 350);
    	MFBLine(100, 350, 370, 350);
    	/* test of MFBArcPath and MFBClipArc */
    	i = 0;
    	pp = MFBClipArc(MFBArcPath(70, 70, 200, 0, 0, 30), 100, 100, 370, 350);
    	while(pp[i].nvertices != 0 && i < 4) {
    		MFBDrawPath(&pp[i]);
    		i++;
    		}
    	/* flush output and wait */
    	MFBUpdate();
    	sleep(6);
    	MFBClose();
    	}

DEBOUNCING THE POINTING DEVICE

The following C program is another example of using MFB routines that demonstrates several methods of debouncing the pointing device. Several graphics terminals can return bogus pointing reports that can be serious and annoying in some applications. Identifying these bogus reports is very terminal dependent (e.g. the AED 512 returns bad button masks, the Metheus 400 returns negative coordinates, etc.), and it is therefore necessary to use all possible tests.

    #include <cad/mfb.h>
    #ifdef vms
    #include <timeb.h>
    #else
    #include <sys/timeb.h>
    #endif
    /*
    	* This is the minimum time in milliseconds
    	* between accepted pointing events.
    	*/
    #define DEBOUNCETIME 100
    /*
    	* we keep track of the time between pointing
    	* events to debounce the cursor
    	*/
    static long LastPointTime = 0;
    /*
    	* routine to read and debounce pointing device.
    	*/
    point(pointX,pointY,Key,Mask)
    	int *pointX,*pointY,*Mask;
    	char *Key;
    	{
    	struct timeb now;
    	long newtime;
    	int X,Y,Buttons;
    	char KeyTyped;
    	SetDebounceTime();
    	/* Loop until DEBOUNCETIME has passed */
    	while(True) {
    		/* Loop until valid report is received */
    		while(True) {
    			/* Get pointing event */
    			MFBPoint(&X,&Y,&KeyTyped,&Buttons);
    			/* Was a character typed? */
    			if(Key != 0)
    				break;
    			/* Does the pointing device have buttons? */
    			if(MFBInfo(POINTINGBUTTONS)){
    				/*
    				* Test button masks and vicinity of coordinate.
    				* Assume a four button mouse.
    				*/
    				if((Buttons == MFBInfo(BUTTON1) ||
    					Buttons == MFBInfo(BUTTON2) ||
    					Buttons == MFBInfo(BUTTON3) ||
    					Buttons == MFBInfo(BUTTON4)) &&
    					(X < MFBInfo(MAXX) && X > 0 &&
    					Y < MFBInfo(MAXY) && Y > 0))
    					break;
    				}
    			}
    		ftime(&now);
    		newtime = 1000 * now.time + now.millitm;
    		if((newtime - LastPointTime) < DEBOUNCETIME) continue;
    		SetDebounceTime();
    		}
    	*pointX = X;
    	*pointY = Y;
    	*Key = KeyTyped;
    	*Mask = Buttons;
    	}
    SetDebounceTime(){
    	struct timeb now;
    	ftime(&now);
    	LastPointTime = 1000 * now.time + now.millitm;
    	}

NOTES

On some systems, MFB is contained in usr rather than ~cad.

MFB will also compile to run under VMS (a trademark of Digital Equipment Corp.) or any other operating system. However, special I/O routines such as those in ~cadsrcmfbvmsio.c must be provided for MFB to function properly.

MFB was written to be utmost UNIX compatible and consistent with the style of the C programming language. For example, a control sequence always begins with a call to an (MFB)Open routine and is terminated by a call to a (MFB)Close routine. Another example is the provision of the MFBHalt routine that is intended primarily for the handling of the SIGTSTP signal. One possible exception to the style of C is the use of a global output descriptor that is set by a call to the SetCurrentMFB routine, as opposed to passing the output descriptor as an argument to ever active function call.

MFB was initially aimed toward the modeling of lower performance graphics terminals (e.g., there is currently no support of segments or definable windows and viewports at the device level). As a result, programs that use MFB are likely to work on the low performance (least expensive) graphics terminals as well as on the more expensive devices.

BUGS

Raster (hard copy) output is not yet implemented.

FUTURE ENHANCEMENTS

Future modifications to MFB may include the following:

    Extension to hard copy graphics devices.

    Definable vector and raster character fonts.

    Improved cursor support including a definable cursor font, cursor tracking by the host, cursor-on/cursor-off capability, and cursor report without event.

    Window/viewport geometry clipping by the terminal if the device possesses that capability.

    Bit block transfer (BitBlt).

FILES
~cad/lib/mfbcap
~cad/include/mfb.h
~cad/lib/mfb.a
~cad/src/mfb

SEE ALSO
mfbcap(5), termcap(5), curses(3), more(1), kic(CAD1)

AUTHOR
Giles Billingsley
Ken Keller

STATUS

The following is a list of the terminals that will currently work with MFB:

4014	Tektronix 4014 with thumbwheels
4113	Tektronix 4112/4113 with thumbwheels or tablet
AED5	AED 512 with joystick or tablet
AED7	AED 767 with joystick or tablet
2648	HP 2648 black and white grahpics terminal with tablet
9872	HP 9872 color pen plotter
D125	DEC VT125 black and white graphics terminal

The following table lists routines that depend on device capabilities and may not work on all graphics devices. Other MFB routines that are not listed below will work for all devices.