forsyth20121205-174063a80cc13 years agoHistory
113 lines · 2.2 KB · C
RawDownload
#include <lib9.h>#include <draw.h>#include <interp.h>#include <isa.h>#include "../libinterp/runt.h"#include <drawif.h>#include <prefab.h>#include <kernel.h> List*prefabwrap(void *elem){	List *l;	Heap *h, *e; 	e = D2H(elem);	h = nheap(sizeof(List) + sizeof(WORD*));	h->t = &Tlist;	Tlist.ref++;	l = H2D(List*, h);	l->tail = H;	l->t = &Tptr;	Tptr.ref++;	e->ref++;	*(WORD**)l->data = elem;	return l;} staticPElement*elistelement1(Prefab_Environ *e, Prefab_Element *elem, Prefab_Element *new, enum Elementtype kind){	int first;	PElement *pelem;	List *atom; 	if(badenviron(e, 0))		return H; 	gchalt++;	first = 0;	if(new == H)		atom = H;	else		atom = prefabwrap(new);	if(elem == H){		pelem = mkelement(e, kind);		elem = &pelem->e;		pelem->first = H;		pelem->nkids = 0;	}else		pelem = (PElement*)elem;	if(atom == H)		goto Return; 	if(elem->kids != pelem->first)		error("list Element has been modified externally");	if(elem->kids == H){		elem->kids = atom;		pelem->first = atom;		pelem->last = atom;		pelem->vfirst = atom;		pelem->vlast = atom;		first = 1;	}	if(new->kind!=ESeparator && Dx(elem->r)==0){		elem->r = new->r;		pelem->drawpt.x = elem->r.min.x;		pelem->drawpt.y = elem->r.min.y;	}	pelem->nkids++;	if(first)		goto Return;	pelem->last->tail = atom;	pelem->last = atom;	pelem->vlast = atom;	if(new->kind != ESeparator){		if(kind == EVertical){			elem->r.max.y += Dy(new->r);			if(elem->r.min.x > new->r.min.x)				elem->r.min.x = new->r.min.x;			if(elem->r.max.x < new->r.max.x)				elem->r.max.x = new->r.max.x;		}else{			elem->r.max.x += Dx(new->r);			if(elem->r.min.y > new->r.min.y)				elem->r.min.y = new->r.min.y;			if(elem->r.max.y < new->r.max.y)				elem->r.max.y = new->r.max.y;		}	}	pelem->pkind = kind;     Return:	gchalt--;	return pelem;} PElement*elistelement(Prefab_Environ *e, Prefab_Element *new, enum Elementtype kind){	return elistelement1(e, H, new, kind);} PElement*appendelist(Prefab_Element *elem, Prefab_Element *new){	if(elem->kind!=EVertical && elem->kind!=EHorizontal){		kwerrstr("appendelist to non-list");		return H;	}	return elistelement1(elem->environ, elem, new, elem->kind);}