/*
 * Clear the disk file to the given color.
 */
HIDDEN int
disk_color_clear(fb *ifp, register unsigned char *bpp)
{
    static unsigned char pix_buf[DISK_DMA_BYTES] = {0};
    register unsigned char *pix_to;
    size_t i;
    int fd;
    size_t pixelstodo;

    /* Fill buffer with background color. */
    for (i = DISK_DMA_PIXELS, pix_to = pix_buf; i > 0; i--) {
	COPYRGB(pix_to, bpp);
	pix_to += sizeof(RGBpixel);
    }

    /* Set start of framebuffer */
    fd = ifp->if_fd;
    if (ifp->if_seekpos != 0 && lseek(fd, 0, 0) == -1) {
	fb_log("disk_color_clear : seek failed.\n");
	return -1;
    }

    /* Send until frame buffer is full. */
    pixelstodo = ifp->if_height * ifp->if_width;
    while (pixelstodo > 0) {
	i = pixelstodo > DISK_DMA_PIXELS ? DISK_DMA_PIXELS : pixelstodo;
	if (write(fd, pix_buf, i * sizeof(RGBpixel)) == -1)
	    return -1;
	pixelstodo -= i;
	ifp->if_seekpos += i * sizeof(RGBpixel);
    }

    return 0;
}
예제 #2
0
/*
  Initialize pseudo-color mapping table for the current view.  This
  color assignment will vary with each set of IR data read so as to
  map the full range of data to the full spectrum of colors.  This
  means that a given color will not necessarily have the same
  temperature mapping for different views of the vehicle, but is only
  valid for display of the current view.
*/
int
init_Temp_To_RGB(void)
{
    int temp, i;
    RGBpixel rgb;
    if ((ir_aperture = fb_getwidth(fbiop)/grid_sz) < 1) {
	bu_log("Grid too large for IR application, max. is %d.\n",
	       IR_DATA_WID
	    );
	return 0;
    }
    sample_sz = pow(ir_aperture, 2);
    if (ir_table != (RGBpixel *)RGBPIXEL_NULL)
	/* Table already initialized presumably from another view,
	   since range may differ we must create a different
	   table of color assignment, so free storage and re-
	   initialize.
	*/
	free((char *) ir_table);
    ir_table = (RGBpixel *) malloc((unsigned)(sizeof(RGBpixel)*((ir_max-ir_min)+1)));
    if (ir_table == (RGBpixel *)RGBPIXEL_NULL) {
	Malloc_Bomb(sizeof(RGBpixel)*((ir_max-ir_min)+1));
	fatal_error = TRUE;
	return 0;
    }
    for (temp = ir_min, i = 0; temp <= ir_max; temp++, i++) {
	temp_To_RGB(rgb, temp);
	COPYRGB(ir_table[i], rgb);
    }
    ir_max_index = i - 1;
    return 1;
}
예제 #3
0
int
fb_rpixel(register FBIO *ifp, unsigned char *pixelp)
{
    if ( ifp->if_pno == -1 )
	if ( _fb_pgin( ifp, ifp->if_pixcur / ifp->if_ppixels ) <= -1 )
	    return	-1;

    COPYRGB( pixelp, (ifp->if_pcurp) );
    ifp->if_pcurp += sizeof(RGBpixel);	/* position in page */
    ifp->if_pixcur++;	/* position in framebuffer */
    if ( ifp->if_pcurp >= ifp->if_pendp ) {
	if ( _fb_pgout( ifp ) <= -1 )
	    return	-1;
	ifp->if_pno = -1;
    }

#ifdef NEVER
    if ( ifp->if_debug & FB_DEBUG_BRW ) {
	fb_log( "fb_rpixel( 0x%lx, 0x%lx ) => [%3d,%3d,%3d]\n",
		(unsigned long)ifp, (unsigned long)pixelp,
		(*pixelp)[RED], (*pixelp)[GRN], (*pixelp)[BLU] );
    }
#endif /* NEVER */

    return	0;
}
static void
val_To_RGB(cell_val cv, unsigned char *rgb)
{
    double val;

    if (color_flag) {
	COPYRGB(rgb, cv.v_color);
	return;
    }
    val = (cv.v_scalar - dom_min) * dom_cvt;
    if ((boolean_flag && !ZERO(cv.v_scalar - bool_val))
	|| (val < SMALL_FASTF) || (val > 10.0))
    {
	COPYRGB(rgb, BACKGROUND);
    } else if (ZERO(val)) {
	COPYRGB(rgb, WHITE);
    } else {
	int idx;
	double rem;
	double res;

	if (interp_flag) {
	    vect_t prev_hsv;
	    vect_t hsv;
	    vect_t next_hsv;

	    idx = val + 0.01; /* convert to range [0 to 10] */
	    if ((rem = val - (double) idx) < 0.0) /* remainder */
		rem = 0.0;
	    res = 1.0 - rem;
#if BLEND_USING_HSV
	    bu_rgb_to_hsv(colortbl[idx], prev_hsv);
	    bu_rgb_to_hsv(colortbl[idx+1], next_hsv);
	    VBLEND2(hsv, res, prev_hsv, rem, next_hsv);
	    bu_hsv_to_rgb(hsv, rgb);
#else
	    VBLEND2(rgb, res, colortbl[idx], rem, colortbl[idx+1]);
#endif
	} else {
	    idx = val + 0.51;
	    COPYRGB(rgb, colortbl[idx]);
	}
    }
    return;
}
예제 #5
0
파일: paint.c 프로젝트: cogitokat/brlcad
void
paintCellFb(struct application *ap, unsigned char *pixpaint, unsigned char *pixexpendable)
{
    int gx, gy;
    int gyfin, gxfin;
    int gxorg, gyorg;
    int x, y;
    int cnt;
#if DEBUG_CELLFB
    brst_log("paintCellFb: expendable {%d, %d, %d}\n",
	     pixexpendable[RED],
	     pixexpendable[GRN],
	     pixexpendable[BLU]);
#endif
    gridToFb(ap->a_x, ap->a_y, &gx, &gy);
    gxorg = gx+1;
    gyorg = gy+1;
    gxfin = zoom == 1 ? gx+zoom+1 : gx+zoom;
    gyfin = zoom == 1 ? gy+zoom+1 : gy+zoom;
    cnt = gxfin - gxorg;
    for (y = gyorg; y < gyfin; y++) {
	if (zoom != 1 && (y - gy) % zoom == 0)
	    continue;
	bu_semaphore_acquire(RT_SEM_STATS);
	(void) fb_read(fbiop, gxorg, y, (unsigned char *)pixbuf, cnt);
	bu_semaphore_release(RT_SEM_STATS);
	for (x = gxorg; x < gxfin; x++) {
	    if (SAMERGB(&pixbuf[x-gxorg][0], pixexpendable)
		) {
#if DEBUG_CELLFB
		brst_log("Clobbering:<%d, %d>{%d, %d, %d}\n",
			 x, y,
			 pixbuf[x-gxorg][RED],
			 pixbuf[x-gxorg][GRN],
			 pixbuf[x-gxorg][BLU]);
#endif
		COPYRGB(&pixbuf[x-gxorg][0], pixpaint);
	    }
#if DEBUG_CELLFB
	    else
		brst_log("Preserving:<%d, %d>{%d, %d, %d}\n",
			 x, y,
			 pixbuf[x-gxorg][RED],
			 pixbuf[x-gxorg][GRN],
			 pixbuf[x-gxorg][BLU]);
#endif
	}
	bu_semaphore_acquire(RT_SEM_STATS);
	(void) fb_write(fbiop, gxorg, y, (unsigned char *)pixbuf, cnt);
	bu_semaphore_release(RT_SEM_STATS);
#if DEBUG_CELLFB
	brst_log("paintCellFb: fb_write(%d, %d)\n", x, y);
#endif
    }
    return;
}
예제 #6
0
파일: paint.c 프로젝트: cogitokat/brlcad
void
paintGridFb()
{
    int fx, fy;
    int fxbeg, fybeg;
    int fxfin, fyfin;
    int fxorg, fyorg;
    int fgridwid;
    if (fb_clear(fbiop, pixbkgr) == -1)
	return;
    gridxmargin = (devwid - (gridwidth*zoom)) / 2.0;
    gridymargin = (devhgt - (gridheight*zoom)) / 2.0;
    gridToFb(gridxorg, gridyorg, &fxbeg, &fybeg);
    gridToFb(gridxfin+1, gridyfin+1, &fxfin, &fyfin);
    gridToFb(0, 0, &fxorg, &fyorg);
    CenterCell(fxorg); /* center of cell */
    CenterCell(fyorg);
    if (zoom == 1) {
	fgridwid = gridwidth + 2;
	fxfin++;
    } else
	fgridwid = gridwidth * zoom + 1;

    /* draw vertical lines */
    for (fx = 1; fx < fgridwid; fx++)
	COPYRGB(&pixbuf[fx][0], pixbkgr);
    for (fx = fxbeg; fx <= fxfin; fx += zoom)
	COPYRGB(&pixbuf[fx-fxbeg][0], &pixgrid[0]);
    for (fy = fybeg; fy <= fyfin; fy++)
	(void) fb_write(fbiop, fxbeg, fy, (unsigned char *)pixbuf, fgridwid);
    for (fy = 0; fy < devwid; fy++)
	(void) fb_write(fbiop, fxorg, fy, pixaxis, 1);

    /* draw horizontal lines */
    if (zoom > 1)
	for (fy = fybeg; fy <= fyfin; fy += zoom)
	    (void) fb_write(fbiop,
			    fxbeg, fy, pixgrid, fgridwid);
    for (fx = 0; fx < devwid; fx++)
	COPYRGB(&pixbuf[fx][0], pixaxis);
    (void) fb_write(fbiop, 0, fyorg, (unsigned char *)pixbuf, devwid);
    return;
}
예제 #7
0
파일: pl-fb.c 프로젝트: cciechad/brlcad
/*
 *	Raster - rasterize stroke.
 *
 *  If immediate mode, draw the individual pixel on the frame buffer.
 *  If banded buffered mode, draw the portion in this band.  If it
 *     overflows into next band, requeue; else free the descriptor.
 *
 *  Method:
 *	Modified Bresenham algorithm.  Guaranteed to mark a dot for
 *	a zero-length stroke.  Please do not try to "improve" this code
 *	as it is extremely hard to get all aspects just right.
 */
static void
Raster(register stroke *vp, register struct band *np)
    /* -> rasterization descr */
    /* *np -> next band 1st descr */
{
    register short	dy;		/* raster within active band */

    CK_STROKE(vp);

    /*
     *  Draw the portion within this band.
     */
    for ( dy = vp->pixel.y - ystart; dy < lines_per_band; ) {

	/* set the appropriate pixel in the buffer */
	if ( immediate )  {
	    fb_write( fbp, vp->pixel.x, dy, vp->col, 1 );
	}  else  {
	    register unsigned char *pp;

	    pp = (unsigned char *)&buffer[((dy*Npixels) + vp->pixel.x)*sizeof(RGBpixel)];
	    COPYRGB( pp, vp->col );
	}

	if ( vp->major-- == 0 ) {
	    /* done! */
	    FREE_STROKE( vp );	/* return to "malloc" */
	    return;
	}

	if ( vp->e < 0 ) {
	    /* advance major & minor */
	    dy += vp->ysign;
	    vp->pixel.x += vp->xsign;
	    vp->e += vp->de;
	} else {
	    /* advance major only */
	    if ( vp->ymajor )	/* Y is major dir */
		++dy;
	    else			/* X is major dir */
		vp->pixel.x += vp->xsign;
	    vp->e -= vp->minor;
	}
    }

    /* overflow into next band; re-queue */
    vp->pixel.y = ystart + lines_per_band;
    Requeue( np, vp );       /* DDA parameters already set */
}
예제 #8
0
파일: pl-fb.c 프로젝트: cciechad/brlcad
/*
 *			P R E P _ D D A
 *
 *  Set up multi-band DDA parameters for stroke
 */
static void
prep_dda(register stroke *vp, register coords *pt1, register coords *pt2)
{
    CK_STROKE(vp);
    vp->pixel = *pt1;		/* initial pixel */
    vp->major = pt2->y - vp->pixel.y;	/* always nonnegative */
    vp->ysign = vp->major ? 1 : 0;
    vp->minor = pt2->x - vp->pixel.x;
    COPYRGB( vp->col, cur_color );
    if ( (vp->xsign = vp->minor ? (vp->minor > 0 ? 1 : -1) : 0) < 0 )
	vp->minor = -vp->minor;

    /* if Y is not really major, correct the assignments */
    if ( !(vp->ymajor = vp->minor <= vp->major) )  {
	register short	temp;	/* temporary for swap */

	temp = vp->minor;
	vp->minor = vp->major;
	vp->major = temp;
    }

    vp->e = vp->major / 2 - vp->minor;	/* initial DDA error */
    vp->de = vp->major - vp->minor;
}
예제 #9
0
파일: char.c 프로젝트: cciechad/brlcad
void
menu_char(int x_adjust, int menu_wid, int odd, register unsigned char *menu_border)
{
    register int    i, j, k;
    int embold = 1;
    int base;
    int totwid = font.width;
    /* Read in the character bit map, with two blank lines on each end. */
    for (i = 0; i < 2; i++)
	clear_buf (totwid, filterbuf[i]);
    for (i = font.height + 1; i >= 2; i--)
	fill_buf (font.width, filterbuf[i]);
    for (i = font.height + 2; i < font.height + 4; i++)
	clear_buf (totwid, filterbuf[i]);

    for (k=0; k<embold; k++)
	for (i=2; i<font.height+2; i++)
	    for (j=totwid+1; j>=2; j--)
		filterbuf[i][j+1] |= filterbuf[i][j];

    /* Initial base line for filtering depends on odd flag. */
    base = (odd ? 1 : 2);

    /* Change bits in menu that correspond to character bitmap. */
    for (i = font.height + base, k = 0; i >= base; i--, k++)
    {
	register RGBpixel *menu;
	menu = menu_addr + k * menu_wid + x_adjust;
	for (j = 0; j < (totwid + 3) - 1; j++, menu++ )
	    if ( filterbuf[i][j] )
	    {
		COPYRGB(*menu, menu_border);
	    }
    }
    return;
}
static bool_t
pars_Argv(int argc, char **argv)
{
    int c;

    /* Parse options. */
    while ((c = bu_getopt(argc, argv, OPT_STRING)) != -1) {
	switch (c) {
	    case 'C':
		color_flag = 1;
		break;
	    case 'M': {
		RGBpixel lo_rgb, hi_rgb;
		int lo_red, lo_grn, lo_blu;
		int hi_red, hi_grn, hi_blu;

		if (sscanf(bu_optarg, "%d %d %d %d %d %d",
			   &lo_red, &lo_grn, &lo_blu,
			   &hi_red, &hi_grn, &hi_blu)
		    < 3) {
		    bu_log("cell-fb: Invalid color-mapping: '%s'\n",
			   bu_optarg);
		    return 0;
		}
		lo_rgb[RED] = lo_red;
		lo_rgb[GRN] = lo_grn;
		lo_rgb[BLU] = lo_blu;
		hi_rgb[RED] = hi_red;
		hi_rgb[GRN] = hi_grn;
		hi_rgb[BLU] = hi_blu;
		fill_colortbl(lo_rgb, hi_rgb);
		break;
	    }
	    case 'F':
		(void) bu_strlcpy(fbfile, bu_optarg, sizeof(fbfile));
		break;
	    case 'N':
		if (sscanf(bu_optarg, "%d", &fb_height) < 1) {
		    bu_log("cell-fb: Invalid frame-buffer height: '%s'\n", bu_optarg);
		    return 0;
		}
		if (fb_height < -1) {
		    bu_log("cell-fb: Frame-buffer height out of range: %d\n", fb_height);
		    return 0;
		}
		break;
	    case 'W':
		if (sscanf(bu_optarg, "%d", &fb_width) < 1) {
		    bu_log("cell-fb: Invalid frame-buffer width: '%s'\n", bu_optarg);
		    return 0;
		}
		if (fb_width < -1) {
		    bu_log("cell-fb: Frame-buffer width out of range: %d\n", fb_width);
		    return 0;
		}
		break;
	    case 'S':
		if (sscanf(bu_optarg, "%d", &fb_height) < 1) {
		    bu_log("cell-fb: Invalid frame-buffer dimension: '%s'\n", bu_optarg);
		    return 0;
		}
		if (fb_height < -1) {
		    bu_log("cell-fb: Frame-buffer dimensions out of range: %d\n",
			   fb_height);
		    return 0;
		}
		fb_width = fb_height;
		break;
	    case 'X':
		if (sscanf(bu_optarg, "%x", &debug_flag) < 1) {
		    bu_log("cell-fb: Invalid debug flag: '%s'\n", bu_optarg);
		    return 0;
		}
		break;
	    case 'a': {
		fastf_t h;
		fastf_t v;
		double scan[2];
		struct locrec *lrp;

		if (sscanf(bu_optarg, "%lf %lf", &scan[0], &scan[1]) != 2) {
		    bu_log("cell-fb: Invalid grid-plane location: '%s'\n", bu_optarg);
		    return 0;
		}
		/* double to fastf_t */
		h = scan[0];
		v = scan[1];
		lrp = mk_locrec(h, v);
		BU_LIST_INSERT(&(gp_locs.l), &(lrp->l));
	    }
		break;
	    case 'b':
		if (sscanf(bu_optarg, "%lf", &bool_val) != 1) {
		    bu_log("cell-fb: Invalid boolean value: '%s'\n", bu_optarg);
		    return 0;
		}
		boolean_flag = 1;
		break;
	    case 'c':
		if (sscanf(bu_optarg, "%lf", &cell_size) != 1) {
		    bu_log("cell-fb: Invalid cell size: '%s'\n", bu_optarg);
		    return 0;
		}
		if (cell_size <= 0) {
		    bu_log("cell-fb: Cell size out of range: %lf\n", cell_size);
		    return 0;
		}
		break;
	    case 'd':
		if (sscanf(bu_optarg, "%lf %lf", &dom_min, &dom_max) < 2) {
		    bu_log("cell-fb: Invalid domain for input: '%s'\n", bu_optarg);
		    return 0;
		}
		if (dom_min >= dom_max) {
		    bu_log("Bad domain for input: [%lf, %lf]\n",
			   dom_min, dom_max);
		    return 0;
		}
		dom_cvt = 10.0 / (dom_max - dom_min);
		break;
	    case 'e':
		erase_flag = 1;
		break;
	    case 'f':
		if (sscanf(bu_optarg, "%d", &field) != 1) {
		    bu_log("cell-fb: Invalid field: '%s'\n", bu_optarg);
		    return 0;
		}
		break;
	    case 'g':
		grid_flag = 1;
		break;
	    case 'i':
		interp_flag = 0;
		break;
	    case 'k':
		key_flag = 1;
		key_height = 2.5;
		break;
	    case 'l':
		if (sscanf(bu_optarg, "%lf%lf", &az, &el) != 2) {
		    bu_log("cell-fb: Invalid view: '%s'\n", bu_optarg);
		    return 0;
		}
		log_flag = 1;
		if (view_flag == 0)
		    view_flag = 1;
		break;
	    case 'm': {
		double value;
		RGBpixel rgb;
		int red, grn, blu;
		int idx;

		if (sscanf(bu_optarg, "%lf %d %d %d", &value, &red, &grn, &blu)
		    < 4) {
		    bu_log("cell-fb: Invalid color-mapping: '%s'\n", bu_optarg);
		    return 0;
		}
		value *= 10.0;
		idx = value + 0.01;
		if (idx < 0 || idx > MAX_COLORTBL) {
		    bu_log("Value out of range (%s)\n", bu_optarg);
		    return 0;
		}
		rgb[RED] = red;
		rgb[GRN] = grn;
		rgb[BLU] = blu;
		COPYRGB(colortbl[idx], rgb);
		break;
	    }
	    case 'p':
		switch (sscanf(bu_optarg, "%d %d", &xorigin, &yorigin)) {
		    case 2: break;
		    case 1: yorigin = xorigin; break;
		    default:
			bu_log("cell-fb: Invalid offset: '%s'\n", bu_optarg);
			return 0;
		}
		break;
	    case 's':
		switch (sscanf(bu_optarg, "%d %d", &wid, &hgt)) {
		    case 2: break;
		    case 1: hgt = wid; break;
		    default:
			bu_log("cell-fb: Invalid cell scale: '%s'\n", bu_optarg);
			return 0;
		}
		break;
	    case 'v':
		if (sscanf(bu_optarg, "%d", &view_flag) < 1) {
		    bu_log("cell-fb: Invalid view number: '%s'\n", bu_optarg);
		    return 0;
		}
		if (view_flag == 0)
		    log_flag = 0;
		break;
	    case 'x':
		if (sscanf(bu_optarg, "%x", (unsigned int *)&bu_debug) < 1) {
		    bu_log("cell-fb: Invalid debug flag: '%s'\n", bu_optarg);
		    return 0;
		}
		break;
	    default:
		return 0;
	}
    }

    if (argc == bu_optind + 1) {
	if ((filep = fopen(argv[bu_optind], "rb")) == NULL) {
	    bu_log("Cannot open file '%s'\n", argv[bu_optind]);
	    return 0;
	}
    } else if (argc != bu_optind) {
	bu_log("Too many arguments!\n");
	return 0;
    } else
	filep = stdin;

    /* if fb_height/width has not been set, do snug fit
     * else if fb_height/width set to 0 force loose fit
     * else take user specified dimensions
     */
    compute_fb_height = (fb_height == -1) ? SNUG_FIT :
	(fb_height == 0) ? LOOSE_FIT : 0;
    compute_fb_width = (fb_width == -1) ? SNUG_FIT :
	(fb_width == 0) ? LOOSE_FIT : 0;
    return 1;
}
static bool_t
display_Cells(long int ncells)
{
    Cell *gp, *ep = &grid[ncells];
    static int zoom;
    unsigned char *buf;
    static RGBpixel pixel;
    double lasty = -INFINITY;
    double dx, dy;
    int y_0 = 0, y_1;

    if (compute_fb_height) {
	dy = ((ymax - ymin) / cell_size + 1.0) * (hgt + grid_flag);
	if (compute_fb_height == SNUG_FIT)
	    fb_height = dy + (key_flag * 2 * hgt) + yorigin;
	else if (dy > LORES)	/* LOOSE_FIT */
	    fb_height = HIRES;
	else
	    fb_height = LORES;
    }
    if (compute_fb_width) {
	dx = ((xmax - xmin) / cell_size + 1.0) * (wid + grid_flag);
	if (compute_fb_width == SNUG_FIT)
	    fb_width = dx + xorigin;
	else if (dx > LORES)	/* LOOSE_FIT */
	    fb_width = HIRES;
	else
	    fb_width = LORES;
    }

    zoom = 1;
    fbiop = fb_open((fbfile[0] != '\0') ? fbfile : NULL, fb_width, fb_height);
    if (fbiop == FB_NULL)
	return 0;
    if (compute_fb_height || compute_fb_width) {
	bu_log("fb_size requested: %d %d\n", fb_width, fb_height);
	fb_width = fb_getwidth(fbiop);
	fb_height = fb_getheight(fbiop);
	bu_log("fb_size obtained: %d %d\n", fb_width, fb_height);
    }
    if (fb_wmap(fbiop, COLORMAP_NULL) == -1)
	bu_log("Cannot initialize color map\n");
    if (fb_zoom(fbiop, zoom, zoom) == -1)
	bu_log("Cannot set zoom <%d, %d>\n", zoom, zoom);
    if (erase_flag && fb_clear(fbiop, BACKGROUND) == -1)
	bu_log("Cannot clear frame buffer\n");

    buf = (unsigned char *) bu_malloc(sizeof(RGBpixel) * fb_width,
				      "line of frame buffer");
    if (debug_flag & CFB_DBG_MEM)
	bu_log("buf = %p... %d pixels @ %lu bytes/pixel\n",
	       (void *)buf, fb_width, sizeof(RGBpixel));

    for (gp = grid; gp < ep; gp++) {
	int x0, x1;

	/* Whenever Y changes, write out row of cells. */
	if (!ZERO(lasty - gp->c_y)) {
	    /* If first time, nothing to write out. */
	    if (!ZERO(lasty - INFINITY)) {
		if (debug_flag & CFB_DBG_GRID)
		    bu_log("%g = V2SCRY(%g)\n", V2SCRY(lasty), lasty);
		y_0 = V2SCRY(lasty);
		if (y_0 >= 0 && y_0 < fb_height) {
		    for (y_1 = y_0 + hgt; y_0 < y_1; y_0++)
			if (fb_write(fbiop, 0, y_0, buf, fb_width) == -1) {
			    bu_log("Couldn't write to <%d, %d>\n", 0, y_0);
			    (void) fb_close(fbiop);
			    return 0;
			}
		}
	    }
	    /* Clear buffer. */
	    for (x0 = 0; x0 < fb_width; x0++) {
		COPYRGB(&buf[3*x0], BACKGROUND);
	    }

	    /* Draw grid line between rows of cells. */
	    if (grid_flag && !ZERO(lasty - INFINITY)) {
		if (fb_write(fbiop, 0, y_0, buf, fb_width) == -1) {
		    bu_log("Couldn't write to <%d, %d>\n", 0, y_0);
		    (void) fb_close(fbiop);
		    return 0;
		}
		if (debug_flag & CFB_DBG_GRID)
		    bu_log("Writing grid row at %d\n", y_0);
	    }
	    lasty = gp->c_y;
	}
	val_To_RGB(gp->c_val, pixel);
	/* Be careful only to write color within bounds of the screen */
	x0 = H2SCRX(gp->c_x);
	if (x0 >= 0 && x0 <= fb_width - wid) {
	    for (x1 = x0 + wid; x0 < x1;  x0++) {
		COPYRGB(&buf[3*x0], pixel);
	    }
	}
    }

    /* Write out last row of cells. */
    if (debug_flag & CFB_DBG_GRID)
	bu_log("%g = V2SCRY(%g)\n", V2SCRY(lasty), lasty);
    for (y_0 = V2SCRY(lasty), y_1 = y_0 + hgt; y_0 < y_1;  y_0++)
	if (fb_write(fbiop, 0, y_0, buf, fb_width) == -1) {
	    bu_log("Couldn't write to <%d, %d>\n", 0, y_0);
	    (void) fb_close(fbiop);
	    return 0;
	}
    /* Draw color key. */
    if (key_flag && (fb_width < (10 + 1) * wid))
	bu_log("Width of key (%d) would exceed frame-buffer width (%d)\n",
	       (10 + 1) * wid, fb_width);
    else if (key_flag) {
	int i, j;
	double base;
	int scr_min, scr_max;
	int scr_center;	/* screen coord of center of view */
	int center_cell;	/* cell # of center of view */

	/* Clear buffer. */
	for (i = 0; i < fb_width; i++) {
	    COPYRGB(&buf[3*i], BACKGROUND);
	}
	/* Center the color key from side-to-side in the viewport.
	 * Find screen coords of min and max vals, clip to (0, fb_width).
	 * If there are fewer than 11 cells, the run the key
	 * from the left edge to beyond the right edge.
	 */
	scr_min = H2SCRX(xmin);
	scr_max = H2SCRX(xmax);
	CLAMP(scr_min, 0, fb_width);
	CLAMP(scr_max, 0, fb_width);

	scr_center = (scr_max + scr_min)/2;
	if ((center_cell = VPX2CX(SCRX2VPX(scr_center))) < 5)
	    center_cell = 5;

	/* Draw 10 cells for the color key */
	dom_cvt = 10.0;
	for (i = 0; i <= 10; i++) {
	    cell_val cv;

	    /*
	     * Determine where to start the key,
	     * being careful not to back up beyond the beginning of buf.
	     */
	    base = VPX2SCRX(CX2VPX(center_cell - 10/2 + i));

	    cv.v_scalar = i / 10.0;

	    val_To_RGB(cv, pixel);
	    for (j = 0; j < wid; j++) {
		int idx = base + j;
		COPYRGB(&buf[3*idx], pixel);
	    }
	}
	dom_cvt = 10.0 / (dom_max - dom_min);

	for (i = yorigin; i < yorigin+hgt; i++)
	    if (fb_write(fbiop, 0, i, buf, fb_width) == -1) {
		bu_log("Couldn't write to <%d, %d>\n", 0, i);
		(void) fb_close(fbiop);
		return 0;
	    }
    }
    (void) fb_close(fbiop);

    bu_free((char *) buf, "line of frame buffer");
    if (debug_flag & CFB_DBG_MEM)
	bu_log("freed buf, which is now %p\n", (void *)buf);
    return 1;
}
예제 #12
0
파일: fbcbars.c 프로젝트: cciechad/brlcad
int
main(int argc, char **argv)
{
    register int x, y;
    register FBIO *fbp;

    if ( !get_args( argc, argv ) )  {
	(void)fputs(usage, stderr);
	bu_exit( 1, NULL );
    }

    if ( (fbp = fb_open( framebuffer, scr_width, scr_height )) == NULL )
	bu_exit(12, NULL);

    /* Get the screen size we were actually given */
    scr_width = fb_getwidth(fbp);
    scr_height = fb_getheight(fbp);

    /*
     *  Operation is bottom-to-top.
     */
    switch (mode)  {
	case M_FCC:
	    for ( x=0; x<scr_width; x++) {
		COPYRGB( &scanline[3*x], fcc_all[x*8/scr_width] );
	    }
	    for ( y=0; y<scr_height; y++)
		fb_write( fbp, 0, y, scanline, scr_width );
	    break;

	case M_EIA:
	    /*
	     *  Build bottom line, and send it for 1/4th of the screen,
	     *  then build the top line, and fill the rest of the screen.
	     */
	    for ( x=0; x<scr_width; x++) {
		COPYRGB( &scanline[3*x], botpart[x*5/scr_width] );
	    }
	    for ( y=0; y<(scr_height/4); y++)
		fb_write( fbp, 0, y, scanline, scr_width );

	    for ( x=0; x<scr_width; x++)  {
		COPYRGB( &scanline[3*x], eia_top[x*7/scr_width] );
	    }
	    for (; y<scr_height; y++)
		fb_write( fbp, 0, y, scanline, scr_width );
	    break;

	case M_SMPTE:
	    /*
	     *  Build bottom line, and send it for 3/16th of the screen,
	     *  then send the SMPTE middle for 1/16th of the screen,
	     *  then build the top line, and fill the rest of the screen.
	     *  (Convert upper 1/4 of EIA -I white Q black to smpte)
	     */
	    for ( x=0; x<scr_width; x++) {
		COPYRGB( &scanline[3*x], botpart[x*5/scr_width] );
	    }
	    for ( y=0; y<(scr_height*3/16); y++)
		fb_write( fbp, 0, y, scanline, scr_width );

	    for ( x=0; x<scr_width; x++) {
		COPYRGB( &scanline[3*x], smpte_middle[x*7/scr_width] );
	    }
	    for (; y<(scr_height*4/16); y++)
		fb_write( fbp, 0, y, scanline, scr_width );

	    for ( x=0; x<scr_width; x++)  {
		COPYRGB( &scanline[3*x], eia_top[x*7/scr_width] );
	    }
	    for (; y<scr_height; y++)
		fb_write( fbp, 0, y, scanline, scr_width );
	    break;
    }
    fb_close(fbp);
    return(0);
}