created mirror

This commit is contained in:
whatever
2026-09-14 20:19:29 -04:00
commit 6764738d92
600 changed files with 87187 additions and 0 deletions

View File

@@ -0,0 +1,546 @@
/*
MessageFlobFactory.zob
*
* Copyright (c) 2000, Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Rauli Ruohonen
*/
package org.gzigzag.module;
import org.gzigzag.module.multimedia.*;
import org.gzigzag.*;
import java.awt.*;
import java.util.*;
public class MessageFlobFactory implements FlobFactory, ZOb {
public static boolean dbg = false;
private static void p(String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
private String d_image = "d.images";
private String d_text = "d.text";
private String d_author = "d.author";
private String d_handle = "d.kahva";
private MediaFlobFactory mediafact=new MediaFlobFactory();
private FTextLayouter ftext=new FTextLayouter();
SceneFlob mysflob = null;
VirtualCommunity vc= null;
STRUCTPARAMS {
/* In pixels. */
int imgtxt_separator
= 0;
/* Originally 1/Ph = img_h/txt_h =~ 0.618. (Ph = Golden Ratio) */
float imgtxt_min_ratio
= (float)(2.0/(Math.sqrt(5.0)+1.0));
ScalableFont font
= new ScalableFont("SansSerif", Font.PLAIN, 12);
/* color of the author blob */
Color authorColor
= Color.yellow.brighter();
/* color of the message blob */
Color messageColor
= new Color(0xffff8c);
Color auth_bg
= new Color(0xffff28);
int border
= 3;
int clipborder
= 2;
}
public MessageFlobFactory(VirtualCommunity vc){
this.vc = vc;
}
public MessageFlobFactory(){
}
private Color back = Color.white;
private FText makeFText(ZZCell c, ZZCell hc,float fract) {
Vector a=new Vector();
int scale=(int)(fract*1000);
Font f=font.getFont(scale);
FontMetrics fm=font.getFontMetrics(scale);
Color fg=Color.black;//,bg=Color.white;
LoopDetector l=new LoopDetector();
c = c.s(d_text,1);
Color fgt = fg;
while(c!=null) {
fgt = fg;
l.detect(c);
/*if( c.s(d_handle,1) != null || c.s(d_handle,-1) != null){
fgt = Color.red;
}*/
a.addElement(new FText.CellPart(c,c,0,-1,f,fm,back,fgt));
//a.addElement(new FText.StringPart(c.getText(),f,fm,back,fgt));
c=c.s(d_text);
}
return new FText(a);
}
public SceneFlob getSFlob(){
return mysflob;
}
private int cacheW = -1;
private Dimension cacheTxt;
private ZZCell cacheC;
private float cacheFract;
private void getSizes(ZZCell c,float fract,int w,int h,Dimension img,
Dimension txt) {
final int MAGIC=2147483647;
ZZCell imgc=c.h(d_image,true);
ZZCell textc=c.s(d_text);
img.width=0; img.height=0; txt.width=0; txt.height=0;
/* Calculate the maximum sizes for both image and text */
if(imgc!=null) img.setSize(mediafact.getSize(imgc,fract));
float aspect=img.width*1.0f/img.height;
if(textc!=null) {
if (cacheW == w && cacheFract == fract && c.equals(cacheC))
txt.setSize(cacheTxt);
else {
cacheTxt = ftext.place(null,makeFText(c,c,fract),
new Rectangle(0,0,w,MAGIC),
1,1,0,0xdeadbeef,false).getSize();
cacheW = w; cacheC = c; cacheFract = fract;
txt.setSize(cacheTxt);
}
}
// Subj. + Auth.
txt.height += (font.getFontMetrics((int)(1000 * fract)).
getHeight())*2;
if (imgc == null) {
txt.height = h;
return;
}
if (textc == null) {
img.height=h-txt.height;
img.width=(int)(img.height*aspect);
if(img.width>w) {
img.width=w;
img.height=(int)(img.width/aspect);
}
txt.height = h-img.height;
return;
}
h-=imgtxt_separator;
float imgtxt_ratio=(h-txt.height)/txt.height; // Text size constant
p("it_rat="+imgtxt_ratio);
if(imgtxt_ratio<imgtxt_min_ratio) imgtxt_ratio=imgtxt_min_ratio;
p("it_rat_fixedf="+imgtxt_ratio);
txt.height=(int)(h/(imgtxt_ratio+1));
img.height=(int)(h*imgtxt_ratio/(imgtxt_ratio+1));
img.width=(int)(img.height*aspect);
if(img.width>w) {
img.width=w;
int tmp=img.height;
img.height=(int)(img.width/aspect);
txt.height+=tmp-img.height;
p("Adjusted.");
}
p("txt: "+txt+" img: "+img+ "world: "+new Dimension(w,h));
}
public Dimension getSize(ZZCell c, float f) { return null; }
public int getHeight(ZZCell c, float fract, int w) {
w-= border*2;
final int MAGIC=2147483647;
ZZCell imgc=c.h(d_image,true);
ZZCell textc=c.s(d_text);
Dimension img = new Dimension(0, 0), txt = new Dimension(0, 0);
/* Calculate the maximum sizes for both image and text */
if(imgc!=null) img.setSize(mediafact.getSize(imgc,fract));
float aspect=img.width*1.0f/img.height;
img.height = (int) (w / aspect);
if(textc!=null) {
if (cacheW == w && cacheFract == fract && c.equals(cacheC))
txt.setSize(cacheTxt);
else {
cacheTxt = ftext.place(null,makeFText(c,c,fract),
new Rectangle(0,0,w,MAGIC),
1,1,0,0xdeadbeef,false).getSize();
cacheW = w; cacheC = c; cacheFract = fract;
txt.setSize(cacheTxt);
}
}
// Subj. + Auth.
txt.height += (font.getFontMetrics((int)(1000 * fract)).
getHeight())*2 + border*2 + 1;
p("getHeight(): w = "+w+", imgh = "+img.height+", txth = "+
txt.height+", imsep = "+imgtxt_separator);
if (imgc == null) return txt.height;
if (textc == null) return img.height+txt.height;
return imgtxt_separator + img.height + txt.height;
}
public Flob makeFlob(FlobSet _into,
ZZCell c, final ZZCell handleCell,
float fract, int x, int y, int d, int w, int h,
float rot) {
return makeFlob(_into, c, handleCell, fract, x, y, d, w, h, rot,
false);
}
public Flob makeFlob(FlobSet _into,
ZZCell c, final ZZCell handleCell,
float fract, int x, int y, int d, int w, int h) {
return makeFlob(_into, c, handleCell, fract, x, y, d, w, h, 0.0f);
}
/* animated text also means that beams are drawn :-) */
public Flob makeFlob(FlobSet _into,
ZZCell c, final ZZCell handleCell,
float fract, int x, int y, int d, int w, int h,
double rot, boolean animateText) {
x+=border; y+=border; w-=border*2; h-=border*2;
int cx = x+w/2; int cy = y+h/2;
Dimension dfs = _into.getSize();
final int borderEdge = 5;
boolean doText = true;
if(cx < borderEdge || cx >= dfs.width - borderEdge ||
cy < borderEdge || cy >= dfs.height - borderEdge)
doText = false;
Dimension img=new Dimension(),txt=new Dimension();
getSizes(c,fract,w,h,img,txt);
int imsep = 0;
if(img.height>0&&txt.height>0) imsep = imgtxt_separator;
x-=border; y-=border; w+=border*2; h+=border*2;
FlobSet into = _into;
SceneFlob sflob = null;
// XXX this shouldn't be here
ZZDrawingJ2D _drw = null;
if (ZZDrawing.instance instanceof ZZDrawingJ2D) {
// XXX SplitCellFlob1.doClip = false;
into = new FlobSet(_into.getSize(),
_into.getForeground(),
_into.getBackground(),
_into.getComponent());
_drw = (ZZDrawingJ2D) ZZDrawing.instance;
sflob = _drw.new RotatedSceneFlob(x, y, d, w, h, c,
into, rot);
mysflob = sflob;
p("into = " +into);
}
final ZZDrawingJ2D drw = _drw;
Flob[] important = new Flob[1];
Flob bgfl=new CellBgFlob(x, y, d, w, h, c) {
public void render(Graphics g, int mx, int my, int md,
int mw, int mh) {
Color oldfg = g.getColor();
g.setColor(bg);
g.fillRect(mx+1, my+1, mw-2, mh-2);
g.setColor(oldfg);
/*boolean bup = ZZDrawing.instance.qualityEnabled();
ZZDrawing.instance.enableQuality(true);
ZZDrawing.instance.setQuality(g);*/
if (!ZZDrawing.instance.qualityEnabled())
g.setColor(new Color(0x333322));
if(mh >= 14)
((Graphics2D)g).setStroke(new BasicStroke(2.0f));
g.drawRect(mx, my, mw-1, mh-1);
((Graphics2D)g).setStroke(new BasicStroke());
/*if(mh >= 14) g.drawRect(mx+1, my+1, mw-3, mh-3);
g.drawRect(mx, my, mw-1, mh-1);*/
/*ZZDrawing.instance.enableQuality(bup);
ZZDrawing.instance.setQuality(g);*/
g.setColor(oldfg);
}
public Object hit(int x0,int y0) {
if (x0 >= this.x && y0 >= this.y && x0 < this.x+this.w &&
y0 < this.y+this.h) return handleCell;
return null;
}
};
important[0] = bgfl;
sflob.setImportant(important);
sflob.setFocus(animateText);
p("MSGF: "+animateText);
x+=border; y+=border; w-=border*2; h-=border*2;
boolean mess = false;
ZZCell tmp=c.s(d_text);
if(tmp!=null) {
int ystart=y+img.height+imsep;
ZZCell locc = c.h(d_author,-1);
Flob header = new Flob(x, ystart, d, w, 1, c) {};
if( locc != c){
mess = true;
back = messageColor;
if(doText) {
Flob sf = makeSubject(into, c, handleCell, fract,
x, ystart, d, w, bgfl, txt.height);
ystart += sf.h;
txt.height -= sf.h;
sf = makeAuthor(into, locc, handleCell,
fract, x, ystart, d, w,fract,fract, bgfl,
txt.height);
ystart += sf.h;
txt.height -= sf.h;
}
//p("ystart = " + ystart);
} else if ( locc == c && c.getRankLength(d_author) > 1){
back = authorColor;
}
Flob tailer = null;
// new Flob(x, ystart, d, txt.width, txt.height,
// c.s(d_text)) {};
//tailer.setParent(bgfl);
//if (animateText) into.add(tailer);
Rectangle r = new Rectangle(x,ystart,txt.width,txt.height);
if(doText) {
ftext.place(into,makeFText(c,handleCell,fract),r,d,1,ystart,
0xdeadbeef, false, tailer);
if(dbg) {
// p(into.findFlob
}
}
}
tmp=c.h(d_image);
if(tmp!=c)
mediafact.makeFlob(into,tmp,handleCell,fract,
x+(w-img.width)/2,y,d,img.width,img.height).
setParent(bgfl);
((CellBgFlob)bgfl).setBg(back);
into.add(bgfl);
back = Color.white;
if( animateText ) {
pa("LINK: " + c);
tmp = c.s(d_text, 1);
while((tmp = tmp.s(d_text, 1)) != null) {
ZZCell hea = tmp.h(d_handle, -1);
if(hea != tmp) {
Flob f= into.findFlob(null, tmp);
pa("FINDFLOB: "+f);
if(f == null)continue;
Point p = new Point(f.x + f.w/2, f.y + f.h/2);
Point p2 = new Point();
sflob.transform(p, p2, true);
vc.product(hea, p2);
}
}
}
if (sflob != null) {
_into.add(sflob);
//SplitCellFlob1.doClip = true;
return sflob;
}
return bgfl;
}
// The following are shamelessly pseudo-cut&pasted from CellFlobFactory1
public Flob placeFlob(FlobSet into,
ZZCell c, ZZCell handleCell,
float fract,
int x, int y, int depth,
float xfract, float yfract) {
Dimension d = getSize(c, fract);
return makeFlob(into, c, handleCell, fract,
(int)(x-xfract*d.width),
(int)(y-yfract*d.height),
depth, d.width, d.height);
}
public Flob centerFlob(FlobSet into,
ZZCell c, ZZCell handleCell,
float fract, Point p, int xalign, int yalign,
int depth, Dimension d) {
if(d == null) d = getSize(c, fract);
int x, y;
x = p.x - d.width/2; y = p.y - d.height/2;
if(xalign < 0) x = p.x;
if(xalign > 0) x = p.x - d.width;
if(yalign < 0) y = p.y;
if(yalign > 0) y = p.y - d.height;
return makeFlob(into, c, handleCell, fract, x, y,
depth, d.width, d.height);
}
public Flob centerFlob(FlobSet into,
ZZCell c, ZZCell handleCell,
float fract, Point p, int xalign, int yalign,
int depth) {
return centerFlob(into, c, handleCell, fract, p, xalign, yalign,
depth, null);
}
public Flob makeSubject(FlobSet into,
ZZCell c, ZZCell handleCell,
float fract,
int x, int y, int depth,
int w, Flob parent, int mh) {
if (mh > 100) mh = 100;
Flob sc = new SubjCell(x,y,depth,w,mh,c, handleCell, fract);
sc.setParent(parent);
into.add(sc);
return sc;
}
public Flob makeAuthor(FlobSet into,
ZZCell c, ZZCell handleCell,
float fract,
int x, int y, int depth, int w,
float xfract, float yfract, Flob parent, int mh) {
if (mh > 100) mh = 100;
Flob ac = new AuthCell(x,y,depth,w,mh,c, handleCell, fract);
ac.setParent(parent);
into.add(ac);
return ac;
}
/**
* Flob for message subjects
*/
class SubjCell extends Flob {
int ascent;
float fr;
ZZCell handle;
public SubjCell(int x, int y, int d, int w, int h, ZZCell c, ZZCell hc,
float fract){
super(x,y,d,w,h,c);
Font f = font.getFont((int)(1000 * fract));
FontMetrics fm = font.getFontMetrics((int)(1000 * fract));
ascent = fm.getAscent();
this.h = fm.getHeight();
if (this.h > h) this.h = h;
//this.w = fm.stringWidth("Subject: " +c.getText());
fr = fract;
handle = hc;
//p("FR = " + fr);
}
public void renderInterp(Graphics g, float fract) { return; }
public void render(Graphics g, int mx, int my, int md,
int mw, int mh) {
/*ZZDrawingJ2D drw = null;
if (ZZDrawing.instance instanceof ZZDrawingJ2D)
drw = (ZZDrawingJ2D)ZZDrawing.instance;
if (drw != null) {
drw.setFIXME(false);
drw.setQuality(g);
}*/
FontMetrics fm = font.getFontMetrics((int)(1000 * fr));
Color old = g.getColor();
g.setFont(font.getFont((int)(fr*1000)));
g.setColor(auth_bg);
Rectangle asd=g.getClipBounds();
g.setClip(mx-clipborder,my-clipborder,mw+clipborder*2,mh+clipborder*2);
g.fillRect(mx,my,mw,mh);
g.setColor(old);
/*if (drw != null) {
drw.setFIXME(true);
drw.setQuality(g);
}*/
if( fm.stringWidth("Subject: " + c.getText()) > mw )
g.drawString( c.getText(), mx,my+ascent);
else g.drawString("Subject: " + c.getText(), mx,my+ascent);
//g.drawLine(mx, my+h, mx+w, my+h);
g.setClip(asd);
}
public Object hit(int x0, int y0) {
if( x0 >= x && y0 >= y && x0 < x+w && y0 < y+h )
return handle;
return null;
}
}
/**
* Flob for message auth
*/
class AuthCell extends Flob {
int ascent;
int height;
ZZCell handle;
float fr = 1.0f;
public AuthCell(int x, int y, int d, int w, int h, ZZCell c, ZZCell hc,
float fract){
super(x,y,d,w,h,c);
Font f = font.getFont((int)(1000 * fract));
FontMetrics fm = font.getFontMetrics((int)(1000 * fract));
ascent = fm.getAscent();
this.h = fm.getHeight();
if (this.h > h) this.h = h;
//this.w = fm.stringWidth("Author: " + c.getText());
fr = fract;
handle = hc;
}
public void renderInterp(Graphics g, float fract) { return; }
public void render(Graphics g, int mx, int my, int md,
int mw, int mh) {
/*ZZDrawingJ2D drw = null;
if (ZZDrawing.instance instanceof ZZDrawingJ2D)
drw = (ZZDrawingJ2D)ZZDrawing.instance;
if (drw != null) {
drw.setFIXME(false);
drw.setQuality(g);
}*/
Color old = g.getColor();
FontMetrics fm = font.getFontMetrics((int)(1000 * fr));
g.setFont(font.getFont((int)(1000 * fr)));
Rectangle asd=g.getClipBounds();
g.setClip(mx-clipborder,my-clipborder,mw+clipborder*2,mh+clipborder*2);
g.setColor(auth_bg);
g.fillRect(mx,my,mw,mh);
g.setColor(old);
/*if (drw != null) {
drw.setFIXME(true);
drw.setQuality(g);
}*/
if( fm.stringWidth("Author: " + c.getText()) < mw )
g.drawString("Author: " + c.getText(), mx,my+ascent);
else g.drawString( c.getText(), mx,my+ascent);
g.drawLine(mx, my+mh-1, mx+mw, my+mh-1);
g.setClip(asd);
}
public Object hit(int x0, int y0) {
if( x0 >= x && y0 >= y && x0 < x+w && y0 < y+h )
return handle;
return null;
}
}
}
// vim: set syntax=java :

View File

@@ -0,0 +1,377 @@
/*
VCView1.java
*
* Copyright (c) 2000, Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Vesa Parkkinen and Tuomas Lukka
*/
package org.gzigzag.module;
import org.gzigzag.*;
import java.util.*;
import java.awt.*;
/** First (bad) virtualcommunity view.
*/
public class VCView1 extends VirtualCommunity {
public static final String rcsid = "$Id: VCView1.java,v 1.4 2001/02/27 23:49:30 veparkki Exp $";
public static boolean dbg = false;
private static void p(String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
public void raster( FlobSet into, FlobFactory fact,
ZZCell view, String[] dims, ZZCell accursed){
ZZCell hist = null, hilite = null;
if (!nohistory) {
hist = ZZDefaultSpace.findInheritableParam(view, "history");
if (hist == null) {
hist = view.h("d.2",1).N("d.2");
hist.setText("history");
}
hilite = hist.h("d.1", 1, true);
}
accursed=accursed.h(text);
if (!nohistory) {
if (accursed.h("d.1").equals(hist)) {
hilite = accursed;
accursed = ZZCursorReal.get(accursed);
}
if (hilite == null) {
hilite = hist.N("d.1");
ZZCursorReal.setcursor(hilite, accursed);
}
histobs.init(view, hilite);
hilite = histobs.histpos;
}
Dimension rd = into.getSize();
int head = rd.height/15;
if (nohistory) head = 0;
Dimension d = new Dimension(rd.width,rd.height-head);
int w = (int)(d.width * right);
int h = (int)(d.height * middleHeight);
int cx = w/2;
int cy = (int)( (d.height - h) / 2);
int vUnit = (int)(cy / 13);
int lw = (int)(d.width * left);
// gapheight=1/13, line=3/13;4*gap+3*lines=1
int bc = 0;
// pointer
ZZCell p = accursed;
// another pointer
ZZCell ptr = p;
// used to hold kahva cells
Hashtable handles = new Hashtable();
Hashtable flobs = new Hashtable();
int fh = d.height;
int fw = (int) (right * d.width);
Flob centerFlob = null;
float fr = ((float)d.width) / 100000.0f;
int magic = 20;
// Draw the history
int div = 1;
if (!nohistory) div = hist.getRankLength("d.1")-1;
if (div > magic) div = magic;
int hw = (d.width/div)-2, sep=2;
if (hw > head*3) { /*sep+=hw-head*3;*/ hw = head*3; }
int hx = d.width-1-hw;
ZZCell it = null;
if (!nohistory) hist.s("d.1");
int cnt=0;
if (!nohistory) {
while (!it.equals(hilite)) { cnt++; it = it.s("d.1"); }
if (cnt*2+1 > magic) cnt = (magic-1)/2;
cnt++;
while (cnt++ < magic) {
if (it.s("d.1") != null) it = it.s("d.1");
else break;
}
}
cnt = 0;
centerFlob = new Flob(0, 0, 1, d.width, head, hist) {};
into.add(centerFlob);
if (!nohistory)
while (!it.equals(hist) && cnt++ < magic) {
ZZCell hit = ZZCursorReal.get(it);
int hy = 0;
if (hilite != null && it.equals(hilite)) hy = 5;
history.makeFlob(into, hit, it, cfr(fr*hw), hx, hy, 1, hw, head).
setParent(centerFlob);
it = it.s("d.1",-1);
hx -= sep+hw;
}
//-------------------------------------------
// we have different possibilities:
// author cell
// - headcell in the author dim
//
// product cell
// - no author dim
// - head cell in the kahva dim
//
// message cell
// - have author, not the head cell
//-------------------------------------------
//if ( fr > 1 ) fr = 1;
//if ( fr < 0.7 ) fr = 0.7f;
p("_____________fr = " +fr);
// make the big blob in the middle
centerFlob = center.makeFlob( into, accursed, accursed, cfr(fr*w),
cx, cy+head, 1, w, h , 0.0f, true);
//-------------------------------------------
// handle the siblings, parent and children
//-------------------------------------------
p = accursed;
int cSibl = 0;
int sY = cy;
int sX = cx;
// siblings above the center blob
// calculate the room...
int rc = 0;//p.getRankLength(replies_list) -1;
while( ( p = p.s(replies_list, -1) ) != null ){
rc++;
}
rc--;
p("got " + rc + " siblings");
p = accursed;
int sroom = (d.height - h)/2;
if( rc > 0 )
sroom = sroom / rc;
//fr = (float)0.7;
while( ( p = p.s(replies_list, -1) ) != null &&
!p.equals( p.h(replies_list, -1)) && ( cSibl < rc ) ) {
sY = sY - sroom+10;
//sibl.makeFlob( into, p, p, (float)1.0,
// sX, sY, 1, w, 3*vUnit);
blobs.makeFlob( into, p, p, cfr(fr*w),
sX, sY+head, 1, w, sroom - 20, 0.1f);
cSibl = cSibl + 1;
//fr -= 0.2;
}
// parent
ZZCell parent = accursed.h(replies_list,-1);
if( !parent.equals(accursed)){
int qx = sX-w/2 +2, qy = 5+head, qw = w/2-10, qh = sroom-20;
parent = parent.s(replies, -1);
sibl.makeFlob( into, parent, parent, cfr(fr*(w/2-10)),
qx + qw/2, qy + qh/2, 1, qw , qh,
-0.1f);
parent = parent.h(replies_list, -1, true);
if (parent != null) {
parent = parent.s(replies, -1);
sibl.makeFlob( into, parent, parent, cfr(fr*(w/2-10)),
qx - qw/4, qy - qh/4, 1, qw , qh,
0.07f);
}
/*into.add(new LineDecor(cx,cy+h/2,sX-w/2+2+(w/2-10)/2,
5+sroom-20,linecol,2));*/
}
p = accursed;
cSibl = 0;
sY = cy + h + vUnit;
rc = 0;
while( ( p = p.s(replies_list,1) ) != null ){
rc++;
}
p("got " + rc + " siblings");
sroom = (d.height - h)/2 - 6;
if( rc > 0 )
sroom = sroom / rc;
p = accursed;
//fr = 0.7f;
// child
ZZCell child = accursed.h(replies,1);
if( child != accursed ){
int qx = sX+w+10, qy = sY+head, qw = w/2, qh = d.height-5-sY;
child = child.s(replies_list, 1);
if( child != null) {
ZZCell child2 = child.s(replies_list, 1);
if (child2 != null) {
sibl.makeFlob( into, child2, child2, cfr(fr*(w/2)),
qx+qw/8, qy-qh/2, 1, qw, qh);
}
sibl.makeFlob( into, child, child, cfr(fr*(w/2)),
qx, /*d.height - 3*vUnit-5*/
qy-qh, 1, qw, qh/*3*vUnit*/);
}
//into.add(new LineDecor(cx+w/2,cy+h,sX+w+10,middle,linecol,2));
}
// siblings below the center blob
while( (p = p.s(replies_list, 1) ) != null && (cSibl < rc) ) {
blobs.makeFlob( into, p, p, cfr(fr*w),
sX, sY+10+head, 1, w, sroom-20);
cSibl = cSibl + 1;
sY = sY + sroom;
}
int th = 0;
//-------------------------------------------
// handle the other blobs
// depending on the center blob type
//-------------------------------------------
//-------------------------------------------
// put all the handles to right side
// in every case
//-------------------------------------------
// loop through the text cells, puts handle cells
// to handles
// XXX loop
p = accursed;
while( (p = p.s(text,1) ) != null){
ptr = p.h(handle);
if( p.getRankLength(handle) > 1 ) {
handles.put( ""+bc, ptr);
bc++;
}
}
if ( bc != 0 )
fh= d.height / bc;
// blobs on the right side
for( int i = 0; i < bc; i++ ){
ptr = (ZZCell)handles.get(""+i);
p("th = " + th + " ptr " + ptr);
p("fw = " +fw );
flobs.put(ptr, blobs.makeFlob( into, ptr, ptr, cfr(fr*(fw-2*xpad)),
d.width - fw-xpad, th+ypad+head, 1,
fw-2*xpad, fh-2*ypad));
th += fh;
}
//-------------------------------------------
// draw the links.
// not correct, but SFW, this is just a demo
//-------------------------------------------
for( int i = 0; i< bc; i++ ){
Flob flo=(Flob)flobs.get(handles.get(""+i));
Point pq = flo.getPoint(-1,0);
p("flo: " + flo + "p: " + pq);
Point pc = centerFlob.getPoint(1,0);
Flob l = new LinkFlob(pc.x,pc.y,pq.x,pq.y-flo.h/5,pq.x,pq.y+flo.h/5);
into.add(l);
}
bc=0;
//-------------------------------------------
// Depending the cell type, put the blobs
// on the left
//-------------------------------------------
bc = 0;
handles = new Hashtable();
p=accursed.h(author,-1);
// author ?
if( accursed == p && p.getRankLength(author) > 1 ){
p("AUTHOR DUDE");
// XXX loop
while( (p = p.s(author,1) ) != null){
//ptr = p.h(text, -1);
p("message");
//if( p.getRankLength(handle) > 1 ) {
handles.put( ""+bc, p);
bc++;
}
} else if ( accursed == (p=accursed.h(handle,-1)) &&
p.getRankLength(handle) > 1){
p("PRODUCT");
// XXX loop
while( (p = p.s(handle,1) ) != null){
ptr = p.h(text, -1);
//p("message");
//if( p.getRankLength(handle) > 1 ) {
handles.put( ""+bc, ptr);
bc++;
}
}
p("BC = " + bc);
th = 0;
if ( bc != 0 )
fh= d.height / bc;
// blobs on the right side
for( int i = 0; i < bc; i++ ){
ptr = (ZZCell)handles.get(""+i);
p("flob message");
p("th = " + th + " ptr " + ptr);
flobs.put(ptr,blobs.makeFlob( into, ptr, ptr, cfr(fr*(w-2*xpad)),
d.width-w-xpad, th+ypad+head, 1,
w-2*xpad, fh-2*ypad));
th += fh;
}
//-------------------------------------------
// draw the links.
// not correct, but SFW, this is just a demo
//-------------------------------------------
for( int i = 0; i< bc; i++ ){
Flob flo=(Flob)flobs.get(handles.get(""+i));
Point pq = flo.getPoint(-1,0);
p("flo: " + flo + "p: " + pq);
Point pc = centerFlob.getPoint(1,0);
Flob l = new LinkFlob(pc.x,pc.y,pq.x,pq.y-flo.h/5,pq.x,pq.y+flo.h/5);
into.add(l);
}
/*
// draw the links
FlobDecorator linker = new VCLinker();
linker.decorate(into, "", view);
*/
}
}

View File

@@ -0,0 +1,263 @@
/*
VCView2.java
*
* Copyright (c) 2001, Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Tuomas Lukka and Vesa Parkkinen
*/
package org.gzigzag.module;
import org.gzigzag.*;
import java.util.*;
import java.awt.*;
/** Second, cardstack-like virtualcommunity view.
*/
public class VCView2 extends VirtualCommunity {
public static final String rcsid = "$Id: VCView2.java,v 1.20 2001/02/28 10:18:20 tjl Exp $";
public static boolean dbg = false;
private static void p(String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
public void childSeries( FlobSet into, ZZCell cur, int x, int y,
int w, float fract, int orot, int dir, int depth) {
ZZCell s;
if(cur.s(replies) != null) {
s = cur.s(replies).s(replies_list);
if(s != null)
siblingSeries(into, s, x, y,
w, fract*magfract, orot, 1, depth+1);
}
}
static int borderLimit = 10;
final int rotinc = 1;
final int SCOFFS = 10;
double[]sins = new double[SCOFFS * 2];
double[]coss = new double[SCOFFS * 2];
// Point mkp(
void addVert(Point p, double h, int rot) {
p("Addvert: "+p+" "+h+" "+rot);
p.x -= (int)(sins[rot+SCOFFS] * h);
p.y += (int)(coss[rot+SCOFFS] * h);
p("Ret: "+p);
}
void addHoriz(Point p, double w, int rot) {
p.x += (int)(coss[rot+SCOFFS] * w);
p.y += (int)(sins[rot+SCOFFS] * w);
}
int getWid(int w, float fract) {
return (int)(w * Math.sqrt(fract));
}
int overlap = 10;
int bend = -5;
public void siblingSeries( FlobSet into, ZZCell cur, int x, int y,
int w,
float fract, int orot, int dir, int depth) {
if(depth >= view2depth) return;
Dimension rd = into.getSize();
ZZCell s;
int rot = 0;//orot;
Point curpoint = new Point(x,y);
Point upstart, downstart;
Point tmp = new Point();
// We do things differently depending on where we are.
// If going to positive direction, first see if we have odd
// or even number of cells and either put a cell in the middle
// or not
boolean domiddle = true;
if(dir == 1) {
cur = cur.h(replies_list);
int count = cur.getRankLength(replies_list) - 1;
if(count % 2 == 0) {
domiddle = false;
}
// Either upper or middle
cur = cur.s(replies_list, (count+1)/2);
}
int cw = getWid(w,fract);
if(domiddle) {
int h = sibl.getHeight(cur, cfr(fract), cw);
// h /= depth+1;
// h = (int)(80*fract);
// If not parent, put children for this center blob
if(dir >= 0) {
Point px = new Point(curpoint);
addHoriz(px, cw, rot);
childSeries(into, cur,
px.x, px.y,
w, fract, orot, 1, depth);
}
addVert(curpoint, -h/2, rot);
sibl.makeFlob(into, cur, cur, cfr(fract),
curpoint.x, curpoint.y, 10, cw, h,
rotunit * orot,
(dir == 0));
upstart = new Point(curpoint);
downstart = new Point(curpoint);
addVert(downstart, h, rot);
} else {
upstart = new Point(curpoint);
downstart = new Point(curpoint);
}
float cf = fract;
s=cur;
if(domiddle) s = s.s(replies_list, -1);
for(; s != null; s = s.s(replies_list, -1)) {
// if(cy <= borderLimit) break;
// Don't do relcell
if(s.s(replies_list, -1) == null) break;
cf *= magfract;
rot -= rotinc;
cw = getWid(w,cf);
int ch = sibl.getHeight(s, cfr(cf), cw);
// ch /= depth+1;
// ch = (int)(80*cf);
addVert(upstart, -ch + overlap, rot);
addHoriz(upstart, bend, rot);
sibl.makeFlob(into, s, s, cfr(cf),
upstart.x, upstart.y,
10, cw, ch,
rotunit * rot,
false);
tmp.setLocation(upstart);
addVert(tmp, ch/2, rot);
addHoriz(tmp, cw, rot);
childSeries(into, s,
tmp.x, tmp.y,
w, cf, rot, 1, depth);
}
cf = fract;
s=cur;
rot = orot;
while((s = s.s(replies_list, +1))!=null) {
// if(cy >= rd.height-borderLimit) break;
cf *= magfract;
rot += rotinc;
cw = getWid(w,cf);
addHoriz(downstart, bend, rot);
addVert(downstart, - overlap, rot);
int ch = sibl.getHeight(s, cfr(cf), cw);
// ch = (int)(80*cf);
// ch /= depth+1;
sibl.makeFlob(into, s, s, cfr(cf),
downstart.x, downstart.y,
10, cw, ch,
rotunit * rot,
false);
tmp.setLocation(downstart);
addVert(tmp, ch/2, rot);
addHoriz(tmp, cw, rot);
childSeries(into, s,
tmp.x, tmp.y,
w, cf, rot, 1, depth);
addVert(downstart, ch, rot);
}
// Parents
s = cur.h(replies_list).s(replies, -1);
if(dir <= 0 && s != null)
siblingSeries(
into, s, x - getWid(w, fract*magfract),
y, w, (float)(fract * magfract),
orot, -1, depth+1);
}
public void raster( FlobSet into, FlobFactory fact,
ZZCell view, String[] dims, ZZCell accursed){
accursed=accursed.h(text);
Dimension rd = into.getSize();
Dimension d = rd;
Dimension dprod = new Dimension(rd.width,70);
// Current rotation
double rot = 0;
{
for(int i=0; i<SCOFFS*2; i++) {
sins[i] = Math.sin((i-SCOFFS)*rotunit);
coss[i] = Math.cos((i-SCOFFS)*rotunit);
}
}
p("Rotunit: "+rotunit);
siblingSeries(into, accursed,
(int)(view2ctr[0] * d.width),
(int)(view2ctr[1] * d.height),
(int)(view2wid * d.width),
(float)view2fract, 0, 0, 0);
if(isProd(accursed)){
messagesFromProd(into,accursed,(float)1.0);
return;
}else if(isAuthor(accursed)){
messagesFrom(into,accursed,(float)1.0, author);
return;
}
addAuthor(into,accursed,1.0f);
drawProducts(into, (float)1.0, dprod);
}
}

View File

@@ -0,0 +1,242 @@
/*
VCView2.java
*
* Copyright (c) 2000, Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Tuomas Lukka and Vesa Parkkinen
*/
package org.gzigzag.module;
import org.gzigzag.*;
import java.util.*;
import java.awt.*;
/** Third, cardstack-like virtualcommunity view.
*/
public class VCView3 extends VirtualCommunity {
public static final String rcsid =
"$Id: VCView3.java,v 1.1 2001/02/27 20:02:21 veparkki Exp $";
public static boolean dbg = false;
private static void p (String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
int dx = 10;
int dy = 20;
public void childSeries( FlobSet into, ZZCell cur, int x, int y,
int w, float fract, double orot,
int dir, int depth) {
ZZCell s;
if(cur.s(replies) != null) {
s = cur.s(replies).s(replies_list);
if(s != null)
siblingSeries(into, s, x+(int)(w*fract), y,
w, fract*magfract, orot, 1, depth+1);
}
}
public void siblingSeries( FlobSet into, ZZCell cur, int x, int y,
int w,
float fract, double orot, int dir, int depth) {
if(depth >= 2) return;
ZZCell s;
int upstartx, upstarty, downstartx, downstarty;
// We do things differently depending on where we are.
// If going to positive direction, first see if we have odd
// or even number of cells and either put a cell in the middle
// or not
boolean domiddle = true;
int count = 0;
if(dir == 1) {
count = cur.getRankLength(replies_list) - 1;
if(count % 2 == 0) {
domiddle = false;
}
// Either upper or middle
cur = cur.s(replies_list, count/2);
}
int cw = (int)(w*fract);
if(domiddle) {
int h = sibl.getHeight(cur, cfr(fract), cw);
h /= depth+1;
// h = (int)(80*fract);
sibl.makeFlob(into, cur, cur, cfr(fract), x, y-h/2, 1, cw, h, orot,
(dir == 0));
// If not parent, put children for this center blob
if(dir >= 0)
childSeries(into, cur, x, y, w, fract, orot, 1, depth);
upstartx = x;
upstarty = y - h/2;
downstartx = x;
downstarty = y + h/2;
} else {
upstartx = x;
upstarty = y;
downstartx = x;
downstarty = y;
}
int cx = upstartx;
int cy = upstarty;
float cf = fract;
s=cur;
//if(!domiddle)
// s = s.s(replies_list, 1);
double rot = orot;
rot = 0.0;
//---
cx = downstartx;
cy = downstarty;
cf = fract;
s=cur;
rot = orot;
count = cur.getRankLength(replies_list) - 1;
if( count > 0){
FlobInfo[] fi = new FlobInfo[count];
int flth=0;
pa("COUNT: " + count);
while((s = s.s(replies_list, +1))!=null ) {
cf *= magfract;
rot += 0.00;
cw = (int)(w*cf);
int ch = sibl.getHeight(s, cfr(cf), cw);
// ch = (int)(80*cf);
ch /= depth+1;
fi[flth] = new FlobInfo(s,s,cfr(cf), cx,cy,1,cw,ch,rot);
pa("flth: " + flth);
//sibl.makeFlob(into, s, s, cfr(cf), cx, cy, 1, cw, ch, rot,
// false);
childSeries(into, s, cx, cy, w, fract, rot, 1, depth);
//cy += dy;
flth++;
}
for( int i=1; i<= flth;i++){
pa("i = " + i);
int mc = 4;
fi[flth-i].y += (flth-i)*(dy) + mc ;
fi[flth-i].x += (flth-i+1)*dx;
fi[flth-i].render(sibl,into);
}
}
cx = upstartx;
cy = upstarty;
cf = fract;
s=cur;
rot = orot;
while(s != null && (s = s.s(replies_list, -1))!=null) {
// Don't do relcell
if(s.s(replies_list, -1) == null) break;
cf *= magfract;
rot = 0.00;
cw = (int)(w*cf);
int ch = sibl.getHeight(s, cfr(cf), cw);
ch /= depth+1;
// ch = (int)(80*cf);
cy -= dy;
cx -= dx;
sibl.makeFlob(into, s, s, cfr(cf), cx, cy, 1, cw, ch, rot,
false);
childSeries(into, s, cx, cy, w, fract, rot, 1, depth);
}
//--
// Parents
s = cur.h(replies_list).s(replies, -1);
if(dir <= 0 && s != null)
siblingSeries(
into, s, x - (int)(w*fract*magfract),
y, w, (float)(fract * magfract),
orot, -1, depth+1);
}
//}
class FlobInfo {
int x;
int y;
int h;
int w;
int d;
ZZCell c;
ZZCell hc;
float fr;
double rot;
FlobInfo(ZZCell c, ZZCell hc, float fr,
int x, int y, int d, int w, int h, double rot){
this.c = c;
this.h=h;
this.fr=fr;
this.x=x;
this.y=y;
this.d=d;
this.w=w;
this.hc=hc;
this.rot = rot;
}
void render(MessageFlobFactory mess, FlobSet into){
mess.makeFlob(into, c, hc, fr, x, y, d, w, h, rot,
false);
}
}
public void raster( FlobSet into, FlobFactory fact,
ZZCell view, String[] dims, ZZCell accursed){
accursed=accursed.h(text);
Dimension rd = into.getSize();
Dimension d = rd;
// Current rotation
double rot = 0;
siblingSeries(into, accursed, 3*d.width/10, d.height/2, 2*d.width/5,
(float)1.0, 0, 0, 0);
}
}

View File

@@ -0,0 +1,141 @@
/*
VCView4.java
*
* Copyright (c) 2001, Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Tuomas Lukka
*/
package org.gzigzag.module;
import org.gzigzag.*;
import java.util.*;
import java.awt.*;
/** Second, cardstack-like virtualcommunity view.
*/
public class VCView4 extends VirtualCommunity {
public static final String rcsid = "$Id: VCView4.java,v 1.8 2001/02/28 10:18:20 tjl Exp $";
public static boolean dbg = false;
private static void p(String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
int xstep = 40;
int ystep = 40;
void mksideFlobs(FlobSet into, ZZCell cur, int x, int y, int w, int h, int d) {
cur = cur.s(replies);
if(cur == null) return;
y += 2*h/3;
h -= 2*h/3;
while((cur = cur.s(replies_list)) != null) {
if(into.findFlob(null, cur) != null)
return;
sibl.makeFlob(into, cur, cur, 0.5f,
x+w, y, d, w/3, h, 0, false);
y -= h/2;
h /= 2;
if(h == 0) return;
}
}
Point singleSiblingSide(FlobSet into, ZZCell outside, int x, int y,
int w, float fract, int dir, int depth, int side) {
ZZCell cur = outside;
for(int i=1; (cur=cur.s(replies_list,side))!=null; i++) {
if(cur.s(replies_list, -1) == null) break;
float mult = fract / i;
x -= side * mult * xstep;
y += side * mult * ystep;
int h = sibl.getHeight(cur, cfr(fract), w);
sibl.makeFlob(into, cur, cur, cfr(fract),
x, y, 1+50*depth + 2*i, w, h,
0, false);
mksideFlobs(into, cur, x, y, w+1, h, 1+50*depth);
}
return new Point(x,y);
}
public void siblingSeries( FlobSet into, ZZCell cur, int x, int y,
int w,
float fract, int dir, int depth) {
// dept
int h = sibl.getHeight(cur, cfr(fract), w);
p("Sibser: "+cur+" "+h+" "+w+" "+x+" "+y);
sibl.makeFlob(into, cur, cur, cfr(fract),
x, y, 1+50*depth, w+1,h,
0, (depth <= 2));
if(depth > 2)
mksideFlobs(into, cur, x, y, w+1, h, 1+50*depth);
Point p0 = singleSiblingSide(into, cur, x, y, w, fract, dir, depth, 1);
Point p1 = singleSiblingSide(into, cur, x, y, w, fract, dir, depth, -1);
into.add(new LineDecor(p0.x, p0.y, p1.x, p1.y, Color.red, 1));
}
public void raster( FlobSet into, FlobFactory fact,
ZZCell view, String[] dims, ZZCell accursed){
accursed=accursed.h(text);
Dimension rd = into.getSize();
Dimension dprod = new Dimension(rd.width,70);
Dimension d = rd;
ZZCell cur = accursed;
int x = d.width / 3;
int y = d.height / 3;
int w = d.width / 3;
float fr = 1.3f;
ZZCell child = accursed.s(replies, 1);
if(child != null) {
child = child.s(replies_list, 1);
siblingSeries(into, child, 2 * d.width / 3, d.height / 2, w,
(float)(fr * 1.0), 0, 1);
}
for(int pd = 0; pd<4 && cur != null; pd++) {
siblingSeries(into, cur, x, y, w,
fr, 0, 2 + pd);
cur = cur.h(replies_list).s(replies,-1);
fr *= 0.9;
w *= 0.9;
x -= 70;
y -= 70;
}
if(isProd(accursed)){
messagesFromProd(into,accursed,(float)1.0);
return;
} else if(isAuthor(accursed)){
messagesFrom(into,accursed,(float)1.0, author);
return;
}
addAuthor(into,accursed,1.0f);
drawProducts(into, (float)1.0, dprod);
}
}

View File

@@ -0,0 +1,444 @@
/*
VirtualCommunity.zob
*
* Copyright (c) 2001 Ted Nelson and Tuomas Lukka
*
* You may use and distribute under the terms of either the GNU Lesser
* General Public License, either version 2 of the license or,
* at your choice, any later version. Alternatively, you may use and
* distribute under the terms of the XPL.
*
* See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of
* the licenses.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README
* file for more details.
*
*/
/*
* Written by Vesa Parkkinen
*/
package org.gzigzag.module;
import org.gzigzag.*;
import java.util.*;
import java.awt.*;
/** A simple cell factory that gives the cells as one-line strings.
* Variable length is possible.
* UGLY: ALL PARAMS HERE.
*/
public abstract class VirtualCommunity implements FlobView, ZOb {
public static final String rcsid = "$Id: VirtualCommunity.zob,v 1.36 2001/02/28 10:18:20 tjl Exp $";
public static boolean dbg = false;
private static void p(String s) { if(dbg) ZZLogger.log(s); }
private static void pa(String s) { ZZLogger.log(s); }
// some parameters would be needed, propably
STRUCTPARAMS {
Font font
= new Font("SansSerif", Font.PLAIN, 11);
ZOb ftextlayouter
= new FTextLayouter();
double left
= 0.1;
double middle
= 0.4;
double right
= 0.3;
double middleHeight
= 0.5;
int xpad
= 5;
int ypad
= 5;
Color linecol
= Color.white;
float magfract
= 0.8f;
float rotunit
= 0.0f;
int view2depth
= 4;
float[] view2ctr // 2..2
= new float[] {0.35f, 0.5f};
float view2wid
= 0.22f;
float view2fract
= 1.4f;
}
/** Bold and italic derivatives of the font given.
* The first index is the level of the text i.e.
* from paragraph to H1.
*/
Font[][][] bifonts;
FontMetrics[][][] bifontms;
INITIALIZE {
bifonts = new Font[7][2][2];
bifontms = new FontMetrics[7][2][2];
for(int l = 0; l < bifonts.length; l++) {
int size = font.getSize();
if(l > 0 && l < 5) size += l-1;
if(l == 5) size += 6;
if(l == 6) size += 9;
bifonts[l][1][0] = new Font(font.getName(),
Font.BOLD, size);
bifonts[l][1][1] = new Font(font.getName(),
Font.BOLD | Font.ITALIC, size);
if(l == 0) {
bifonts[l][0][0] = new Font(font.getName(), 0, size);
bifonts[l][0][1] = new Font(font.getName(),
Font.ITALIC, size);
} else { // All bold for headers
bifonts[l][0][0] = bifonts[l][1][0];
bifonts[l][0][1] = bifonts[l][1][1];
}
for(int b = 0; b<2; b++)
for(int i = 0; i<2; i++)
bifontms[l][b][i] = FONTMETRICS(bifonts[l][b][i]);
}
}
Color linkcolor = Color.red;
Color default_bgcolor = Color.white;
static String text = "d.text";
static String handle = "d.kahva";
static String author = "d.author";
static String replies = "d.replies";
static String replies_list = "d.replies-list";
static protected class Foobar implements ZZObs {
private void add() {
vc.h("d.cursor-cargo", -1, this).
h("d.cursor-list", -1, this).s("d.cursor", -1, this);
}
public void chg() {
ZZCell targ = ZZCursorReal.get(vc).h(text);
ZZCell hist = ZZDefaultSpace.findInheritableParam(vc,"history");
if (targ.h("d.1").equals(hist)) {
p("Historical item");
histpos = targ;
add();
return;
}
ZZCell it = hist.s("d.1");
while (!it.equals(histpos) && !ZZCursorReal.get(it).equals(targ))
it = it.s("d.1");
if (!it.equals(histpos)) {
histpos = it;
ZZCursorReal.set(vc, histpos);
} else if (!targ.equals(ZZCursorReal.get(histpos))) {
if (histpos.s("d.1") != null) histpos.disconnect("d.1",1);
histpos = histpos.N("d.1");
ZZCursorReal.setcursor(histpos, targ);
}
add();
}
public void init(ZZCell _vc, ZZCell hilite) {
if (inited == false || !_vc.equals(vc)) {
vc = _vc;
histpos = hilite;
inited = true;
}
add();
}
boolean inited = false;
ZZCell vc;
public ZZCell histpos;
}
static protected Foobar histobs = new Foobar();
// flobFactories
MessageFlobFactory blobs = new MessageFlobFactory();
MessageFlobFactory center = new MessageFlobFactory();
MessageFlobFactory sibl = new MessageFlobFactory(this);
FlobFactory history = new MessageFlobFactory();
boolean nohistory = true;
/** Cut fracts into reasonable range.
*/
protected final float cfr(float fr) {
if (fr < 0.7f) return 0.7f;
if (fr > 2.0f) return 1.5f;
return fr;
}
abstract public void raster( FlobSet into, FlobFactory fact,
ZZCell view, String[] dims, ZZCell accursed);
static public ZZModule module = new ZZModule() {
public void action(String id,
ZZCell code,
ZZCell target,
ZZView view, ZZView cview,
String key, Point pt, ZZScene xi) {
if(id.equals("NEW")) {
} else {
p("Unknown VC module action: "+id);
}
}
public ZOb newZOb(String id) {
if(id.equals("View"))
return new VCView2();
if(id.equals("View2"))
return new VCView2();
if(id.equals("View3"))
return new VCView3();
if(id.equals("View4"))
return new VCView4();
else
return null;
}
};
class VCLinker implements FlobDecorator{
public void decorate(FlobSet f, String path, ZZCell view) {
}
}
class LinkFlob extends Flob {
int n = 4;
int[] xs = new int[n];
int[] ys = new int[n];
// Color fg = new Color(0xa6dbac);
Color fg = new Color(0x86bbac);
public LinkFlob(int x, int y, int x1, int y1, int x2, int y2) {
super(x,y,1,x1-x,y2-y1,null);
xs[0] = x;
xs[1] = x1;
xs[2] = x2;
ys[0] = y;
ys[1] = y1;
ys[2] = y2;
n = 3;
}
public LinkFlob(int x, int y, int x1, int y1, int x2, int y2, int x3, int y3) {
super(x,y,1,x1-x,y2-y1,null);
xs[0] = x;
xs[1] = x1;
xs[2] = x2;
xs[3] = x3;
ys[0] = y;
ys[1] = y1;
ys[2] = y2;
ys[3] = y3;
n = 4;
}
public void render(Graphics g, int mx, int my, int md,
int mw, int mh) {
Color old = g.getColor();
g.setColor(fg );
g.fillPolygon(xs, ys, n);
g.setColor(old);
}
}
Hashtable prods;
class Dfoo{
int d;
Dfoo(int d){
this.d = d;
}
}
/**
*
*/
void product(ZZCell c, Point p){
if(c == null ) return;
if( prods == null) prods = new Hashtable();
// XXX overwrites...
prods.put(c, p);
}
public void messagesFromProd(FlobSet into, ZZCell c, float fract){
messagesFrom(into,c,fract,handle);
}
public void messagesFrom(FlobSet into, ZZCell c, float fract,
String dim){
ZZCell d = c.h(text,-1);
int xpad = 5;
int ypad = 5;
int y = ypad;
int w = 100;
int h = into.getSize().height;
int x = into.getSize().width - w - xpad;
int l = d.getRankLength(dim) -1;
pa("L = " + l);
if( l < 1 ) return;
int hd = h/l;
hd -= ypad;
int depth = 1;
Flob flob = sibl.getSFlob().getFlobSet().findFlob(null,c);
Point pnt = flob.getPoint(1,0);
int cx = pnt.x;//into.getSize().width/2;
int cy = pnt.y;
d = d.s(dim,1);
ZZCell tmp = d;
while(d != null){
// make flob
tmp = d.h(text,-1);
sibl.makeFlob(into, tmp, tmp, cfr(fract),
x, y, depth, w,hd,
0, false);
// draw link
into.add(new LinkFlob(cx,cy,
x,y+ypad,
x,y+hd-ypad));
d = d.s(dim,1);
y+=hd + ypad;
}
}
boolean isProd(ZZCell c){
p("isProd: " + c);
c = c.h(text,-1);
if( c == null ) return false;
if( c.h(handle,-1) == c && c.s(handle,1) != null){
p("TRUE");
return true;
}
return false;
}
boolean isAuthor(ZZCell c){
if( c.h(author,-1) == c && c.s(author,1) != null )
return true;
return false;
}
ZZCell getAuthor(ZZCell c){
ZZCell d = c.h(text,-1);
d = d.h(author,-1);
return d;
}
void addAuthor(FlobSet into, ZZCell c, float fract){
if( isAuthor(c) ) return;
p("add author");
if( c==null) return;
ZZCell a = getAuthor(c);
if( a == null ) return;
Dimension d = into.getSize();
int xpad = 5;
int ypad = 5;
int w = d.width / 5;
int h = d.height / 5;
int x = 0+xpad;
int y = d.height - h-ypad;
int depth = 1;
sibl.makeFlob(into,a,a, fract,
x,y,depth,w,h,0,false);
Flob fl = into.findFlob(null, c);
Point p = fl.getPoint(-1,0);
into.add(new LinkFlob(p.x+5, p.y, p.x,p.y, x+w, y,x+w+5,y));
}
/**
*
*/
public void drawProducts(FlobSet into, float fraction,
Dimension dp){
// draw products from cells
p("cells");
if( prods == null || prods.size() < 1 ) return ;
int nprods = prods.size();
int upperH = dp.height;
int w = into.getSize().width;
int ypad = 5;
int y = ypad;
int xpad = 10;
int x = xpad/2;
int wd = w/(nprods);
int d = 1;
int dprod = 1;
if( wd > w/2 ) wd = w/2;
//FlobSet fs = sibl.getFlobSet();
wd -= xpad;
for(Enumeration e = prods.keys();
e.hasMoreElements();){
ZZCell cell = (ZZCell)e.nextElement();
Point p = (Point)prods.get(cell);
//Dimension pd = blobs.getSize(cells[i], fraction);
//if ( pd == null ) continue;
sibl.makeFlob(into, cell, cell, fraction,x,y,d,
wd,upperH, 0, false);
int center = x+wd/2;
into.add(new LinkFlob(center+5, upperH, center, upperH,
p.x,p.y,p.x+5,p.y));
x += wd + xpad;
}
}
}
// vim: set syntax=java :