Use sensible margins; added support for rendering interfaces implemented
and inner classes declared within the box for the appropriate class. git-svn-id: https://samskivert.googlecode.com/svn/trunk@193 6335cc39-0255-0410-8fd6-9bcaacd3b74c
This commit is contained in:
@@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// $Id: Driver.java,v 1.4 2001/07/17 06:01:08 mdb Exp $
|
// $Id: Driver.java,v 1.5 2001/07/17 07:18:09 mdb Exp $
|
||||||
|
|
||||||
package com.samskivert.viztool;
|
package com.samskivert.viztool;
|
||||||
|
|
||||||
@@ -49,16 +49,24 @@ public class Driver
|
|||||||
if (print) {
|
if (print) {
|
||||||
// we use the print system to render things
|
// we use the print system to render things
|
||||||
PrinterJob job = PrinterJob.getPrinterJob();
|
PrinterJob job = PrinterJob.getPrinterJob();
|
||||||
job.setPrintable(viz);
|
|
||||||
|
|
||||||
// pop up a dialog to format our pages
|
// pop up a dialog to format our pages
|
||||||
// PageFormat format = job.pageDialog(job.defaultPage());
|
// PageFormat format = job.pageDialog(job.defaultPage());
|
||||||
PageFormat format = job.defaultPage();
|
PageFormat format = job.defaultPage();
|
||||||
|
|
||||||
|
// use sensible margins
|
||||||
|
Paper paper = new Paper();
|
||||||
|
paper.setImageableArea(72*0.5, 72*0.5, 72*7.5, 72*10);
|
||||||
|
format.setPaper(paper);
|
||||||
|
|
||||||
// pop up a dialog to control printing
|
// pop up a dialog to control printing
|
||||||
job.printDialog();
|
job.printDialog();
|
||||||
|
|
||||||
|
// use our configured page format
|
||||||
|
job.setPrintable(viz, format);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
// invoke the printing process
|
||||||
job.print();
|
job.print();
|
||||||
} catch (PrinterException pe) {
|
} catch (PrinterException pe) {
|
||||||
pe.printStackTrace(System.err);
|
pe.printStackTrace(System.err);
|
||||||
|
|||||||
+80
-5
@@ -1,11 +1,12 @@
|
|||||||
//
|
//
|
||||||
// $Id: CascadingChainVisualizer.java,v 1.7 2001/07/17 06:01:08 mdb Exp $
|
// $Id: CascadingChainVisualizer.java,v 1.8 2001/07/17 07:18:09 mdb Exp $
|
||||||
|
|
||||||
package com.samskivert.viztool.viz;
|
package com.samskivert.viztool.viz;
|
||||||
|
|
||||||
import java.awt.Font;
|
import java.awt.Font;
|
||||||
import java.awt.Graphics2D;
|
import java.awt.Graphics2D;
|
||||||
import java.awt.font.TextLayout;
|
import java.awt.font.TextLayout;
|
||||||
|
import java.awt.font.FontRenderContext;
|
||||||
import java.awt.geom.*;
|
import java.awt.geom.*;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
@@ -38,6 +39,24 @@ public class CascadingChainVisualizer
|
|||||||
// the header will be the name of this chain surrounded by N
|
// the header will be the name of this chain surrounded by N
|
||||||
// points of space and a box
|
// points of space and a box
|
||||||
Rectangle2D bounds = getTextBox(gfx, layout);
|
Rectangle2D bounds = getTextBox(gfx, layout);
|
||||||
|
|
||||||
|
// add our inner classes and interface implementations, but only
|
||||||
|
// if we're not an out of package class
|
||||||
|
if (chain.inPackage()) {
|
||||||
|
String[] impls = chain.getImplementsNames();
|
||||||
|
for (int i = 0; i < impls.length; i++) {
|
||||||
|
bounds = accomodate(bounds, impls[i],
|
||||||
|
FontPicker.getImplementsFont(),
|
||||||
|
gfx.getFontRenderContext());
|
||||||
|
}
|
||||||
|
String[] decls = chain.getDeclaresNames();
|
||||||
|
for (int i = 0; i < decls.length; i++) {
|
||||||
|
bounds = accomodate(bounds, decls[i],
|
||||||
|
FontPicker.getDeclaresFont(),
|
||||||
|
gfx.getFontRenderContext());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
double maxwid = bounds.getWidth();
|
double maxwid = bounds.getWidth();
|
||||||
|
|
||||||
// the children will be below the name of this chain and inset by
|
// the children will be below the name of this chain and inset by
|
||||||
@@ -62,6 +81,17 @@ public class CascadingChainVisualizer
|
|||||||
chain.setBounds(cbounds.getX(), cbounds.getY(), maxwid, y);
|
chain.setBounds(cbounds.getX(), cbounds.getY(), maxwid, y);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected Rectangle2D accomodate (Rectangle2D bounds, String name,
|
||||||
|
Font font, FontRenderContext frc)
|
||||||
|
{
|
||||||
|
TextLayout layout = new TextLayout(name, font, frc);
|
||||||
|
Rectangle2D tbounds = layout.getBounds();
|
||||||
|
bounds.setRect(bounds.getX(), bounds.getY(),
|
||||||
|
Math.max(bounds.getWidth(), tbounds.getWidth()+INSET),
|
||||||
|
bounds.getHeight() + tbounds.getHeight());
|
||||||
|
return bounds;
|
||||||
|
}
|
||||||
|
|
||||||
// docs inherited from interface
|
// docs inherited from interface
|
||||||
public void renderChain (Chain chain, Graphics2D gfx)
|
public void renderChain (Chain chain, Graphics2D gfx)
|
||||||
{
|
{
|
||||||
@@ -76,16 +106,55 @@ public class CascadingChainVisualizer
|
|||||||
TextLayout layout = new TextLayout(chain.getName(), font,
|
TextLayout layout = new TextLayout(chain.getName(), font,
|
||||||
gfx.getFontRenderContext());
|
gfx.getFontRenderContext());
|
||||||
|
|
||||||
// stroke a box that will contain the name
|
|
||||||
Rectangle2D tbounds = getTextBox(gfx, layout);
|
Rectangle2D tbounds = getTextBox(gfx, layout);
|
||||||
double dx = -tbounds.getX(), dy = -tbounds.getY();
|
double dx = -tbounds.getX(), dy = -tbounds.getY();
|
||||||
tbounds.setRect(x, y, tbounds.getWidth(), tbounds.getHeight());
|
double maxwid = tbounds.getWidth();
|
||||||
gfx.draw(tbounds);
|
|
||||||
|
|
||||||
// now draw the name
|
// draw the name
|
||||||
layout.draw(gfx, (float)(x + dx + HEADER_BORDER),
|
layout.draw(gfx, (float)(x + dx + HEADER_BORDER),
|
||||||
(float)(y + dy + HEADER_BORDER));
|
(float)(y + dy + HEADER_BORDER));
|
||||||
|
|
||||||
|
// draw the interface and inner class info, but only if we're not
|
||||||
|
// an out of package class
|
||||||
|
double ix = x + HEADER_BORDER + INSET;
|
||||||
|
double iy = y + tbounds.getHeight() - HEADER_BORDER;
|
||||||
|
|
||||||
|
if (chain.inPackage()) {
|
||||||
|
String[] impls = chain.getImplementsNames();
|
||||||
|
for (int i = 0; i < impls.length; i++) {
|
||||||
|
TextLayout ilay =
|
||||||
|
new TextLayout(impls[i], FontPicker.getImplementsFont(),
|
||||||
|
gfx.getFontRenderContext());
|
||||||
|
Rectangle2D ibounds = ilay.getBounds();
|
||||||
|
double newwid = ibounds.getWidth() + 2*HEADER_BORDER + INSET;
|
||||||
|
if (newwid > maxwid) {
|
||||||
|
maxwid = newwid;
|
||||||
|
}
|
||||||
|
ilay.draw(gfx, (float)(ix - ibounds.getX()),
|
||||||
|
(float)(iy - ibounds.getY()));
|
||||||
|
iy += ibounds.getHeight();
|
||||||
|
}
|
||||||
|
|
||||||
|
String[] decls = chain.getDeclaresNames();
|
||||||
|
for (int i = 0; i < decls.length; i++) {
|
||||||
|
TextLayout ilay =
|
||||||
|
new TextLayout(decls[i], FontPicker.getDeclaresFont(),
|
||||||
|
gfx.getFontRenderContext());
|
||||||
|
Rectangle2D ibounds = ilay.getBounds();
|
||||||
|
double newwid = ibounds.getWidth() + 2*HEADER_BORDER + INSET;
|
||||||
|
if (newwid > maxwid) {
|
||||||
|
maxwid = newwid;
|
||||||
|
}
|
||||||
|
ilay.draw(gfx, (float)(ix - ibounds.getX()),
|
||||||
|
(float)(iy - ibounds.getY()));
|
||||||
|
iy += ibounds.getHeight();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// stroke a box that will contain the name
|
||||||
|
tbounds.setRect(x, y, maxwid, iy - y + HEADER_BORDER);
|
||||||
|
gfx.draw(tbounds);
|
||||||
|
|
||||||
// render our connecty lines
|
// render our connecty lines
|
||||||
ArrayList kids = chain.getChildren();
|
ArrayList kids = chain.getChildren();
|
||||||
if (kids.size() > 0) {
|
if (kids.size() > 0) {
|
||||||
@@ -139,4 +208,10 @@ public class CascadingChainVisualizer
|
|||||||
* The number of points of spacing between each child chain.
|
* The number of points of spacing between each child chain.
|
||||||
*/
|
*/
|
||||||
protected static final double GAP = 4;
|
protected static final double GAP = 4;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The number of points that interfaces and inner class declarations
|
||||||
|
* are indented.
|
||||||
|
*/
|
||||||
|
protected static final double INSET = 3;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// $Id: Chain.java,v 1.4 2001/07/17 01:54:19 mdb Exp $
|
// $Id: Chain.java,v 1.5 2001/07/17 07:18:09 mdb Exp $
|
||||||
|
|
||||||
package com.samskivert.viztool.viz;
|
package com.samskivert.viztool.viz;
|
||||||
|
|
||||||
@@ -16,10 +16,11 @@ public class Chain implements Element
|
|||||||
/**
|
/**
|
||||||
* Constructs a chain with the specified class as its root.
|
* Constructs a chain with the specified class as its root.
|
||||||
*/
|
*/
|
||||||
public Chain (String name, Class root)
|
public Chain (String name, Class root, boolean inpkg)
|
||||||
{
|
{
|
||||||
_name = name;
|
_name = name;
|
||||||
_root = root;
|
_root = root;
|
||||||
|
_inpkg = inpkg;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -39,6 +40,15 @@ public class Chain implements Element
|
|||||||
return _root;
|
return _root;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns true if the class represented by this point in the chain is
|
||||||
|
* in the package we are visualizing, false if it is not.
|
||||||
|
*/
|
||||||
|
public boolean inPackage ()
|
||||||
|
{
|
||||||
|
return _inpkg;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the name of the class that forms the root of this chain.
|
* Returns the name of the class that forms the root of this chain.
|
||||||
*/
|
*/
|
||||||
@@ -47,6 +57,77 @@ public class Chain implements Element
|
|||||||
return _root.getName();
|
return _root.getName();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the names of the interfaces implemented by this class.
|
||||||
|
*/
|
||||||
|
public String[] getImplementsNames ()
|
||||||
|
{
|
||||||
|
Class[] ifaces = _root.getInterfaces();
|
||||||
|
String[] names = new String[ifaces.length];
|
||||||
|
String pkg = ChainUtil.pkgFromClass(_root.getName());
|
||||||
|
|
||||||
|
for (int i = 0; i < ifaces.length; i++) {
|
||||||
|
String name = ifaces[i].getName();
|
||||||
|
String ipkg = ChainUtil.pkgFromClass(name);
|
||||||
|
if (pkg.equals(ipkg)) {
|
||||||
|
names[i] = ChainUtil.nameFromClass(name);
|
||||||
|
} else {
|
||||||
|
names[i] = removeOverlap(pkg, name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected static String removeOverlap (String pkg, String name)
|
||||||
|
{
|
||||||
|
// strip off package elements until we've eliminated all but one
|
||||||
|
// level of overlap
|
||||||
|
String overlap = "";
|
||||||
|
int didx;
|
||||||
|
|
||||||
|
while ((didx = pkg.indexOf(".", overlap.length()+1)) != -1) {
|
||||||
|
// see if this chunk still overlaps
|
||||||
|
String prefix = pkg.substring(0, didx);
|
||||||
|
if (name.startsWith(prefix)) {
|
||||||
|
overlap = prefix;
|
||||||
|
} else {
|
||||||
|
// we've stopped overlapping, we need to back up one
|
||||||
|
// element and then we're good to go
|
||||||
|
if ((didx = overlap.lastIndexOf(".")) == -1) {
|
||||||
|
overlap = "";
|
||||||
|
} else {
|
||||||
|
overlap = overlap.substring(0, didx);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// if there's an overlap, remove it
|
||||||
|
if (overlap.length() > 0) {
|
||||||
|
return ".." + name.substring(overlap.length());
|
||||||
|
} else {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the names of the inner classes declared by this class.
|
||||||
|
*/
|
||||||
|
public String[] getDeclaresNames ()
|
||||||
|
{
|
||||||
|
Class[] decls = _root.getDeclaredClasses();
|
||||||
|
String[] names = new String[decls.length];
|
||||||
|
|
||||||
|
for (int i = 0; i < decls.length; i++) {
|
||||||
|
String name = decls[i].getName();
|
||||||
|
int didx = name.indexOf("$");
|
||||||
|
names[i] = (didx == -1) ? name : name.substring(didx+1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a <code>Rectangle2D</code> instance representing the size
|
* Returns a <code>Rectangle2D</code> instance representing the size
|
||||||
* of this chain (and all contained subchains).
|
* of this chain (and all contained subchains).
|
||||||
@@ -100,7 +181,11 @@ public class Chain implements Element
|
|||||||
*/
|
*/
|
||||||
public void addClass (String name, Class child)
|
public void addClass (String name, Class child)
|
||||||
{
|
{
|
||||||
Chain chain = new Chain(name, child);
|
// we assume that the addition of a derived class is only done for
|
||||||
|
// classes that are in the package we're visualizing. out of
|
||||||
|
// package classes are only included as roots of chains that
|
||||||
|
// subsequently contain classes that are in the package
|
||||||
|
Chain chain = new Chain(name, child, true);
|
||||||
if (!_children.contains(chain)) {
|
if (!_children.contains(chain)) {
|
||||||
_children.add(chain);
|
_children.add(chain);
|
||||||
}
|
}
|
||||||
@@ -157,6 +242,7 @@ public class Chain implements Element
|
|||||||
|
|
||||||
protected String _name;
|
protected String _name;
|
||||||
protected Class _root;
|
protected Class _root;
|
||||||
|
protected boolean _inpkg;
|
||||||
|
|
||||||
protected ArrayList _children = new ArrayList();
|
protected ArrayList _children = new ArrayList();
|
||||||
protected Rectangle2D _bounds = new Rectangle2D.Double();
|
protected Rectangle2D _bounds = new Rectangle2D.Double();
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// $Id: ChainUtil.java,v 1.3 2001/07/14 00:55:21 mdb Exp $
|
// $Id: ChainUtil.java,v 1.4 2001/07/17 07:18:09 mdb Exp $
|
||||||
|
|
||||||
package com.samskivert.viztool.viz;
|
package com.samskivert.viztool.viz;
|
||||||
|
|
||||||
@@ -115,7 +115,7 @@ public class ChainUtil
|
|||||||
// if we have no parent, we want to insert ourselves as a root
|
// if we have no parent, we want to insert ourselves as a root
|
||||||
// class
|
// class
|
||||||
if (parent == null || parent.equals(Object.class)) {
|
if (parent == null || parent.equals(Object.class)) {
|
||||||
insertRoot(roots, name, target);
|
insertRoot(roots, name, target, true);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
String tpkg = pkgFromClass(target.getName());
|
String tpkg = pkgFromClass(target.getName());
|
||||||
@@ -125,7 +125,7 @@ public class ChainUtil
|
|||||||
// into the hierarchy as a root class
|
// into the hierarchy as a root class
|
||||||
if (!tpkg.equals(ppkg)) {
|
if (!tpkg.equals(ppkg)) {
|
||||||
String pname = generateName(parent, pkgroot, true);
|
String pname = generateName(parent, pkgroot, true);
|
||||||
insertRoot(roots, pname, parent);
|
insertRoot(roots, pname, parent, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
// and now hang ourselves off of our parent class
|
// and now hang ourselves off of our parent class
|
||||||
@@ -196,9 +196,9 @@ public class ChainUtil
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected static boolean insertRoot (ArrayList roots, String name,
|
protected static boolean insertRoot (ArrayList roots, String name,
|
||||||
Class root)
|
Class root, boolean inpkg)
|
||||||
{
|
{
|
||||||
Chain chroot = new Chain(name, root);
|
Chain chroot = new Chain(name, root, inpkg);
|
||||||
// make sure no chain already exists for this root
|
// make sure no chain already exists for this root
|
||||||
if (!roots.contains(chroot)) {
|
if (!roots.contains(chroot)) {
|
||||||
roots.add(chroot);
|
roots.add(chroot);
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
//
|
//
|
||||||
// $Id: HierarchyVisualizer.java,v 1.6 2001/07/17 05:28:46 mdb Exp $
|
// $Id: HierarchyVisualizer.java,v 1.7 2001/07/17 07:18:09 mdb Exp $
|
||||||
|
|
||||||
package com.samskivert.viztool.viz;
|
package com.samskivert.viztool.viz;
|
||||||
|
|
||||||
@@ -37,7 +37,13 @@ public class HierarchyVisualizer implements Printable
|
|||||||
// dump all the classes into an array list so that we can
|
// dump all the classes into an array list so that we can
|
||||||
// repeatedly scan through the list
|
// repeatedly scan through the list
|
||||||
while (iter.hasNext()) {
|
while (iter.hasNext()) {
|
||||||
_classes.add(iter.next());
|
// strip out inner classes, we'll catch those via their
|
||||||
|
// declaring classes
|
||||||
|
String name = (String)iter.next();
|
||||||
|
if (name.indexOf("$") != -1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
_classes.add(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
// compile a list of all packages in our collection
|
// compile a list of all packages in our collection
|
||||||
|
|||||||
Reference in New Issue
Block a user