home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Simtel MSDOS 1992 December
/
simtel1292_SIMTEL_1292_Walnut_Creek.iso
/
msdos
/
ddjmag
/
ddj8907.arc
/
PORTER.LST
< prev
next >
Wrap
File List
|
1989-06-01
|
10KB
|
317 lines
_GRAPHICS PROGRAMMING COLUMN_
by Kent Porter
[LISTING ONE]
/* VCOORDS.C: Implements virtual coordinates in GRAFIX library */
/* K. Porter, DDJ Graphics Programming Column, July '89 */
#include <math.h>
#include "grafix.h"
/* Variables for this compile unit */
double xf = 1.0, yf = 1.0; /* x, y conversion factors */
double ox = 0.0, oy = 0.0; /* virtual x, y origin */
/* ------------------------------------------------------------------ */
/* set virtual coordinate space */
void far setcoords (double left, double top, double right, double bottom)
{
xf = (double) vp_width() / (right - left); /* conversion factors */
yf = (double) vp_height() / (bottom - top);
ox = (double) vp_width() - (right * xf); /* origin */
oy = (double) vp_height() - (bottom * yf);
} /* ---------------------------------------------------------------- */
int far dx (double vx) /* convert virtual x to device x */
{
return (xf * vx) + ox;
} /* ---------------------------------------------------------------- */
int far dy (double vy) /* convert virtual y to device y */
{
return (yf * vy) + oy;
} /* ---------------------------------------------------------------- */
int far dxunits (double vx) /* device x units for vx */
{
return (int)(fabs)(xf * vx);
} /* ---------------------------------------------------------------- */
int far dyunits (double vy) /* device y units for vy */
{
return (int)(fabs)(yf * vy);
} /* ---------------------------------------------------------------- */
[LISTING TWO]
Caption: Add this to your copy of GRAFIX.H
/* From July, '89 */
/* -------------- */
void far setcoords /* set virtual coordinate space */
(double left, double top, double right, double bottom);
int far dx (double vx); /* convert virtual x to device x */
int far dy (double vy); /* convert virtual y to device y */
int far dxunits (double vx); /* device x units for vx */
int far dyunits (double vy); /* device y units for vy */
[LISTING THREE]
/* TRIGPLOT.C: Plot sine, cosine, and their sum */
/* X axis is integral, Y axis is floating-point */
#include <math.h>
#include <conio.h>
#include "grafix.h"
#define DEG2RAD 3.1415927 / 180.0 /* degrees to radians */
int px = 999, py; /* previous point */
void main ()
{
void plot (int angle, double (*fcn)(double theta));
double sum (double);
int angle;
if (init_video (EGA)) {
/* Scale the axes */
setcoords (-360, 1.5, 360, -1.5);
/* Draw the registration lines */
set_color1 (2); /* green */
hline (dx(-360), dy(0), dxunits (720)); /* x axis */
draw_line (dx(0), dy(1.3), dx(0), dy(-1.3)); /* y axis */
set_color1 (1); /* blue */
hline (dx(-360), dy(1), dxunits (720)); /* +1.0 */
hline (dx(-360), dy(-1),dxunits (720)); /* -1.0 */
/* Plot the sine curve */
set_color1 (3); /* cyan */
for (angle = -360; angle <= 360; angle++)
plot (angle, sin);
/* Plot the cosine curve */
set_color1 (5); /* magenta */
px = 999; /* new curve */
for (angle = -360; angle <= 360; angle++)
plot (angle, cos);
/* Plot the sum of sine and cosine */
set_color1 (15); /* white */
px = 999; /* new */
for (angle = -360; angle <= 360; angle++)
plot (angle, sum);
/* Wait for keypress and quit */
getch();
}
} /* ------------------------ */
double sum (double theta)
{
return (sin (theta) + cos (theta));
} /* ------------------------ */
void plot (int angle, double (*fcn)(double theta))
{
double theta, y;
theta = (double) angle * DEG2RAD; /* convert to radians */
y = (*fcn) (theta); /* derive value */
if (px != 999) /* if not first point */
draw_line (px, py, dx (angle), dy (y));
px = dx (angle); /* save current point */
py = dy (y);
} /* ------------------------ */
[LISTING FOUR]
/* LENDIST.C: Produces a histogram of line lengths in a text file */
/* Illustrates integral virtual coords, self-scaling bar chart */
#include <stdio.h>
#include <string.h>
#include <conio.h>
#include <stdlib.h>
#include "grafix.h"
#define MAXLEN 80 /* max length of a line */
#define MAXCAT MAXLEN / 5 /* number of categories */
void main (int argc, char *argv[])
{
double group [MAXCAT]; /* results array */
int category; /* grouping by length (0-4, 5-9, etc) */
double maxcount = 0; /* highest count for any category */
int color = 1; /* color of histogram bar */
char buf [MAXLEN]; /* receiving buffer */
FILE *fp; /* text file pointer */
/* check command line for a filename */
if (argc < 2) {
puts ("Usage: LENDIST <filename.ext>");
exit (EXIT_FAILURE);
}
/* clear the length array */
for (category = 0; category < MAXCAT; category++)
group [category] = 0.0;
/* pass thru the file getting lengths of lines */
if ((fp = fopen (argv[1], "r")) == NULL) {
printf ("Unable to open %s\n", argv[1]);
exit (EXIT_FAILURE);
} else {
while (fgets (buf, MAXLEN, fp)) {
category = strlen (buf) / 5; /* group 0-4, 5-9, etc. */
++group [category]; /* count */
}
fclose (fp);
}
/* find highest count of any group */
for (category = 0; category < MAXCAT; category++)
if (group [category] > maxcount)
maxcount = group [category];
/* Normalize groupings to 100 */
for (category = 0; category < MAXCAT; category++)
group [category] /= (maxcount / 100);
/* enter graphics mode */
if (init_video (EGA)) {
/* scale the histogram width */
/* leave space on top and left for text */
setcoords (-22, -2, 100, 23);
/* label the histogram */
printf ("Distribution of line lengths in %s\n\n", argv[1]);
for (category = 0; category < MAXCAT; category++)
printf (" Length %2d-%2d:\n", category*5, (category*5)+4);
/* set up the graph area */
draw_rect (dx(-22), dy (-1), dxunits (122),
dyunits(MAXCAT + 2));
set_color1 (1); /* blue */
for (category = 0; category < 100; category+=10)
draw_line (dx(category), dy(-0.5), dx(category), dy(MAXCAT));
/* draw the histogram bars */
for (category = 0; category < MAXCAT; category++) {
set_color1 (color);
if (++color == 16) color = 1;
fill_rect (dx (0), dy (category), dxunits (group [category]),
dyunits (0.75));
}
/* hold for keypress, then quit */
getch();
pc_textmode();
} else
puts ("Unable to enter EGA graphics");
}
[LISTING FIVE]
/* RESIZE.C: Effects of resizing virtual coords to fit viewports */
#include "grafix.h"
#include <conio.h>
#include <stdio.h>
#define BORDER 15
void main ()
{
void set_vp (int, int, int, int);
if (init_video (EGA)) {
/* Set colors for shading */
set_ega_palreg (1, ega_blend (RED3, GRN1, BLU0));
set_ega_palreg (2, ega_blend (RED2, GRN1, BLU0));
set_ega_palreg (3, ega_blend (RED2, GRN0, BLU0));
/* Draw 4-pointed star in variously-sized viewports */
set_vp (1, 1, 160, 120); /* square */
set_vp (200, 1, 120, 347); /* tall and skinny */
set_vp (360, 270, 238, 78); /* short and fat */
/* Wait for keypress and quit */
getch();
pc_textmode();
} else
puts ("Unable to enter EGA graphics");
} /* ---------------------------------- */
void set_vp (int left, int top, int width, int height)
{
VP_HAN vp;
void drawstar (void);
vp = vp_open (left, top, width, height);
set_color1 (BORDER);
vp_outline (vp);
setcoords (-120, 120, 120, -120); /* constants scale to vp size */
drawstar();
vp_close (vp);
} /* ---------------------------------- */
void drawstar (void)
{
set_color1 (BORDER); /* border color */
setfillborder (BORDER);
draw_rect (dx(-30), dy(-30), dxunits(60), dyunits(60));
set_color1 (3); /* center of star */
floodfill (dx(0), dy(0));
set_color1 (BORDER);
draw_line (dx(-30), dy(30), dx(0), dy(100)); /* top ray */
draw_line (dx(0), dy(100), dx(30), dy(30));
draw_line (dx(0), dy(100), dx(0), dy(30));
draw_line (dx(-30), dy(30), dx(-100), dy(0)); /* left ray */
draw_line (dx(-100), dy(0), dx(-30), dy(-30));
draw_line (dx(-100), dy(0), dx(-30), dy(0));
draw_line (dx(-30), dy(-30), dx(0), dy(-100)); /* bottom ray */
draw_line (dx(0), dy(-100), dx(30), dy(-30));
draw_line (dx(0), dy(-100), dx(0), dy(-30));
draw_line (dx(30), dy(-30), dx(100), dy(0)); /* right ray */
draw_line (dx(100), dy(0), dx(30), dy(30));
draw_line (dx(100), dy(0), dx(30), dy(0));
set_color1 (1);
floodfill (dx(10), dy(40));
floodfill (dx(-40), dy(20));
floodfill (dx(10), dy(-40));
floodfill (dx(40), dy(20));
set_color1 (2);
floodfill (dx(-10), dy(40));
floodfill (dx(-40), dy(-20));
floodfill (dx(-10), dy(-40));
floodfill (dx(40), dy(-20));
}