Пример #1
0
/*
 * Just free the data structures, don't do graphics
 */
void
memlfree(Memimage *i)
{
	Memlayer *l;

	l = i->layer;
	freememimage(l->save);
	free(l);
	freememimage(i);
}
Пример #2
0
int
memlsetrefresh(Memimage *i, Refreshfn fn, void *ptr)
{
    Memlayer *l;

    l = i->layer;
    if(l->refreshfn!=0 && fn!=0) {	/* just change functions */
        l->refreshfn = fn;
        l->refreshptr = ptr;
        return 1;
    }

    if(l->refreshfn == 0) {	/* is using backup image; just free it */
        freememimage(l->save);
        l->save = nil;
        l->refreshfn = fn;
        l->refreshptr = ptr;
        return 1;
    }

    l->save = allocmemimage(i->r, i->chan);
    if(l->save == nil)
        return 0;
    /* easiest way is just to update the entire save area */
    l->refreshfn(i, i->r, l->refreshptr);
    l->refreshfn = 0;
    l->refreshptr = nil;
    return 1;
}
Пример #3
0
static
void
freecimage(Cimage *ci)
{
	Cimage *ci1;

	qlock(&cimagelock);
	if(decref(ci) == 0){
		if(ci->i)
			freeimage(ci->i);
		else if(ci->mi)
			freememimage(ci->mi);
		urlfree(ci->url);
		ci1 = cimages;
		if(ci1 == ci)
			cimages = ci->next;
		else{
			while(ci1){
				if(ci1->next == ci){
					ci1->next = ci->next;
					break;
				}
				ci1 = ci1->next;
			}
		}
		free(ci);
	}
	qunlock(&cimagelock);
}
Пример #4
0
void
swcursorinit(void)
{
	static int init, warned;
	VGAscr *scr;

	didswcursorinit = 1;
	if(!init){
		init = 1;
		addclock0link(swcursorclock, 10);
	}
	scr = &vgascreen[0];
	if(scr==nil || scr->gscreen==nil)
		return;

	if(scr->dev == nil || scr->dev->linear == nil){
		if(!warned){
			print("cannot use software cursor on non-linear vga screen\n");
			warned = 1;
		}
		return;
	}

	if(swback){
		freememimage(swback);
		freememimage(swmask);
		freememimage(swmask1);
		freememimage(swimg);
		freememimage(swimg1);
	}

	swback = allocmemimage(Rect(0,0,32,32), gscreen->chan);
	swmask = allocmemimage(Rect(0,0,16,16), GREY8);
	swmask1 = allocmemimage(Rect(0,0,16,16), GREY1);
	swimg = allocmemimage(Rect(0,0,16,16), GREY8);
	swimg1 = allocmemimage(Rect(0,0,16,16), GREY1);
	if(swback==nil || swmask==nil || swmask1==nil || swimg==nil || swimg1 == nil){
		print("software cursor: allocmemimage fails");
		return;
	}

	memfillcolor(swmask, DOpaque);
	memfillcolor(swmask1, DOpaque);
	memfillcolor(swimg, DBlack);
	memfillcolor(swimg1, DBlack);
}
Пример #5
0
void
main(int argc, char *argv[])
{
	Biobuf bout;
	Memimage *i;
	int fd;
	char *err, *filename;
	ImageInfo II;

	ARGBEGIN{
	case 'c':
		II.comment = ARGF();
		if(II.comment == nil)
			usage();
		II.fields_set |= II_COMMENT;
		break;
	case 'g':
		II.gamma = atof(ARGF());
		if(II.gamma == 0.)
			usage();
		II.fields_set |= II_GAMMA;
		break;
	case 't':
		break;
	default:
		usage();
	}ARGEND

	if(Binit(&bout, 1, OWRITE) < 0)
		sysfatal("Binit failed: %r");
	memimageinit();

	if(argc == 0){
		fd = 0;
		filename = "<stdin>";
	}else{
		fd = open(argv[0], OREAD);
		if(fd < 0)
			sysfatal("can't open %s: %r", argv[0]);
		filename = argv[0];
	}

	i = readmemimage(fd);
	if(i == nil)
		sysfatal("can't readimage %s: %r", filename);
	close(fd);

	err = memwritepng(&bout, i, &II);
	freememimage(i);

	if(err != nil)
		fprint(2, "topng: %s\n", err);
	exits(err);
}
Пример #6
0
Memsubfont*
openmemsubfont(char *name)
{
	Memsubfont *sf;
	Memimage *i;
	Fontchar *fc;
	int fd, n;
	char hdr[3*12+4+1];
	uchar *p;

	fd = open(name, OREAD);
	if(fd < 0)
		return nil;
	p = nil;
	i = readmemimage(fd);
	if(i == nil)
		goto Err;
	if(readn(fd, hdr, 3*12) != 3*12){
		werrstr("openmemsubfont: header read error: %r");
		goto Err;
	}
	n = atoi(hdr);
	if(n <= 0 || n > 0x7fff){
		werrstr("openmemsubfont: bad fontchar count %d", n);
		goto Err;
	}
	p = malloc(6*(n+1));
	if(p == nil)
		goto Err;
	if(readn(fd, p, 6*(n+1)) != 6*(n+1)){
		werrstr("openmemsubfont: fontchar read error: %r");
		goto Err;
	}
	fc = malloc(sizeof(Fontchar)*(n+1));
	if(fc == nil)
		goto Err;
	_unpackinfo(fc, p, n);
	sf = allocmemsubfont(name, n, atoi(hdr+12), atoi(hdr+24), fc, i);
	if(sf == nil){
		free(fc);
		goto Err;
	}
	close(fd);
	free(p);
	return sf;
Err:
	close(fd);
	free(p);
	freememimage(i);
	return nil;
}
Пример #7
0
static void
xdestroyfid(Fid *fid)
{
	Memsubfont *sf;
	
	sf = fid->aux;
	if(sf == nil)
		return;

	freememimage(sf->bits);
	free(sf->info);
	free(sf);
	fid->aux = nil;
}
Пример #8
0
int
memunload(Memimage *src, Rectangle r, uint8_t *data, int n)
{
	Memimage *tmp;
	Memlayer *dl;
	Rectangle lr;
	int dx;

    Top:
	dl = src->layer;
	if(dl == nil)
		return unloadmemimage(src, r, data, n);

	/*
 	 * Convert to screen coordinates.
	 */
	lr = r;
	r.min.x += dl->delta.x;
	r.min.y += dl->delta.y;
	r.max.x += dl->delta.x;
	r.max.y += dl->delta.y;
	dx = dl->delta.x&(7/src->depth);
	if(dl->clear && dx==0){
		src = dl->screen->image;
		goto Top;
	}

	/*
	 * src is an obscured layer or data is unaligned
	 */
	if(dl->save && dx==0){
		if(dl->refreshfn != nil)
			return -1;	/* can't unload window if it's not Refbackup */
		if(n > 0)
			memlhide(src, r);
		n = unloadmemimage(dl->save, lr, data, n);
		return n;
	}
	tmp = allocmemimage(lr, src->chan);
	if(tmp == nil)
		return -1;
	memdraw(tmp, lr, src, lr.min, nil, lr.min, S);
	n = unloadmemimage(tmp, lr, data, n);
	freememimage(tmp);
	return n;
}
Пример #9
0
void
getimage(Cimage *ci, Rune *altr)
{
    Rectangle r;
    Memimage *mi;
    Image *i, *i2;
    char buf[128];
    uchar *bits;
    int nbits;

    mi = ci->mi;
    if(mi == nil) {
        snprint(buf, sizeof(buf), "[%S]", altr ? altr : L"IMG");
        r.min = Pt(0, 0);
        r.max.x = 2*Space + stringwidth(font, buf);
        r.max.y = 2*Space + font->height;
        ci->i = eallocimage(display, r, GREY1, 1, DBlack);
        r.min.x += Space;
        r.min.y += Space;
        string(ci->i, r.min, display->white, ZP, font, buf);
        return;
    }
    nbits = bytesperline(mi->r, mi->depth)*Dy(mi->r);
    bits = emalloc(nbits);
    unloadmemimage(mi, mi->r, bits, nbits);
    /*
    	/* get rid of alpha channel from transparent gif * /

    	if(mi->depth == 16){
    		for(y=1; y<nbits; y+=2)
    			bits[y>>1] = bits[y];
    	}
    */
    i = eallocimage(display, mi->r, mi->chan, 0, DNofill);
    loadimage(i, i->r, bits, nbits);
    i2 = eallocimage(display, i->r, RGB24, 1, DNofill);
    draw(i2, i2->r, display->black, nil, ZP);
    draw(i2, i2->r, i, nil, i->r.min);
    free(bits);
    freememimage(mi);
    freeimage(i);
    ci->i = i2;
    ci->mi = nil;
}
Пример #10
0
static void
screenwin(void)
{
	Point p, q;
	char *greet;
	Memimage *orange;
	Rectangle r;

	memsetchan(gscreen, RGB16);

	back = memwhite;
	conscol = memblack;

	orange = allocmemimage(Rect(0,0,1,1), RGB16);
	orange->flags |= Frepl;
	orange->clipr = gscreen->r;
	orange->data->bdata[0] = 0x40;
	orange->data->bdata[1] = 0xfd;

	w = memdefont->info[' '].width;
	h = memdefont->height;

	r = insetrect(gscreen->r, 4);

	memimagedraw(gscreen, r, memblack, ZP, memopaque, ZP, S);
	window = insetrect(r, 4);
	memimagedraw(gscreen, window, memwhite, ZP, memopaque, ZP, S);

	memimagedraw(gscreen, Rect(window.min.x, window.min.y,
			window.max.x, window.min.y+h+5+6), orange, ZP, nil, ZP, S);
	freememimage(orange);
	window = insetrect(window, 5);

	greet = " Plan 9 Console ";
	p = addpt(window.min, Pt(10, 0));
	q = memsubfontwidth(memdefont, greet);
	memimagestring(gscreen, p, conscol, ZP, memdefont, greet);
	flushmemscreen(r);
	window.min.y += h+6;
	curpos = window.min;
	window.max.y = window.min.y+((window.max.y-window.min.y)/h)*h;
}
Пример #11
0
Файл: term.c Проект: npe9/harvey
static void
screenwin(void)
{
	Point p;
	char *greet;
	Memimage *grey;

	drawqlock();
	back = memwhite;
	conscol = memblack;
	memfillcolor(gscreen, 0x444488FF);
	
	h = memdefont->height;

	window.min = addpt(gscreen->r.min, Pt(20,20));
	window.max.x = window.min.x + Dx(gscreen->r)*3/4-40;
	window.max.y = window.min.y + Dy(gscreen->r)*3/4-100;

	memimagedraw(gscreen, window, memblack, ZP, memopaque, ZP, S);
	window = insetrect(window, 4);
	memimagedraw(gscreen, window, memwhite, ZP, memopaque, ZP, S);

	/* a lot of work to get a grey color */
	grey = allocmemimage(Rect(0,0,1,1), CMAP8);
	grey->flags |= Frepl;
	grey->clipr = gscreen->r;
	memfillcolor(grey, 0xAAAAAAFF);
	memimagedraw(gscreen, Rect(window.min.x, window.min.y,
			window.max.x, window.min.y+h+5+6), grey, ZP, nil, ZP, S);
	freememimage(grey);
	window = insetrect(window, 5);

	greet = " Plan 9 Console ";
	p = addpt(window.min, Pt(10, 0));
	memimagestring(gscreen, p, conscol, ZP, memdefont, greet);
	window.min.y += h+6;
	curpos = window.min;
	window.max.y = window.min.y+((window.max.y-window.min.y)/h)*h;
	flushmemscreen(gscreen->r);
	drawqunlock();
}
Пример #12
0
Memsubfont*
getmemdefont(void)
{
	char *hdr, *p;
	int n;
	Fontchar *fc;
	Memsubfont *f;
	int ld;
	Rectangle r;
	Memdata *md;
	Memimage *i;

	/*
	 * make sure data is word-aligned.  this is true with Plan 9 compilers
	 * but not in general.  the byte order is right because the data is
	 * declared as char*, not u32int*.
	 */
	p = (char*)defontdata;
	n = (uintptr)p & 3;
	if(n != 0){
		memmove(p+(4-n), p, sizeofdefont-n);
		p += 4-n;
	}
	ld = atoi(p+0*12);
	r.min.x = atoi(p+1*12);
	r.min.y = atoi(p+2*12);
	r.max.x = atoi(p+3*12);
	r.max.y = atoi(p+4*12);

	md = mallocz(sizeof(Memdata), 1);
	if(md == nil)
		return nil;
	
	p += 5*12;

	md->base = nil;		/* so freememimage doesn't free p */
	md->bdata = (uchar*)p;	/* ick */
	md->ref = 1;
	md->allocd = 1;		/* so freememimage does free md */

	i = allocmemimaged(r, drawld2chan[ld], md, nil);
	if(i == nil){
		free(md);
		return nil;
	}

	hdr = p+Dy(r)*i->width*sizeof(u32int);
	n = atoi(hdr);
	p = hdr+3*12;
	fc = malloc(sizeof(Fontchar)*(n+1));
	if(fc == 0){
		freememimage(i);
		return 0;
	}
	_unpackinfo(fc, (uchar*)p, n);
	f = allocmemsubfont("*default*", n, atoi(hdr+12), atoi(hdr+24), fc, i);
	if(f == 0){
		freememimage(i);
		free(fc);
		return 0;
	}
	return f;
}
Пример #13
0
static int
xgraph(HConnect *c)
{
	char *name;
	Hio *hout;
	Memimage *m;
	int dotext;
	Graph g;
	Arg arg;
	char *graph, *a;

	name = hargstr(c, "arg", "");
	if((arg.index = findname(name)) == -1 && strcmp(name, "*") != 0){
		werrstr("unknown name %s", name);
		goto error;
	}
	a = hargstr(c, "arg2", "");
	if(a[0] && (arg.index2 = findname(a)) == -1){
		werrstr("unknown name %s", a);
		goto error;
	}

	g.arg = &arg;
	g.t0 = hargint(c, "t0", -120);
	g.t1 = hargint(c, "t1", 0);
	g.min = hargint(c, "min", -1);
	g.max = hargint(c, "max", -1);
	g.wid = hargint(c, "wid", -1);
	g.ht = hargint(c, "ht", -1);
	dotext = hargstr(c, "text", "")[0] != 0;
	g.fill = hargint(c, "fill", -1);
	
	graph = hargstr(c, "graph", "raw");
	if(strcmp(graph, "raw") == 0)
		g.fn = rawgraph;
	else if(strcmp(graph, "diskbw") == 0)
		g.fn = diskgraph;
	else if(strcmp(graph, "iobw") == 0)
		g.fn = iograph;
	else if(strcmp(graph, "netbw") == 0)
		g.fn = netgraph;
	else if(strcmp(graph, "diff") == 0)
		g.fn = diffgraph;
	else if(strcmp(graph, "pct") == 0)
		g.fn = pctgraph;
	else if(strcmp(graph, "pctdiff") == 0)
		g.fn = pctdiffgraph;
	else if(strcmp(graph, "divdiff") == 0)
		g.fn = divdiffgraph;
	else{
		werrstr("unknown graph %s", graph);
		goto error;
	}

	if(dotext){
		hsettype(c, "text/plain");
		dotextbin(&c->hout, &g);
		hflush(&c->hout);
		return 0;
	}

	m = statgraph(&g);
	if(m == nil)
		goto error;

	if(hsettype(c, "image/png") < 0)
		return -1;
	hout = &c->hout;
	writepng(hout, m);
	qlock(&memdrawlock);
	freememimage(m);
	qunlock(&memdrawlock);
	hflush(hout);
	return 0;

error:
	return herror(c);
}
Пример #14
0
/*
 * Place i so i->r.min = log, i->layer->screenr.min == scr.
*/
int
memlorigin(Memimage *i, Point log, Point scr)
{
	Memlayer *l;
	Memscreen *s;
	Memimage *t, *shad, *nsave;
	Rectangle x, newr, oldr;
	Point delta;
	int overlap, eqlog, eqscr, wasclear;

	l = i->layer;
	s = l->screen;
	oldr = l->screenr;
	newr = Rect(scr.x, scr.y, scr.x+Dx(oldr), scr.y+Dy(oldr));
	eqscr = eqpt(scr, oldr.min);
	eqlog = eqpt(log, i->r.min);
	if(eqscr && eqlog)
		return 0;
	nsave = nil;
	if(eqlog==0 && l->save!=nil){
		nsave = allocmemimage(Rect(log.x, log.y, log.x+Dx(oldr), log.y+Dy(oldr)), i->chan);
		if(nsave == nil)
			return -1;
	}

	/*
	 * Bring it to front and move logical coordinate system.
	 */
	memltofront(i);
	wasclear = l->clear;
	if(nsave){
		if(!wasclear)
			memimagedraw(nsave, nsave->r, l->save, l->save->r.min, nil, Pt(0,0), S);
		freememimage(l->save);
		l->save = nsave;
	}
	delta = subpt(log, i->r.min);
	i->r = rectaddpt(i->r, delta);
	i->clipr = rectaddpt(i->clipr, delta);
	l->delta = subpt(l->screenr.min, i->r.min);
	if(eqscr)
		return 0;

	/*
	 * To clean up old position, make a shadow window there, don't paint it,
	 * push it behind this one, and (later) delete it.  Because the refresh function
	 * for this fake window is a no-op, this will cause no graphics action except
	 * to restore the background and expose the windows previously hidden.
	 */
	shad = memlalloc(s, oldr, memlnorefresh, nil, DNofill);
	if(shad == nil)
		return -1;
	s->frontmost = i;
	if(s->rearmost == i)
		s->rearmost = shad;
	else
		l->rear->layer->front = shad;
	shad->layer->front = i;
	shad->layer->rear = l->rear;
	l->rear = shad;
	l->front = nil;
	shad->layer->clear = 0;

	/*
	 * Shadow is now holding down the fort at the old position.
	 * Move the window and hide things obscured by new position.
	 */
	for(t=l->rear->layer->rear; t!=nil; t=t->layer->rear){
		x = newr;
		overlap = rectclip(&x, t->layer->screenr);
		if(overlap){
			memlhide(t, x);
			t->layer->clear = 0;
		}
	}
	l->screenr = newr;
	l->delta = subpt(scr, i->r.min);
	l->clear = rectinrect(newr, l->screen->image->clipr);

	/*
	 * Everything's covered.  Copy to new position and delete shadow window.
	 */
	if(wasclear)
		memdraw(s->image, newr, s->image, oldr.min, nil, Pt(0,0), S);
	else
		memlexpose(i, newr);
	memldelete(shad);

	return 1;
}
Пример #15
0
void
screeninit(int x, int y, char *chanstr)
{
	Point p, q;
	char *greet;
	char buf[128];
	Memimage *grey;
	Rectangle r;
	int chan;

	cursorver = 0;

	memimageinit();
	chan = strtochan(chanstr);
	if(chan == 0)
		error("bad screen channel string");

	r = Rect(0, 0, x, y);
	gscreen = allocmemimage(r, chan);
	if(gscreen == nil){
		snprint(buf, sizeof buf, "can't allocate screen image: %r");
		error(buf);
	}

	offscreen = Pt(x + 100, y + 100);
	cursorr = Rect(0, 0, CURSORDIM, CURSORDIM);
	cursorset = allocmemimage(cursorr, GREY8);
	cursorclear = allocmemimage(cursorr, GREY1);
	if(cursorset == nil || cursorclear == nil){
		freememimage(gscreen);
		freememimage(cursorset);
		freememimage(cursorclear);
		gscreen = nil;
		cursorset = nil;
		cursorclear = nil;
		snprint(buf, sizeof buf, "can't allocate cursor images: %r");
		error(buf);
	}

	drawlock();

	/*
	 * set up goo for screenputs
	 */
	memdefont = getmemdefont();

	back = memwhite;
	conscol = memblack;

	/* a lot of work to get a grey color */
	curscol = allocmemimage(Rect(0,0,1,1), RGBA32);
	curscol->flags |= Frepl;
	curscol->clipr = gscreen->r;
	memfillcolor(curscol, 0xff0000ff);

	memfillcolor(gscreen, 0x444488FF);

	w = memdefont->info[' '].width;
	h = memdefont->height;

	window.min = addpt(gscreen->r.min, Pt(20,20));
	window.max.x = window.min.x + Dx(gscreen->r)*3/4-40;
	window.max.y = window.min.y + Dy(gscreen->r)*3/4-100;

	memimagedraw(gscreen, window, memblack, ZP, memopaque, ZP, S);
	window = insetrect(window, 4);
	memimagedraw(gscreen, window, memwhite, ZP, memopaque, ZP, S);

	/* a lot of work to get a grey color */
	grey = allocmemimage(Rect(0,0,1,1), CMAP8);
	grey->flags |= Frepl;
	grey->clipr = gscreen->r;
	memfillcolor(grey, 0xAAAAAAFF);
	memimagedraw(gscreen, Rect(window.min.x, window.min.y,
			window.max.x, window.min.y+h+5+6), grey, ZP, nil, ZP, S);
	freememimage(grey);
	window = insetrect(window, 5);

	greet = " Plan 9 Console ";
	p = addpt(window.min, Pt(10, 0));
	q = memsubfontwidth(memdefont, greet);
	memimagestring(gscreen, p, conscol, ZP, memdefont, greet);
	window.min.y += h+6;
	curpos = window.min;
	window.max.y = window.min.y+((window.max.y-window.min.y)/h)*h;
	flushmemscreen(gscreen->r);

	drawunlock();

	setcursor(&arrow);
}
Пример #16
0
void
imagebits(Biobuf *ioutb, Memimage *im)
{
	int spb;
	int bitoff;
	int j, n, n4, i, bpl, nrest;
	int lsf;
	uchar c85[6], *data, *src, *dst;
	Memimage *tmp;
	Rectangle r;

	tmp = nil;
	if (debug)
		fprint(2, "imagebits, r=%d %d %d %d, depth=%d\n",
			im->r.min.x, im->r.min.y, im->r.max.x, im->r.max.y, im->depth);
	width = Dx(im->r);
	height = Dy(im->r);
	bps = im->depth;	/* # bits per sample */
	bitoff = 0;		/* # bit offset of beginning sample within first byte */
	if (bps < 8) {
		spb = 8 / bps;
		bitoff = (im->r.min.x % spb) * bps;
	}
	if (bitoff != 0) {
/* 		# Postscript image wants beginning of line at beginning of byte */
		r = im->r;
		r.min.x -= bitoff/im->depth;
		r.max.x -= bitoff/im->depth;
		tmp = allocmemimage(r, im->chan);
		if(tmp == nil){
			fprint(2, "p9bitpost: allocmemimage failed: %r\n");
			exits("alloc");
		}
		memimagedraw(tmp, r, im, im->r.min, nil, ZP, S);
		im = tmp;
	}
	lsf = 0;
	/* compact data to remove word-boundary padding */
	bpl = bytesperline(im->r, im->depth);
	n = bpl*Dy(im->r);
	data = malloc(n);
	if(data == nil){
		fprint(2, "p9bitpost: malloc failed: %r\n");
		exits("malloc");
	}
	for(i=0; i<Dy(im->r); i++){
		/* memmove(data+bpl*i, byteaddr(im, Pt(im->r.min.x, im->r.min.y+i)), bpl); with inversion */
		dst = data+bpl*i;
		src = byteaddr(im, Pt(im->r.min.x, im->r.min.y+i));
		for(j=0; j<bpl; j++)
			*dst++ = 255 - *src++;
	}
	n4 = (n / 4) * 4;
	for (i = 0; i < n4; i += 4){
		cmap2ascii85(data+i, c85);
		lsf += strlen((char *)c85);
		Bprint(ioutb, "%s", (char *)c85);
		if (lsf > 74) {
			Bprint(ioutb, "\n");
			lsf = 0;
		}
	}
	nrest = n - n4;
	if (nrest != 0) {
		uchar foo[4];

		for (i=0; i<nrest; i++)
			foo[i] = data[n4+i];
		for (i=nrest; i<4; i++)
			foo[i] = '\0';
		cmap2ascii85(foo, c85);
		if (strcmp((char *)c85, "z") == 0 )
			strcpy((char *)c85, "!!!!!");
		Bprint(ioutb, "%.*s", nrest+1, (char *)c85);
	}
	Bprint(ioutb, "\n~>");
	Bprint(ioutb, "\n");
	freememimage(tmp);
}
Пример #17
0
int
image2psfile(int fd, Memimage *im, int dpi) {
	Rectangle r;
	Rectangle bbox;
	int e;
	int xmargin = 36;
	int ymargin = 36;
	double paperaspectratio;
	double imageaspectratio;
	Biobuf ioutb;
	Memimage *tmp;

	if(im->depth >= 8 && im->chan != CMAP8 && im->chan != GREY8){
		/*
		 * the postscript libraries can only handle [1248]-bit grey, 8-bit cmap,
		 * and 24-bit color, so convert.
		 */
		tmp = allocmemimage(im->r, strtochan("b8g8r8"));
		if(tmp == nil)
			return 1;
		memimagedraw(tmp, tmp->r, im, im->r.min, nil, ZP, S);
		freememimage(im);
		im = tmp;
	}

	Binit(&ioutb, fd, OWRITE);
 	r = im->r;
	width = Dx(r);
	height = Dy(r);
	imageaspectratio = (double) width / (double) height;
	if (landscape) {
		paperaspectratio = ((double)paperlength - (ymargin * 2)) / ((double)paperwidth - (xmargin * 2));
		if (dpi > 0) {
			iwidth = width * 72 / dpi;
			iheight = height * 72 / dpi;
		} else if (imageaspectratio > paperaspectratio) {
			iwidth = paperlength - (ymargin * 2);
			iheight = iwidth / imageaspectratio;
		} else {
			iheight = paperwidth - (xmargin * 2);
			iwidth  = iheight * imageaspectratio;
		}
		xstart = paperwidth - xmargin - (iheight * ymagnification);
		ystart = paperlength - ymargin;
		rotation = -90;
	} else {
		paperaspectratio = ((double)paperwidth - (xmargin * 2)) / ((double)paperlength - (ymargin * 2));
		if (dpi > 0) {
			iwidth = width * 72 / dpi;
			iheight = height * 72 / dpi;
		} else if (imageaspectratio > paperaspectratio) {
			iwidth = paperwidth - (xmargin * 2);
			iheight = iwidth / imageaspectratio;
		} else {
			iheight = paperlength - (ymargin * 2);
			iwidth  = iheight * imageaspectratio;
		}
		xstart = xmargin;
		ystart = paperlength - ymargin - (iheight * ymagnification);
		rotation = 0;
	}
	bbox = Rect(xstart,ystart,xstart+iwidth,ystart+iheight);
	e = preamble(&ioutb, bbox);
	if(e != 0)
		return e;
	Bprint(&ioutb, "%%%%Page: 1\n%%%%BeginPageSetup\n");
	Bprint(&ioutb, "/pgsave save def\n");
	Bprint(&ioutb, "%%%%EndPageSetup\n");
	bps = im->depth;
	Bprint(&ioutb, "%d 0 %d %d %d %d %d %d %s doimage\n", iheight, iwidth, ystart, xstart, height, width, bps, im->flags&Fgrey ? "true" : "false");
 	imagebits(&ioutb, im);
	Bprint(&ioutb, "pgsave restore\nshowpage\n");
	e = trailer(&ioutb, 1);
	if(e != 0)
		return e;
	Bterm(&ioutb);
	return 0;
}
Пример #18
0
void
main(int argc, char *argv[])
{
	Biobuf bout;
	Memimage *i, *ni;
	int fd, j, dt, trans, loop;
	char buf[256];
	char *err, *comment, *s;

	comment = nil;
	dt = -1;
	trans = -1;
	loop = UNSET;
	ARGBEGIN{
	case 'l':
		s = ARGF();
		if(s==nil || (!isdigit(s[0]) && s[0]!='-'))
			usage();
		loop = atoi(s);
		break;
	case 'c':
		comment = ARGF();
		if(comment == nil)
			usage();
		break;
	case 'd':
		s = ARGF();
		if(s==nil || !isdigit(s[0]))
			usage();
		dt = atoi(s);
		break;
	case 't':
		s = ARGF();
		if(s==nil || !isdigit(s[0]))
			usage();
		trans = atoi(s);
		if(trans > 255)
			usage();
		break;
	default:
		usage();
	}ARGEND

	if(Binit(&bout, 1, OWRITE) < 0)
		sysfatal("Binit failed: %r");

	memimageinit();

	err = nil;

	if(argc == 0){
		i = readmemimage(0);
		if(i == nil)
			sysfatal("reading input: %r");
		ni = memonechan(i);
		if(ni == nil)
			sysfatal("converting image to RGBV: %r");
		if(i != ni){
			freememimage(i);
			i = ni;
		}
		err = memstartgif(&bout, i, -1);
		if(err == nil){
			if(comment)
				err = memwritegif(&bout, i, comment, dt, trans);
			else{
				snprint(buf, sizeof buf, "Converted by Plan 9 from <stdin>");
				err = memwritegif(&bout, i, buf, dt, trans);
			}
		}
	}else{
		if(loop == UNSET){
			if(argc == 1)
				loop = -1;	/* no loop for single image */
			else
				loop = 0;	/* the default case: 0 means infinite loop */
		}
		for(j=0; j<argc; j++){
			if(argv[j][0] == '-' && argv[j][1]=='d'){
				/* time change */
				if(argv[j][2] == '\0'){
					s = argv[++j];
					if(j == argc)
						usage();
				}else
					s = &argv[j][2];
				if(!isdigit(s[0]))
					usage();
				dt = atoi(s);
				if(j == argc-1)	/* last argument must be file */
					usage();
				continue;
			}
			fd = open(argv[j], OREAD);
			if(fd < 0)
				sysfatal("can't open %s: %r", argv[j]);
			i = readmemimage(fd);
			if(i == nil)
				sysfatal("can't readimage %s: %r", argv[j]);
			close(fd);
			ni = memonechan(i);
			if(ni == nil)
				sysfatal("converting image to RGBV: %r");
			if(i != ni){
				freememimage(i);
				i = ni;
			}
			if(j == 0){
				err = memstartgif(&bout, i, loop);
				if(err != nil)
					break;
			}
			if(comment)
				err = memwritegif(&bout, i, comment, dt, trans);
			else{
				snprint(buf, sizeof buf, "Converted by Plan 9 from %s", argv[j]);
				err = memwritegif(&bout, i, buf, dt, trans);
			}
			if(err != nil)
				break;
			freememimage(i);
			comment = nil;
		}
	}
	memendgif(&bout);

	if(err != nil)
		fprint(2, "togif: %s\n", err);
	exits(err);
}
Пример #19
0
void
main(int argc, char **argv)
{
	int fd, xsize, ysize;
	Memimage *im, *nim;
	ulong ochan, tchan;

	xsize = ysize = 0;
	ARGBEGIN{
	case 'a':
		xsize = ysize = getsize(EARGF(usage()));
		break;
	case 'x':
		xsize = getsize(EARGF(usage()));
		break;
	case 'y':
		ysize = getsize(EARGF(usage()));
		break;
	default:
		usage();
	}ARGEND
	fd = 0;
	if(*argv){
		fd = open(*argv, OREAD);
		if(fd < 0)
			sysfatal("open: %r");
	}
	memimageinit();
	if((im = readmemimage(fd)) == nil)
		sysfatal("readmemimage: %r");
	if(xsize & PERCENT)
		xsize = ((xsize & ~PERCENT) * Dx(im->r)) / 100;
	if(ysize & PERCENT)
		ysize = ((ysize & ~PERCENT) * Dy(im->r)) / 100;
	if(xsize || ysize){
		if(ysize == 0)
			ysize = (xsize * Dy(im->r)) / Dx(im->r);
		if(xsize == 0)
			xsize = (ysize * Dx(im->r)) / Dy(im->r);
		ochan = im->chan;
		switch(ochan){
		default:
			for(tchan = ochan; tchan; tchan >>= 8)
				if(TYPE(tchan) == CAlpha){
					tchan = RGBA32;
					break;
				}
			if(tchan == 0)
				tchan = RGB24;
			break;
		case GREY8:
		case RGB24:
		case RGBA32:
		case ARGB32:
		case XRGB32:
			tchan = ochan;
			break;
		case GREY1:
		case GREY2:
		case GREY4:
			tchan = GREY8;
			break;
		}
		if(tchan != ochan){
			if((nim = allocmemimage(im->r, tchan)) == nil)
				sysfatal("allocimage: %r");
			memimagedraw(nim, nim->r, im, im->r.min, nil, ZP, S);
			freememimage(im);
			im = nim;
		}
		if((nim = allocmemimage(
			Rect(im->r.min.x, im->r.min.y, im->r.min.x+xsize, im->r.min.y+ysize), 
			tchan)) == nil)
			sysfatal("allocmemimage: %r");
		resample(nim, nim->r, im, im->r);
		freememimage(im);
		im = nim;
		if(tchan != ochan){
			if((im = allocmemimage(nim->r, ochan)) == nil)
				sysfatal("allocimage: %r");
			memimagedraw(im, im->r, nim, nim->r.min, nil, ZP, S);
			freememimage(nim);
		}
	}
	if(writememimage(1, im) < 0)
		sysfatal("writememimage: %r");
	exits(0);
}
Пример #20
0
Файл: arc.c Проект: 0intro/vx32
/*
 * make a "wedge" mask covering the desired angle and contained in
 * a surrounding square; draw a full ellipse; intersect that with the
 * wedge to make a mask through which to copy src to dst.
 */
void
memarc(Memimage *dst, Point c, int a, int b, int t, Memimage *src, Point sp, int alpha, int phi, int op)
{
	int i, w, beta, tmp, c1, c2, m, m1;
	Rectangle rect;
	Point p,	bnd[8];
	Memimage *wedge, *figure, *mask;

	if(a < 0)
		a = -a;
	if(b < 0)
		b = -b;
	w = t;
	if(w < 0)
		w = 0;
	alpha = -alpha;		/* compensate for upside-down coords */
	phi = -phi;
	beta = alpha + phi;
	if(phi < 0){
		tmp = alpha;
		alpha = beta;
		beta = tmp;
		phi = -phi;
	}
	if(phi >= 360){
		memellipse(dst, c, a, b, t, src, sp, op);
		return;
	}
	while(alpha < 0)
		alpha += 360;
	while(beta < 0)
		beta += 360;
	c1 = alpha/90 & 3;	/* number of nearest corner */
	c2 = beta/90 & 3;
		/*
		 * icossin returns point at radius ICOSSCALE.
		 * multiplying by m1 moves it outside the ellipse
		*/
	rect = Rect(-a-w, -b-w, a+w+1, b+w+1);
	m = rect.max.x;	/* inradius of bounding square */
	if(m < rect.max.y)
		m = rect.max.y;
	m1 = (m+ICOSSCALE-1) >> 10;
	m = m1 << 10;		/* assure m1*cossin is inside */
	i = 0;
	bnd[i++] = Pt(0,0);
	icossin(alpha, &p.x, &p.y);
	bnd[i++] = mulpt(p, m1);
	for(;;) {
		bnd[i++] = mulpt(corners[c1], m);
		if(c1==c2 && phi<180)
			break;
		c1 = (c1+1) & 3;
		phi -= 90;
	}
	icossin(beta, &p.x, &p.y);
	bnd[i++] = mulpt(p, m1);

	figure = nil;
	mask = nil;
	wedge = allocmemimage(rect, GREY1);
	if(wedge == nil)
		goto Return;
	memfillcolor(wedge, DTransparent);
	memfillpoly(wedge, bnd, i, ~0, memopaque, p00, S);
	figure = allocmemimage(rect, GREY1);
	if(figure == nil)
		goto Return;
	memfillcolor(figure, DTransparent);
	memellipse(figure, p00, a, b, t, memopaque, p00, S);
	mask = allocmemimage(rect, GREY1);
	if(mask == nil)
		goto Return;
	memfillcolor(mask, DTransparent);
	memimagedraw(mask, rect, figure, rect.min, wedge, rect.min, S);
	c = subpt(c, dst->r.min);
	memdraw(dst, dst->r, src, subpt(sp, c), mask, subpt(p00, c), op);

    Return:
	freememimage(wedge);
	freememimage(figure);
	freememimage(mask);
}
Пример #21
0
int
screensize(int x, int y, int z, uint32_t chan)
{
	Proc *up = externup();
	VGAscr *scr;
	void *oldsoft;

	lock(&vgascreenlock);
	if(waserror()){
		unlock(&vgascreenlock);
		nexterror();
	}

	memimageinit();
	scr = &vgascreen[0];
	oldsoft = softscreen;

	if(scr->paddr == 0){
		int width = (x*z)/BI2WD;
		void *p;

		p = malloc(width*BY2WD*y);
		if(p == nil)
			error("no memory for vga soft screen");
		gscreendata.bdata = softscreen = p;
		if(scr->dev && scr->dev->page){
			scr->vaddr = KADDR(VGAMEM());
			scr->apsize = 1<<16;
		}
		scr->useflush = 1;
	}
	else{
		gscreendata.bdata = scr->vaddr;
		scr->useflush = scr->dev && scr->dev->flush;
	}

	scr->gscreen = nil;
	if(gscreen)
		freememimage(gscreen);
	gscreen = allocmemimaged(Rect(0,0,x,y), chan, &gscreendata);
	if(gscreen == nil)
		error("no memory for vga memimage");
	vgaimageinit(chan);

	scr->palettedepth = 6;	/* default */
	scr->gscreendata = &gscreendata;
	scr->memdefont = getmemdefont();
	scr->gscreen = gscreen;

	physgscreenr = gscreen->r;
	unlock(&vgascreenlock);
	poperror();
	if(oldsoft)
		free(oldsoft);

	memimagedraw(gscreen, gscreen->r, memblack, ZP, nil, ZP, S);
	flushmemscreen(gscreen->r);

	if(didswcursorinit)
		swcursorinit();
	drawcmap();
	return 0;
}
Пример #22
0
Memsubfont*
mksubfont(XFont *f, char *name, int lo, int hi, int size, int antialias)
{
	CFStringRef s;
	CGColorSpaceRef color;
	CGContextRef ctxt;
	CTFontRef font;
	CTFontDescriptorRef desc;
	CGRect bbox;
	Memimage *m, *mc, *m1;
	int x, y, y0;
	int i, height, ascent;
	Fontchar *fc, *fc0;
	Memsubfont *sf;
	CGFloat whitef[] = { 1.0, 1.0 };
	CGColorRef white;

	s = c2mac(name);
	desc = CTFontDescriptorCreateWithNameAndSize(s, size);
	CFRelease(s);
	if(desc == nil)
		return nil;
	font = CTFontCreateWithFontDescriptor(desc, 0, nil);
	CFRelease(desc);
	if(font == nil)
		return nil;
	
	
	bbox = CTFontGetBoundingBox(font);
	x = (int)(bbox.size.width*2 + 0.99999999);

	fontheight(f, size, &height, &ascent);
	y = height;
	y0 = height - ascent;

	m = allocmemimage(Rect(0, 0, x*(hi+1-lo)+1, y+1), GREY8);
	if(m == nil)
		return nil;
	mc = allocmemimage(Rect(0, 0, x+1, y+1), GREY8);
	if(mc == nil){
		freememimage(m);
		return nil;
	}
	memfillcolor(m, DBlack);
	memfillcolor(mc, DBlack);
	fc = malloc((hi+2 - lo) * sizeof fc[0]);
	sf = malloc(sizeof *sf);
	if(fc == nil || sf == nil) {
		freememimage(m);
		freememimage(mc);
		free(fc);
		free(sf);
		return nil;
	}
	fc0 = fc;

	color = CGColorSpaceCreateWithName(kCGColorSpaceGenericGray);
	ctxt = CGBitmapContextCreate(byteaddr(mc, mc->r.min), Dx(mc->r), Dy(mc->r), 8,
		mc->width*sizeof(u32int), color, kCGImageAlphaNone);
	white = CGColorCreate(color, whitef);
	CGColorSpaceRelease(color);
	if(ctxt == nil) {
		freememimage(m);
		freememimage(mc);
		free(fc);
		free(sf);
		return nil;
	}

	CGContextSetAllowsAntialiasing(ctxt, antialias);
	CGContextSetTextPosition(ctxt, 0, 0);	// XXX
#if OSX_VERSION >= 101400
	CGContextSetAllowsFontSmoothing(ctxt, false);
#endif

	x = 0;
	for(i=lo; i<=hi; i++, fc++) {
		char buf[20];
		CFStringRef str;
		CFDictionaryRef attrs;
		CFAttributedStringRef attrString;
		CTLineRef line;
		CGRect r;
		CGPoint p1;
		CFStringRef keys[] = { kCTFontAttributeName, kCTForegroundColorAttributeName };
		CFTypeRef values[] = { font, white };

		sprint(buf, "%C", (Rune)mapUnicode(name, i));
 		str = c2mac(buf);
 		
 		// See https://developer.apple.com/library/ios/documentation/StringsTextFonts/Conceptual/CoreText_Programming/LayoutOperations/LayoutOperations.html#//apple_ref/doc/uid/TP40005533-CH12-SW2
 		attrs = CFDictionaryCreate(kCFAllocatorDefault, (const void**)&keys,
			(const void**)&values, sizeof(keys) / sizeof(keys[0]),
			&kCFTypeDictionaryKeyCallBacks,
			&kCFTypeDictionaryValueCallBacks);
		attrString = CFAttributedStringCreate(kCFAllocatorDefault, str, attrs);
		CFRelease(str);
		CFRelease(attrs);

		line = CTLineCreateWithAttributedString(attrString);
		CGContextSetTextPosition(ctxt, 0, y0);
		r = CTLineGetImageBounds(line, ctxt);
		memfillcolor(mc, DBlack);
		CTLineDraw(line, ctxt);		
		CFRelease(line);

		fc->x = x;
		fc->top = 0;
		fc->bottom = Dy(m->r);

//		fprint(2, "printed %#x: %g %g\n", mapUnicode(i), p1.x, p1.y);
		p1 = CGContextGetTextPosition(ctxt);
		if(p1.x <= 0 || mapUnicode(name, i) == 0xfffd) {
			fc->width = 0;
			fc->left = 0;
			if(i == 0) {
				drawpjw(m, fc, x, (int)(bbox.size.width + 0.99999999), y, y - y0);
				x += fc->width;
			}	
			continue;
		}

		memimagedraw(m, Rect(x, 0, x + p1.x, y), mc, ZP, memopaque, ZP, S);
		fc->width = p1.x;
		fc->left = 0;
		x += p1.x;
	}
	fc->x = x;

	// round up to 32-bit boundary
	// so that in-memory data is same
	// layout as in-file data.
	if(x == 0)
		x = 1;
	if(y == 0)
		y = 1;
	if(antialias)
		x += -x & 3;
	else
		x += -x & 31;
	m1 = allocmemimage(Rect(0, 0, x, y), antialias ? GREY8 : GREY1);
	memimagedraw(m1, m1->r, m, m->r.min, memopaque, ZP, S);
	freememimage(m);
	freememimage(mc);

	sf->name = nil;
	sf->n = hi+1 - lo;
	sf->height = Dy(m1->r);
	sf->ascent = Dy(m1->r) - y0;
	sf->info = fc0;
	sf->bits = m1;
	
	return sf;
}