home *** CD-ROM | disk | FTP | other *** search
- /*
- GRDEMO.C - Demonstrates capabilities of the QuickC graphics library
-
- Since this program uses functions not found in the QuickC core
- library or the graphics library, you must use a program list to
- compile in memory. Select Set Program List from the File menu
- and enter GRDEMO as the program list name. Then specify GRDEMO
- as the only entry in the program list.
-
- An alternative is to create a quick library containing the routines
- used in GRDEMO. Use the following lines to build the quick library
- and load it into QuickC:
-
- QLIB /s grdemo.c
- QC /l grdemo.qlb grdemo
- */
-
- #include <graph.h>
- #include <string.h>
- #include <math.h>
- #include <stdlib.h>
- #include <stdio.h>
- #include <conio.h>
- #include <time.h>
- #include <bios.h>
-
- /* Functions - prototypes and macros */
-
- /* Demo functions */
-
- int main(void);
-
- /* Demo selections */
- void circles(void);
- void sphere(void);
- int polygons(void);
- int spiral(int angle, int inc);
- int inspiral(int side, int angle, int inc);
- void adjust(void);
-
- /* Menus */
- int menu(int row, int col, char * *items);
- void box(int row, int col, int hi, int wid);
- void itemize(int row, int col, char *str, int len);
-
- /* Color changes */
- int nextatrib(int init);
- void nextcolor(void);
-
- /* Turtle graphics routines */
-
- /* Initiate and set defaults */
- short setturtle(short mode);
- void home(void);
-
- /* Control pen and color */
- int pendown(int state);
- short fillstate(short state);
- short penatrib(short atrib);
- short borderatrib(short border);
-
- /* Control angle */
- short turn(short angle);
- short turnto(short angle);
-
- /* Turtle movement */
- short move(short distance);
- short moveto(short x,short y);
- short poly(short number,short side);
-
- /* Figures (defined as macros) */
-
- /* Puts a circle with radius <r> at current location.
- Returns nonzero if successful. */
- #define circle(r) _ellipse(tc.isFill, \
- tc.xCur-(r), adj(tc.yCur-(r)), tc.xCur+(r), adj(tc.yCur+(r)))
-
- /* Puts an ellipse with width <w> and height <h> at current location.
- Returns nonzero if successful. */
- #define ellipse(w,h) _ellipse(tc.isFill, tc.xCur-((w)/2), \
- adj(tc.yCur-((h)/2)), tc.xCur+((w)/2), adj(tc.yCur+((h)/2)))
-
- /* Miscellaneous */
-
- /* Fills starting at the current location.
- Returns nonzero if successful. */
- #define fillin() _floodfill(tc.xCur, adj(tc.yCur),tc.border)
-
- /* Returns nonzero if the current location is onscreen. */
- #define onscreen() (!((tc.xCur < -xMAX) || (tc.xCur > xMAX) || \
- (tc.yCur < -yMAX) || (tc.yCur > yMAX)))
-
- /* Returns a long int mixed from red <r>, green <g>, and blue <b> bytes. */
- #define RGB(r,g,b) (((long) ((b) << 8 | (g)) << 8) | (r))
-
- short adj(short y);
- unsigned cursor(unsigned value);
-
- /* Constants */
-
- #define xMAX (tc.xCnt / 2)
- #define yMAX (tc.yCnt / 2)
- #define CIRCUMFERENCE 360
- #define HALFCIRCUMFERENCE 180
-
- #define PI 3.141593
- #define DEFAULT -1
- #define TRUE 1
- #define FALSE 0
- #define TCURSOROFF 0x2020
- #define LASTATR 15
- #define NLASTATR 14
-
- /* Scan codes */
-
- #define UP 72
- #define DOWN 80
- #define LEFT 75
- #define RIGHT 77
- #define ENTER 28
-
- /* Structures for configuration and other data */
- struct videoconfig vc;
-
- struct {
- long xUnits, yUnits;
- short xCnt, yCnt;
- short xCur, yCur;
- short angle;
- short border;
- short numAtribs;
- short numColors;
- short atrib;
- short isPen;
- short isFill;
- } tc = { 125L, 90L }; /* Initial values for aspect.
- Change to adjust for your screen. */
-
- /* Initial and work arrays for remapable colors. */
-
- long iColors[] = {
- _BLACK, _BLUE, _GREEN, _CYAN,
- _RED, _MAGENTA, _BROWN, _WHITE,
- _GRAY, _LIGHTBLUE, _LIGHTGREEN, _LIGHTCYAN,
- _LIGHTRED, _LIGHTMAGENTA, _LIGHTYELLOW, _BRIGHTWHITE };
-
- long wColors[256];
-
- /* Array and enum for main menu */
-
- char *mnuMain[] = {
- "Quit",
- "Circles",
- "Sphere",
- "Tunnel",
- "Spiral",
- "Inverted Spiral",
- "Adjust Aspect",
- "Change Mode",
- NULL };
-
- /* Define constants 0 to 7 (equivalent to multiple #define statements) */
-
- enum choice { QUIT, CIRCLES, SPHERE, TUNNEL, SPIRAL,
- INSPIRAL, ADJUST, CHANGE };
-
- /* Arrays for video modes */
-
- char *mnuModes[] = {
- "MRES4COLOR ",
- "MRESNOCOLOR",
- "HRESBW",
- "MRES16COLOR",
- "HRES16COLOR",
- "ERESCOLOR",
- "VRES2COLOR",
- "VRES16COLOR",
- "MRES256COLOR",
- NULL };
-
- /* Array for modes */
- int modes[] = {
- _MRES4COLOR,
- _MRESNOCOLOR,
- _HRESBW,
- _MRES16COLOR,
- _HRES16COLOR,
- _ERESCOLOR,
- _VRES2COLOR,
- _VRES16COLOR,
- _MRES256COLOR,
- _ERESNOCOLOR,
- _HERCMONO,
- DEFAULT };
-
- /* Structure for menu attributes (variables for color and monochrome) */
- struct mnuAtr {
- int fgNormal, fgSelect, fgBorder;
- long bgNormal, bgSelect, bgBorder;
- int centered;
- char nw[2], ne[2], se[2], sw[2], ns[2], ew[2];
- };
-
- struct mnuAtr menus = {
- 0x00, 0x0f, 0x04,
- 0x03, 0x04, 0x03,
- TRUE,
- "┌", "┐", "┘", "└", "│", "─"
- };
-
- struct mnuAtr bwmenus = {
- 0x07, 0x00, 0x07,
- 0x00, 0x07, 0x00,
- TRUE,
- "┌", "┐", "┘", "└", "│", "─"
- };
-
- char mess1[] = { "Graphics Demonstration Program" } ;
- char mess2[] = { "Move to menu selection with cursor keys" };
- char mess3[] = { "Press ENTER to select" };
- int lmess1 = sizeof(mess1), lmess2 = sizeof(mess2), lmess3 = sizeof(mess3);
-
- main ()
- {
- int choice, crow, ccol;
- int vmode;
-
- _setvideomode (_DEFAULTMODE);
- _getvideoconfig(&vc);
- crow = vc.numtextrows / 2;
- ccol = vc.numtextcols / 2;
-
- /* Select best text and graphics modes and adjust menus */
-
- switch (vc.adapter) {
- case _MDPA :
- puts("No graphics mode available.\n");
- exit(0);
- case _CGA :
- mnuModes[3] = NULL;
- vmode = _MRES4COLOR;
- break;
- case _HGC :
- mnuModes[6] = NULL;
- vmode = _HERCMONO;
- break;
- case _EGA :
- mnuModes[6] = NULL;
- if (vc.memory > 64)
- vmode = _ERESCOLOR;
- else
- vmode = _HRES16COLOR;
- break;
- case _VGA :
- case _MCGA :
- vmode = _MRES256COLOR;
- break;
- }
- switch (vc.mode) {
- case _TEXTBW80 :
- case _TEXTBW40 :
- menus = bwmenus;
- break;
- case _TEXTMONO :
- case _ERESNOCOLOR :
- case _HERCMONO :
- menus = bwmenus;
- if (vmode != _HERCMONO)
- vmode = _ERESNOCOLOR;
- mnuMain[7] = NULL;
- }
-
- srand((unsigned)time(0L));
-
- _settextposition(1,ccol - (lmess1 / 2));
- _outtext(mess1);
- _settextposition(2,ccol - (lmess2 / 2));
- _outtext(mess2);
- _settextposition(3,ccol - (lmess3 / 2));
- _outtext(mess3);
-
- /* Select and branch to menu choices */
-
- for (;;) {
- choice = menu(crow,ccol,mnuMain);
- setturtle(vmode);
-
- switch (choice) {
- case QUIT :
- _setvideomode (_DEFAULTMODE); exit(0);
- case CIRCLES :
- circles(); break;
- case SPHERE :
- sphere(); break;
- case TUNNEL :
- nextatrib(0);
- pendown(FALSE);
- moveto((short)(-xMAX * .3), (short)(yMAX * .3));
- turn(35);
- pendown(TRUE);
- polygons();
- while (!kbhit())
- nextcolor();
- break;
- case SPIRAL :
- nextatrib(0);
- spiral((rand() % 50) + 30, (rand() % 4) + 1);
- while (!kbhit())
- nextcolor();
- break;
- case INSPIRAL :
- nextatrib(0);
- inspiral((rand() % 12) + 8, (rand() %20) + 2,
- (rand() % 30) + 1);
- while (!kbhit())
- nextcolor();
- break;
- case ADJUST :
- adjust();
- _setvideomode(_DEFAULTMODE);
- continue;
- case CHANGE :
- for (;;) {
- _setvideomode (_DEFAULTMODE);
- vmode = modes[menu(crow,ccol,mnuModes)];
- if (!setturtle(vmode)) {
- _settextposition(1,22);
- _outtext("Mode not available on this machine.\n");
- } else
- break;
- }
- _setvideomode (_DEFAULTMODE);
- continue;
- }
- _bios_keybrd(_KEYBRD_READ);
- _setvideomode (_DEFAULTMODE);
- }
- return (0);
- }
-
- /* Put circles of varying sizes and colors on screen in a round pattern */
-
- void circles()
- {
- int i, x, y;
- long tb;
-
- tb = _getbkcolor();
- if ((vc.mode < _HRESBW) || (tc.numAtribs == 2))
- fillstate(FALSE);
- else {
- fillstate(TRUE);
- _setbkcolor(_BRIGHTWHITE);
- }
- pendown(FALSE);
- for (;;) {
- if (tc.numAtribs <= 4)
- nextcolor();
- for (i = 5; i <= 150; ++i) { /* Draw circles */
- x = (int)((xMAX-30) * atan(sin(i / PI)));
- y = (int)((yMAX-30) * atan(cos(i / PI)));
- penatrib(nextatrib(DEFAULT));
- moveto(x,y);
- circle (i % 30);
- if (kbhit()) {
- _setbkcolor(tb);
- pendown(TRUE);
- return;
- }
- }
- }
- }
-
- /* Draw and fill sphere; rotate colors in EGA modes;
- change palette in CGA modes */
-
- void sphere()
- {
- int ix, x, y, border, inc;
-
- y = x = (int)(tc.yCnt * 0.9);
- fillstate(FALSE);
- nextatrib(0);
- inc = y / 14;
- border = penatrib(DEFAULT);
- borderatrib(border);
- for (ix = inc; ix <= x; ix += (inc * 2)) /* Draw circles */
- ellipse(ix, y);
- fillstate(TRUE);
- pendown(FALSE);
- turn(90);
- x /= 2;
- moveto(-x + inc,0);
- while (tc.xCur <= (x - inc)) { /* Fill circles */
- penatrib(nextatrib(DEFAULT));
- fillin();
- move(inc);
- }
- while (!kbhit()) /* Rotate colors */
- nextcolor();
- pendown(TRUE);
- }
-
- /* Draw polygons of increasing size by incrementing the number of sides.
- Return 1 for user interrupt, 0 for edge of screen encountered. */
-
- int polygons()
- {
- int sides = 3, size = 2, atrib = 1;
- for (;;) {
- penatrib(nextatrib(atrib++ % NLASTATR));
- if (!poly(sides++,size++))
- return(0);
- if (kbhit())
- return(1);
- }
- }
-
- /* Draw a spiral by increasing each side of a rotating figure.
- <angle> determines tightness.
- <inc> determines size.
- Return 1 for user interrupt, 0 for edge of screen encountered. */
-
- int spiral(int angle, int inc)
- {
- int side = 1, atrib = 1;
-
- for (;;) {
- penatrib(nextatrib(atrib++ % NLASTATR));
- if (!move(side += inc))
- return(0);
- turn(angle);
- if (kbhit())
- return(1);
- }
- }
-
- /* Draw an inverted spiral by increasing each angle of a rotating figure.
- <side> determines size.
- <angle> determines shape.
- <inc> determines tightness and shape.
- Return 1 for user interrupt, 0 for edge of screen encountered. */
-
- int inspiral(int side, int angle, int inc)
- {
- int atrib = 1;
-
- for (;;) {
- penatrib(nextatrib(atrib++ % NLASTATR));
- if (!move(side))
- return(0);
- turn(angle += inc);
- if (kbhit())
- return(1);
- }
- }
-
- /* Draw an adjustable circle to enable the user to visually adjust the
- screen aspect. */
-
- void adjust()
- {
- int i, y, pen, radius = (int)(yMAX * .6);
- char buffer[3];
-
- pen = penatrib(DEFAULT);
- _outtext("Modify initial structure\nvalues in program");
- _outtext("\n\nAdjust with cursor keys: ");
- _outtext("\n UP - adjust up");
- _outtext("\n DOWN - adjust down");
- _outtext("\n ENTER - finished\n\n");
- _outtext("xUnits 125\n");
- for (;;) {
- y = (int)tc.yUnits;
- penatrib(pen);
- home();
- pendown(FALSE); /* Draw white circle with cross. */
- moveto(75,0);
- circle(radius);
- for (i = 1; i <= 4; i++) {
- pendown(TRUE);
- move(radius);
- turn(180);
- pendown(FALSE);
- move(radius);
- turn(90);
- }
-
- _settextposition(11,1); /* Show units and adjust */
- _outtext("yUnits ");
- ltoa(tc.yUnits,buffer,10);
- _outtext(buffer);
- _outtext(" ");
- switch ((_bios_keybrd(_KEYBRD_READ) & 0xff00) >> 8) {
- case UP :
- --y;
- break;
- case DOWN :
- ++y;
- break;
- case ENTER :
- tc.yUnits = y;
- return;
- }
- penatrib(0); /* Erase circle with black */
- moveto(75,0);
- circle(radius);
- for (i = 1; i <= 4; i++) {
- pendown(TRUE);
- move(radius);
- turn(180);
- pendown(FALSE);
- move(radius);
- turn(90);
- }
- tc.yUnits = y;
- }
- }
-
- /* Put menu on screen.
- Starting <row> and <column>.
- Array of menu <items> strings.
- Global structure variable <menus> determines:
- Colors of border, normal items, and selected item.
- Centered or left justfied.
- Border characters.
- Returns number of item selected. */
-
- int menu(int row, int col, char * *items)
- {
- int i, num, max = 2, prev, curr = 0;
- int litem[25];
- long bcolor;
-
- cursor(TCURSOROFF);
- bcolor = _getbkcolor();
-
- /* Count items, find longest, and put length of each in array */
-
- for (num = 0; items[num]; num++) {
- litem[num] = strlen(items[num]);
- max = (litem[num] > max) ? litem[num] : max;
- }
- max += 2;
-
- if (menus.centered) {
- row -= num / 2;
- col -= max / 2;
- }
-
- /* Draw menu box */
-
- _settextcolor(menus.fgBorder);
- _setbkcolor(menus.bgBorder);
- box(row++,col++,num,max);
-
- /* Put items in menu */
-
- for (i = 0; i < num; ++i) {
- if (i == curr) {
- _settextcolor(menus.fgSelect);
- _setbkcolor(menus.bgSelect);
- } else {
- _settextcolor(menus.fgNormal);
- _setbkcolor(menus.bgNormal);
- }
- itemize(row+i,col,items[i],max - litem[i]);
- }
-
- /* Get selection */
-
- for (;;) {
- switch ((_bios_keybrd(_KEYBRD_READ) & 0xff00) >> 8) {
- case UP :
- prev = curr;
- curr = (curr > 0) ? (--curr % num) : num-1;
- break;
- case DOWN :
- prev = curr;
- curr = (curr < num) ? (++curr % num) : 0;
- break;
- case ENTER :
- _setbkcolor(bcolor);
- return(curr);
- default :
- continue;
- }
- _settextcolor(menus.fgSelect);
- _setbkcolor(menus.bgSelect);
- itemize(row+curr,col,items[curr],max - litem[curr]);
- _settextcolor(menus.fgNormal);
- _setbkcolor(menus.bgNormal);
- itemize(row+prev,col,items[prev],max - litem[prev]);
- }
- }
-
- /* Draw menu box.
- <row> and <col> are upper left of box.
- <hi> and <wid> are height and width. */
-
- void box(int row, int col, int hi, int wid)
- {
- int i;
- char temp[80];
-
- _settextposition(row,col);
- temp[0] = *menus.nw;
- memset(temp+1,*menus.ew,wid);
- temp[wid+1] = *menus.ne;
- temp[wid+2] = 0;
- _outtext(temp);
- for (i = 1; i <= hi; ++i) {
- _settextposition(row+i,col);
- _outtext(menus.ns);
- _settextposition(row+i,col+wid+1);
- _outtext(menus.ns);
- }
- _settextposition(row+hi+1,col);
- temp[0] = *menus.sw;
- memset(temp+1,*menus.ew,wid);
- temp[wid+1] = *menus.se;
- temp[wid+2] = 0;
- _outtext(temp);
- }
-
- /* Put an item in menu.
- <row> and <col> are left position.
- <str> is the string item.
- <len> is the number of blanks to fill. */
-
- void itemize(int row, int col, char *str, int len)
- {
- char temp[80];
-
- _settextposition(row,col);
- _outtext(" ");
- _outtext(str);
- memset(temp,' ',len--);
- temp[len] = 0;
- _outtext(temp);
- }
-
- /* Rotate to next color attribute.
- <init> initializes new starting color.
- (specify DEFAULT to rotate to next color)
- Return rotated color attribute. */
-
- int nextatrib(int init)
- {
- static int atr;
-
- if (tc.numAtribs == 2)
- return(atr = !atr);
- if (!(init == DEFAULT))
- atr = init;
- return(atr = (atr % (tc.numAtribs-1) + 1));
- }
-
- /* Rotate to next palette array for EGA and higher.
- Rotate palette for CGA color. */
-
- void nextcolor()
- {
- static int co = 0;
- int w, i;
-
- if ((vc.adapter <= _CGA) || !tc.numColors)
- return;
- if ((--co < 0) || (co >= tc.numColors - 1))
- co = tc.numColors - 1;
- w = co;
- for (i = LASTATR-1; i > 0; --i) {
- _remappalette(i, wColors[w]);
- if (--w < 0)
- w = tc.numColors - 1;
- }
-
- }
-
- /* Set the display mode and establish turtle defaults.
- <mode> is the mode to set.
- Returns 0 if mode is invalid, else returns nonzero. */
-
- short setturtle(short mode)
- {
- int ret, i = 0, btm, top = 63, inc, red = 0, green = 0, blue = 0;
-
- _getvideoconfig(&vc);
- if (mode < _MRES4COLOR)
- return(0);
- if (!(mode == vc.mode)) {
- if(!(ret = _setvideomode(mode)))
- return(0);
- _getvideoconfig(&vc);
- } else
- ret = mode;
-
- home();
- switch (vc.mode) { /* Set palette defaults */
- case _ERESNOCOLOR :
- case _HERCMONO :
- tc.numColors = 0;
- tc.numAtribs = 2;
- return(ret);
- case _MRES256COLOR :
- tc.numColors = tc.numAtribs = 125;
- inc = btm = 12;
- break;
- case _ERESCOLOR :
- case _VRES16COLOR :
- /* For full 64 color palette, btm = 0; tc.numColors = 64 */
- inc = btm = 16; tc.numColors = 27;
- break;
- case _MRES4COLOR :
- case _MRESNOCOLOR :
- inc = 32; btm = 0; tc.numColors = 8;
- break;
- default:
- tc.numColors = 16;
- memcpy(wColors,iColors,16 * sizeof(iColors[0]));
- _remapallpalette(iColors);
- nextcolor();
- return(ret);
- }
-
- /* Fill palette arrays */
- for (blue = btm; blue <= top; blue += inc)
- for (green = btm; green <= top; green += inc)
- for (red = btm; red <= top; red += inc)
- wColors[i++] = RGB(red, green, blue);
- nextcolor();
- return(ret);
- }
-
- /* Sets initial turtle parameters. Use to reset without changing mode. */
-
- void home()
- {
- float ratio;
-
- if (vc.mode == _MRES256COLOR)
- tc.numAtribs = 125;
- else
- tc.numAtribs = vc.numcolors;
- tc.xCnt = vc.numxpixels;
- tc.yCnt = vc.numypixels;
- _setlogorg(tc.xCnt / 2, tc.yCnt / 2);
-
- ratio = (float)(tc.xUnits * tc.yCnt) / (tc.yUnits * tc.xCnt);
- tc.yCnt /= ratio;
-
- tc.xCur = 0;
- tc.yCur = 0;
- tc.isPen = 1;
- _moveto(0, 0);
- tc.angle = 0;
- _remappalette(LASTATR,_BRIGHTWHITE);
- borderatrib(LASTATR);
- penatrib(LASTATR);
- fillstate(_GBORDER);
- }
-
- /* Makes the turtle pen used in move() and moveto() visible or invisible.
- <state> can be TRUE (visible), FALSE (invisible),
- or DEFAULT (return current)
- Returns current state. */
-
- int pendown(int state)
- {
- switch (state) {
- case TRUE:
- tc.isPen = TRUE;
- break;
- case FALSE:
- tc.isPen = FALSE;
- }
- return(tc.isPen);
- }
-
- /* Determines whether figures should be filled.
- <state> can be TRUE (fill), FALSE (border only),
- or DEFAULT (return current)
- Returns current state. */
-
- short fillstate(short state)
- {
- switch (state) {
- case _GBORDER:
- case FALSE:
- tc.isFill = _GBORDER;
- break;
- case _GFILLINTERIOR:
- case TRUE:
- tc.isFill = _GFILLINTERIOR;
- }
- return(tc.isFill);
- }
-
- /* Sets the color attribute of the pen.
- <atrib> is new atribute (use DEFAULT to get current).
- Returns current color attribute. */
-
- short penatrib(short atrib)
- {
- if (!(atrib == DEFAULT)) {
- _setcolor(tc.atrib = atrib);
- }
- return(tc.atrib);
- }
-
- /* Sets the color attribute to be used as a boundary in fills.
- <border> is new border (use DEFAULT to get current).
- Returns border attribute. */
-
- short borderatrib(short border)
- {
- if (!(border == DEFAULT))
- tc.border = border;
- return(tc.border);
- }
-
- /* Sets a new turtle <angle> relative to the current angle.
- Returns the new angle. */
-
- short turn(short angle)
- {
- return(tc.angle = ((tc.angle + angle) % CIRCUMFERENCE));
- }
-
- /* Sets a specified turtle <angle>.
- Returns the new angle. */
-
- short turnto(short angle)
- {
- return(tc.angle = (angle % CIRCUMFERENCE));
- }
-
- /* Moves from the current position in the current direction. A line is
- drawn if the pen is down. The current position is reset.
- <distance> is the adjusted length of line.
- Returns 0 if the new position is off the screen. */
-
- short move(short distance)
- {
- short dX, dY;
- double workangle;
-
- workangle = (tc.angle - 90) * PI / HALFCIRCUMFERENCE;
- dX = (short)(distance * cos(workangle));
- dY = (short)(distance * sin(workangle));
- if (tc.isPen)
- _lineto(tc.xCur + dX, adj(tc.yCur + dY));
- else
- _moveto(tc.xCur + dX, adj(tc.yCur + dY));
- tc.xCur += dX;
- tc.yCur += dY;
- return(onscreen());
- }
-
- /* Moves from the current position to a specified position. A line is
- drawn if the pen is down. The current position is reset.
- <x> and <y> are destination coordinates.
- Returns 0 if new position is off screen. */
-
- short moveto(short x, short y)
- {
- if (tc.isPen)
- _lineto(x, adj(y));
- else
- _moveto(x, adj(y));
- tc.xCur = x;
- tc.yCur = y;
- return(onscreen());
- }
-
- /* Draws a polygon
- <number> specifies how many sides.
- <side> specifies the length of each side.
- Returns 0 if any part of polygon is off screen. */
-
- short poly(short number, short side)
- {
- int i, ret = 1;
- double angle;
-
- angle = (double)(360 / number);
- for (i = 1; i <= number; ++i) {
- ret = move(side) && ret;
- turn((short)angle);
- }
- return(ret);
- }
-
- /* Adjusts a specified <y> value for screen aspect.
- Returns the new value. */
-
- short adj(short y)
- {
- if (y)
- y = (short)(((long)y * (tc.xUnits*vc.numypixels)) /
- (tc.yUnits*vc.numxpixels));
- return(y);
- }
-
- /* Change the cursor shape.
- <value> has starting line in upper byte, ending line in lower byte.
- Returns the previous cursor value. */
-
- unsigned cursor(unsigned value)
- {
- union REGS inregs, outregs;
- int ret;
-
- inregs.h.ah = 3; /* Get old cursor */
- inregs.h.bh = 0;
- int86(0x10,&inregs,&outregs);
- ret = outregs.x.cx;
-
- inregs.h.ah = 1; /* Set new cursor */
- inregs.x.cx = value;
- int86(0x10,&inregs,&outregs);
-
- return(ret);
- }
-