public GraphVisualisation(rndalg.Graph graphToShow, Vector<Vertex> cut) {
    super();

    Graph displayed = new Graph(false);
    displayed.addColumn("id", String.class);
    displayed.addColumn("isCut", Boolean.class);

    this.makeGraph(displayed, graphToShow, cut);
    this.addGraph("graph", displayed);

    LabelRenderer r = new LabelRenderer("id");
    r.setRoundedCorner(10, 10);
    r.setHorizontalPadding(5);
    r.setVerticalPadding(2);
    this.setRendererFactory(new DefaultRendererFactory(r));

    ActionList layoutActions = new ActionList(Activity.INFINITY);
    ForceDirectedLayout layout = new ForceDirectedLayout("graph");
    layoutActions.add(layout);
    layoutActions.add(new RepaintAction());

    // black text
    ColorAction textCA =
        new ColorAction("graph.nodes", VisualItem.TEXTCOLOR, ColorLib.rgb(0, 0, 0));
    // black edges
    // ColorAction edgeCA = new ColorAction("graph.edges", VisualItem.STROKECOLOR,
    // ColorLib.rgb(0,0,0));
    // edges
    ColorAction edgeCA =
        new ColorAction(
            "graph.edges",
            ExpressionParser.predicate("isCut = false"),
            VisualItem.STROKECOLOR,
            ColorLib.rgb(0, 0, 0));
    ColorAction edgeCutCA =
        new ColorAction(
            "graph.edges",
            ExpressionParser.predicate("isCut = true"),
            VisualItem.STROKECOLOR,
            ColorLib.rgb(255, 0, 0));

    // concatenate the color actions
    ActionList colorActions = new ActionList();
    colorActions.add(textCA);
    colorActions.add(edgeCA);
    colorActions.add(edgeCutCA);

    this.putAction("draw", colorActions);
    this.putAction("layout", layoutActions);
    this.runAfter("draw", "layout");

    this.run("draw");
  }
Beispiel #2
0
  public trial(int st, String n) {

    // setup a visualisation
    super(new Visualization());

    System.out.println(st + "  " + n);

    // generate a graph
    initGraph(n, st);

    //  standard labelRenderer for the given label
    LabelRenderer nodeRenderer = new LabelRenderer(LABEL);
    // rendererFactory for the visualization items
    DefaultRendererFactory rendererFactory = new DefaultRendererFactory();
    // set the labelRenderer
    rendererFactory.setDefaultRenderer(nodeRenderer);
    m_vis.setRendererFactory(rendererFactory);

    // Color Actions
    ColorAction nodeText = new ColorAction(NODES, VisualItem.TEXTCOLOR);
    nodeText.setDefaultColor(ColorLib.gray(0));
    ColorAction nodeStroke = new ColorAction(NODES, VisualItem.STROKECOLOR);
    nodeStroke.setDefaultColor(ColorLib.gray(100));
    ColorAction nodeFill = new ColorAction(NODES, VisualItem.FILLCOLOR);
    nodeFill.setDefaultColor(ColorLib.gray(255));
    ColorAction edgeStrokes = new ColorAction(EDGES, VisualItem.STROKECOLOR);
    edgeStrokes.setDefaultColor(ColorLib.gray(100));

    // ColorAction fill = new ColorAction(NODES, VisualItem.FILLCOLOR,
    ColorLib.rgb(200, 200, 255);
    // fill.add(VisualItem.FIXED, ColorLib.rgb(255,100,100));
    // fill.add(VisualItem.HIGHLIGHT, ColorLib.rgb(255,200,125));

    // bundle the color actions
    ActionList draw = new ActionList();
    //    draw.add(fill);
    draw.add(new ColorAction(NODES, VisualItem.STROKECOLOR, 0));
    draw.add(new ColorAction(NODES, VisualItem.TEXTCOLOR, ColorLib.rgb(0, 0, 0)));
    draw.add(new ColorAction(EDGES, VisualItem.FILLCOLOR, ColorLib.gray(200)));
    draw.add(new ColorAction(EDGES, VisualItem.STROKECOLOR, ColorLib.gray(200)));
    draw.add(nodeText);
    draw.add(nodeStroke);
    draw.add(nodeFill);
    draw.add(edgeStrokes);

    ActionList animate = new ActionList(Activity.INFINITY);
    //   animate.add(fill);
    animate.add(new RepaintAction());

    m_nodeRenderer = new LabelRenderer(m_label);

    m_nodeRenderer.setRenderType(AbstractShapeRenderer.RENDER_TYPE_FILL);
    m_nodeRenderer.setHorizontalAlignment(Constants.LEFT);
    m_nodeRenderer.setRoundedCorner(8, 8);
    m_edgeRenderer = new EdgeRenderer(Constants.EDGE_TYPE_CURVE);

    DefaultRendererFactory rf = new DefaultRendererFactory(m_nodeRenderer);
    m_vis.setRendererFactory(rf);

    // DataSizeAction
    DataSizeAction nodeDataSizeAction = new DataSizeAction(NODES, SIZE);
    draw.add(nodeDataSizeAction);
    m_vis.putAction("draw", draw);
    m_vis.putAction("layout", animate);

    m_vis.runAfter("draw", "layout");

    // create the layout action for the graph
    NodeLinkTreeLayout treeLayout = new NodeLinkTreeLayout(GRAPH, m_orientation, 80, 5, 10);
    treeLayout.setLayoutAnchor(new Point2D.Double(250, -150));
    m_vis.putAction("treeLayout", treeLayout);
    m_vis.addFocusGroup("selected");

    CollapsedSubtreeLayout subLayout = new CollapsedSubtreeLayout(GRAPH, m_orientation);
    m_vis.putAction("subLayout", subLayout);

    m_vis.run("treeLayout");
    m_vis.run("draw");

    pan(250, 250);
    setHighQuality(true);
    addControlListener(new ZoomControl());
    addControlListener(new PanControl());
    addControlListener(new DragControl(true));
    addControlListener(new NodeClicked());
    addControlListener(new FocusControl());

    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_LEFT_RIGHT),
        "left-to-right",
        KeyStroke.getKeyStroke("ctrl 1"),
        WHEN_FOCUSED);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_TOP_BOTTOM),
        "top-to-bottom",
        KeyStroke.getKeyStroke("ctrl 2"),
        WHEN_FOCUSED);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_RIGHT_LEFT),
        "right-to-left",
        KeyStroke.getKeyStroke("ctrl 3"),
        WHEN_FOCUSED);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_BOTTOM_TOP),
        "bottom-to-top",
        KeyStroke.getKeyStroke("ctrl 4"),
        WHEN_FOCUSED);
    TupleSet search = new PrefixSearchTupleSet();
    m_vis.addFocusGroup(Visualization.SEARCH_ITEMS, search);
    search.addTupleSetListener(
        new TupleSetListener() {
          public void tupleSetChanged(TupleSet t, Tuple[] add, Tuple[] rem) {
            m_vis.cancel("animatePaint");
            m_vis.run("fullPaint");
            m_vis.run("animatePaint");
          }
        });
  }
  public ConcordanceTree() {
    super(new Visualization());

    m_display_self = this;
    m_label = NAME;

    tree = new Tree();
    Table ntable = tree.getNodeTable();
    ntable.addColumn(NAME, String.class);
    ntable.addColumn(NODECOUNT, int.class);
    ntable.addColumn(ROWCOUNT, int.class);
    resetTree();

    m_vis.add(TREE, tree);
    // m_vis.add(TREE, t, new WordCountPredicate());

    m_nodeRenderer = new LabelRenderer(m_label);
    m_nodeRenderer.setRenderType(AbstractShapeRenderer.RENDER_TYPE_FILL);
    m_nodeRenderer.setHorizontalAlignment(Constants.LEFT);
    m_nodeRenderer.setRoundedCorner(8, 8);
    m_edgeRenderer = new EdgeRenderer(Constants.EDGE_TYPE_CURVE);

    DefaultRendererFactory rf = new DefaultRendererFactory(m_nodeRenderer);
    rf.add(new InGroupPredicate(TREEEDGES), m_edgeRenderer);
    m_vis.setRendererFactory(rf);

    // colors
    ItemAction nodeColor = new NodeColorAction(TREENODES);
    ItemAction textColor = new ColorAction(TREENODES, VisualItem.TEXTCOLOR, ColorLib.rgb(0, 0, 0));
    m_vis.putAction("textColor", textColor);

    ItemAction edgeColor =
        new ColorAction(TREEEDGES, VisualItem.STROKECOLOR, ColorLib.rgb(255, 155, 155));

    // quick repaint
    ActionList repaint = new ActionList();
    repaint.add(nodeColor);
    // WordSizeAction wsaction = new WordSizeAction(TREEEDGES);
    repaint.add(new RepaintAction());
    m_vis.putAction("repaint", repaint);

    // full paint
    ActionList fullPaint = new ActionList();
    fullPaint.add(nodeColor);
    m_vis.putAction("fullPaint", fullPaint);

    // animate paint change
    ActionList animatePaint = new ActionList(400);
    animatePaint.add(new ColorAnimator(TREENODES));
    animatePaint.add(new RepaintAction());
    m_vis.putAction("animatePaint", animatePaint);

    // create the tree layout action
    NodeLinkTreeLayout treeLayout = new NodeLinkTreeLayout(TREE, m_orientation, 10, 0, 0);

    Point2D anchor = new Point2D.Double(25, HEIGHT / 2);
    treeLayout.setLayoutAnchor(anchor);
    m_vis.putAction("treeLayout", treeLayout);

    CollapsedSubtreeLayout subLayout = new CollapsedSubtreeLayout(TREE, m_orientation);
    m_vis.putAction("subLayout", subLayout);

    AutoPanAction autoPan = new AutoPanAction();
    AutoCenterAction autocenter = new AutoCenterAction();
    AutoFitAction autofit = new AutoFitAction();

    ActionList positioning = new ActionList();
    positioning.add(autofit);
    m_vis.putAction("positioning", positioning);

    ActionList fna = new ActionList();
    fna.add(new WordFontAction(TREENODES, defaultTreeFont));
    //   fna.add(new EdgeWidthAction(TREEEDGES));
    // fna.add(new WordSizeAction(TREEEDGES));
    m_vis.putAction("fontnodeaction", fna);

    // create the filtering and layout
    ActionList filter = new ActionList();
    filter.add(fna);
    filter.add(fisheyetreefilter);
    // VisibilityFilter visibfilter = new VisibilityFilter(new WordCountPredicate());
    // filter.add(visibfilter);
    filter.add(treeLayout);
    filter.add(subLayout);
    filter.add(textColor);
    filter.add(nodeColor);
    filter.add(edgeColor);
    m_vis.putAction("filter", filter);

    // This doesn't quite work as expected; the layout is calculated
    // for the entire tree and low freq nodes are simply not shown,
    // leaving gaps in the layout
    //
    // setPredicate(new WordCountPredicate());

    // animated transition
    ActionList animate = new ActionList(1000);
    animate.setPacingFunction(new SlowInSlowOutPacer());
    // animate.add(autoPan);
    animate.add(new QualityControlAnimator());
    animate.add(new VisibilityAnimator(TREE));
    animate.add(new LocationAnimator(TREENODES));
    animate.add(new ColorAnimator(TREENODES));
    animate.add(new RepaintAction());
    m_vis.putAction("animate", animate);
    m_vis.alwaysRunAfter("filter", "animate");

    // create animator for orientation changes
    ActionList orient = new ActionList(2000);
    orient.setPacingFunction(new SlowInSlowOutPacer());
    // orient.add(autoPan);
    // orient.add(autocenter);
    orient.add(new QualityControlAnimator());
    orient.add(new LocationAnimator(TREENODES));
    orient.add(new RepaintAction());
    // orient.add(autofit);

    m_vis.putAction("orient", orient);

    // ------------------------------------------------

    // initialize the display
    setSize(WIDTH, HEIGHT);
    setItemSorter(new TreeDepthItemSorter());
    addControlListener(new ZoomToFitControl());
    addControlListener(new ZoomControl());
    addControlListener(new WheelZoomControl());
    addControlListener(new PanControl());
    addControlListener(new FocusControl(1, "filter"));
    addControlListener(new ToolTipControl(NODECOUNT));

    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_LEFT_RIGHT),
        "left-to-right",
        KeyStroke.getKeyStroke("ctrl 1"),
        WHEN_IN_FOCUSED_WINDOW);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_TOP_BOTTOM),
        "top-to-bottom",
        KeyStroke.getKeyStroke("ctrl 2"),
        WHEN_IN_FOCUSED_WINDOW);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_RIGHT_LEFT),
        "right-to-left",
        KeyStroke.getKeyStroke("ctrl 3"),
        WHEN_IN_FOCUSED_WINDOW);
    registerKeyboardAction(
        new OrientAction(Constants.ORIENT_BOTTOM_TOP),
        "bottom-to-top",
        KeyStroke.getKeyStroke("ctrl 4"),
        WHEN_IN_FOCUSED_WINDOW);
    registerKeyboardAction(
        new FisheyeExpandAction(-1),
        "collapse-one",
        KeyStroke.getKeyStroke("ctrl 5"),
        WHEN_IN_FOCUSED_WINDOW);
    registerKeyboardAction(
        new FisheyeExpandAction(+1),
        "expand-one",
        KeyStroke.getKeyStroke("ctrl 6"),
        WHEN_IN_FOCUSED_WINDOW);

    // ------------------------------------------------

    // filter graph and perform layout
    setOrientation(m_orientation);
    m_vis.run("filter");

    /*
    TupleSet search = new PrefixSearchTupleSet();
      m_vis.addFocusGroup(Visualization.SEARCH_ITEMS, search);
      search.addTupleSetListener(new TupleSetListener() {
          public void tupleSetChanged(TupleSet t, Tuple[] add, Tuple[] rem) {
            m_vis.cancel("animatePaint");
            m_vis.run("fullPaint");
            m_vis.run("animatePaint");
          }
        });
       */

  }
  public PhysioMapRadialGraphView(
      SemGenSettings sets, Graph g, String label, SemSimModel semsimmodel) {
    super(new Visualization());
    this.semsimmodel = semsimmodel;

    // -- set up visualization --
    m_vis.add(tree, g);
    m_vis.setInteractive(treeEdges, null, false);

    // -- set up renderers --
    LabelRenderer m_nodeRenderer = new LabelRenderer(label);
    m_nodeRenderer.setRenderType(AbstractShapeRenderer.RENDER_TYPE_DRAW_AND_FILL);
    m_nodeRenderer.setHorizontalAlignment(Constants.CENTER);
    m_nodeRenderer.setRoundedCorner(8, 8);
    EdgeRenderer m_edgeRenderer =
        new EdgeRenderer(Constants.EDGE_TYPE_LINE, prefuse.Constants.EDGE_ARROW_REVERSE);
    m_edgeRenderer.setArrowType(prefuse.Constants.EDGE_ARROW_REVERSE);
    m_edgeRenderer.setArrowHeadSize(8, 8);

    // MAYBE HERE?
    DefaultRendererFactory rf = new DefaultRendererFactory(m_nodeRenderer);
    rf.add(new InGroupPredicate(treeEdges), m_edgeRenderer);
    m_vis.setRendererFactory(rf);
    // m_vis.

    // -- set up processing actions --
    // colors
    ItemAction nodeColor = new NodeColorAction(treeNodes);
    ItemAction borderColor = new BorderColorAction(treeNodes);
    m_vis.putAction("borderColor", borderColor);
    ItemAction textColor = new TextColorAction(treeNodes);
    m_vis.putAction("textColor", textColor);
    ItemAction edgeColor =
        new ColorAction(treeEdges, VisualItem.STROKECOLOR, ColorLib.rgb(0, 0, 0));
    ItemAction arrowColor = new ArrowColorAction(treeEdges);
    m_vis.putAction("arrowColor", arrowColor);

    FontAction fonts = new FontAction(treeNodes, FontLib.getFont("Verdana", 12));
    fonts.add("ingroup('_focus_')", FontLib.getFont("Verdana", 12));

    // recolor
    // When recolor, do these actions
    ActionList recolor = new ActionList();
    recolor.add(nodeColor);
    recolor.add(borderColor);
    recolor.add(textColor);
    recolor.add(arrowColor);
    m_vis.putAction("recolor", recolor);

    // repaint
    ActionList repaint = new ActionList();
    repaint.add(recolor);
    repaint.add(new RepaintAction());
    m_vis.putAction("repaint", repaint);

    // animate paint change
    ActionList animatePaint = new ActionList(400);
    animatePaint.add(new ColorAnimator(treeNodes));
    animatePaint.add(new RepaintAction());
    m_vis.putAction("animatePaint", animatePaint);

    // create the tree layout action
    RadialTreeLayout treeLayout = new RadialTreeLayout(tree);
    treeLayout.setAutoScale(true);
    m_vis.putAction("treeLayout", treeLayout);

    CollapsedSubtreeLayout subLayout = new CollapsedSubtreeLayout(tree);
    m_vis.putAction("subLayout", subLayout);

    // create the filtering and layout
    ActionList filter = new ActionList();
    filter.add(new TreeRootAction(tree));
    filter.add(fonts);
    filter.add(treeLayout);
    filter.add(borderColor);
    filter.add(subLayout);
    filter.add(textColor);
    filter.add(nodeColor);
    filter.add(edgeColor);
    filter.add(arrowColor);
    m_vis.putAction("filter", filter);

    // animated transition
    ActionList animate = new ActionList(700);
    animate.setPacingFunction(new SlowInSlowOutPacer());
    animate.add(new QualityControlAnimator());
    animate.add(new VisibilityAnimator(tree));
    animate.add(new PolarLocationAnimator(treeNodes, linear));
    animate.add(new ColorAnimator(treeNodes));
    animate.add(new RepaintAction());
    m_vis.putAction("animate", animate);
    m_vis.alwaysRunAfter("filter", "animate");
    // ------------------------------------------------

    // initialize the display

    setSize(sets.getAppWidth() - ExtractorTab.leftpanewidth - 50, sets.getAppHeight() - 235);
    setItemSorter(new TreeDepthItemSorter());
    addControlListener(new DragControl());
    addControlListener(new ZoomToFitControl());
    addControlListener(new ZoomControl());
    addControlListener(new PanControl());
    addControlListener(new FocusControl(1, "filter"));
    addControlListener(new HoverActionControl("repaint"));

    // ------------------------------------------------

    // filter graph and perform layout
    m_vis.run("filter");

    // maintain a set of items that should be interpolated linearly
    // this isn't absolutely necessary, but makes the animations nicer
    // the PolarLocationAnimator should read this set and act accordingly
    m_vis.addFocusGroup(linear, new DefaultTupleSet());
    m_vis
        .getGroup(Visualization.FOCUS_ITEMS)
        .addTupleSetListener(
            new TupleSetListener() {
              public void tupleSetChanged(TupleSet t, Tuple[] add, Tuple[] rem) {
                TupleSet linearInterp = m_vis.getGroup(linear);
                if (add.length < 1) return;
                linearInterp.clear();
                for (Node n = (Node) add[0]; n != null; n = n.getParent()) linearInterp.addTuple(n);
              }
            });

    SearchTupleSet search = new PrefixSearchTupleSet();
    m_vis.addFocusGroup(Visualization.SEARCH_ITEMS, search);
    search.addTupleSetListener(
        new TupleSetListener() {
          public void tupleSetChanged(TupleSet t, Tuple[] add, Tuple[] rem) {
            m_vis.cancel("animatePaint");
            m_vis.run("recolor");
            m_vis.run("animatePaint");
          }
        });
  }
Beispiel #5
0
  public static void main(String[] argv) {

    // -- 1. load the data ------------------------------------------------

    // load the socialnet.xml file. it is assumed that the file can be
    // found at the root of the java classpath
    Graph graph = null;
    try {
      graph = new GraphMLReader().readGraph(System.in);
    } catch (DataIOException e) {
      e.printStackTrace();
      System.err.println("Error loading graph. Exiting...");
      System.exit(1);
    }

    // -- 2. the visualization --------------------------------------------

    // add the graph to the visualization as the data group "graph"
    // nodes and edges are accessible as "graph.nodes" and "graph.edges"
    Visualization vis = new Visualization();
    vis.add("graph", graph);
    vis.setInteractive("graph.edges", null, false);

    // -- 3. the renderers and renderer factory ---------------------------

    // draw the "name" label for NodeItems
    LabelRenderer r = new LabelRenderer("label");
    r.setRoundedCorner(8, 8); // round the corners

    EdgeRenderer eRender =
        new EdgeRenderer(Constants.EDGE_TYPE_CURVE, Constants.EDGE_ARROW_FORWARD);

    // create a new default renderer factory
    // return our name label renderer as the default for all non-EdgeItems
    // includes straight line edges for EdgeItems by default
    vis.setRendererFactory(new DefaultRendererFactory(r, eRender));

    // -- 4. the processing actions ---------------------------------------

    // create our nominal color palette
    // pink for females, baby blue for males
    int[] palette =
        new int[] {
          ColorLib.rgb(190, 190, 255), ColorLib.rgb(255, 180, 180), ColorLib.rgb(128, 128, 128),
        };
    // map nominal data values to colors using our provided palette
    DataColorAction fill =
        new DataColorAction(
            "graph.nodes", "type", Constants.NOMINAL, VisualItem.FILLCOLOR, palette);

    // use black for node text
    ColorAction text = new ColorAction("graph.nodes", VisualItem.TEXTCOLOR, ColorLib.gray(0));
    // use light grey for edges
    ColorAction edges = new ColorAction("graph.edges", VisualItem.STROKECOLOR, ColorLib.gray(200));
    ColorAction arrows = new ColorAction("graph.edges", VisualItem.FILLCOLOR, ColorLib.gray(200));

    // create an action list containing all color assignments
    ActionList color = new ActionList();
    color.add(fill);
    color.add(text);
    color.add(edges);
    color.add(arrows);

    // Add a size action
    DataSizeAction size = new DataSizeAction("graph.nodes", "type", 2, Constants.LINEAR_SCALE);
    vis.putAction("size", size);

    // create an action list with an animated layout
    ActionList layout = new ActionList(Activity.INFINITY);
    layout.add(new ForceDirectedLayout("graph"));
    layout.add(new RepaintAction());

    // add the actions to the visualization
    vis.putAction("color", color);
    vis.putAction("layout", layout);

    // -- 5. the display and interactive controls -------------------------

    Display d = new Display(vis);
    d.setSize(720, 500); // set display size
    // drag individual items around
    d.addControlListener(new DragControl());
    // pan with left-click drag on background
    d.addControlListener(new PanControl());
    // zoom with right-click drag
    d.addControlListener(new ZoomControl());

    // -- 6. launch the visualization -------------------------------------

    // create a new window to hold the visualization
    JFrame frame = new JFrame("IFDS Visualization");
    // ensure application exits when window is closed
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.add(d);
    frame.pack(); // layout components in window
    frame.setVisible(true); // show the window

    // assign the colors
    vis.run("color");
    // start up the animated layout
    vis.run("layout");
  }
  /* (non-Javadoc)
   * @see org.lukep.javavis.visualisation.views.AbstractVisualisationView#visit(org.lukep.javavis.visualisation.visualisers.PrefuseVisualiser, org.lukep.javavis.ui.swing.WorkspaceContext, prefuse.Display)
   */
  @Override
  public void visit(PrefuseVisualiser visualiser, WorkspaceContext wspContext, Display display) {

    display.reset();

    // -- 1. load the data ------------------------------------------------

    Graph graph = new Graph();
    graph.addColumn("type", String.class);
    graph.addColumn("name", String.class);
    graph.addColumn("model", IGenericModelNode.class);
    graph.addColumn("metricMeasurement", double.class);

    // create package vertices
    ProjectModel modelStore = wspContext.getModelStore();
    HashMap<IGenericModelNode, Node> parentNodeMap =
        new HashMap<IGenericModelNode, Node>(modelStore.getPackageMap().size() + 10);
    Node curNode;

    for (PackageModel pkg : modelStore.getPackageMap().values()) {

      // add the package node
      curNode = graph.addNode();
      curNode.setString("type", pkg.getModelTypeName());
      curNode.setString("name", pkg.getSimpleName());
      curNode.set("model", pkg);

      // link to the parent with an edge
      IGenericModelNode parentPackage = pkg.getParent();
      if (parentPackage != null
          && parentPackage instanceof PackageModel
          && parentNodeMap.containsKey(parentPackage)) {

        // link to the parent package with an edge
        graph.addEdge(parentNodeMap.get(parentPackage), curNode);
      }

      parentNodeMap.put(pkg, curNode);
    }

    // create class and method nodes
    Queue<IGenericModelNode> modelQueue =
        new LinkedList<IGenericModelNode>(modelStore.getClassMap().values());
    IGenericModelNode model;

    while (modelQueue.peek() != null) {
      model = modelQueue.remove();

      curNode = graph.addNode();
      curNode.setString("type", model.getModelTypeName());
      curNode.setString("name", model.getSimpleName());
      curNode.set("model", model);

      // add children to iterModels
      if (model.getChildCount() > 0) {
        for (Relationship r : model.getChildren())
          if (r.getRelationshipType() == RelationshipType.ENCLOSED_IN)
            modelQueue.add(r.getTarget());
        parentNodeMap.put(model, curNode);
      }

      // link to the parent package
      if (parentNodeMap.containsKey(model.getParent())) {
        graph.addEdge(parentNodeMap.get(model.getParent()), curNode);
      }

      // grab metric measurement if applicable
      if (model instanceof IMeasurableNode
          && wspContext.getMetric().testAppliesTo(model.getModelTypeName())) {
        curNode.setDouble(
            "metricMeasurement",
            ((IMeasurableNode) (model)).getMetricMeasurement(wspContext.getMetric()).getResult());
      }
    }

    // -- 2. the visualisation --------------------------------------------

    // TODO implement a Visualization cache
    Visualization vis = new Visualization();
    vis.add("graph", graph);
    vis.setInteractive("graph.edges", null, false);

    // -- 3. the renderers and renderer factory ---------------------------

    LabelRenderer r = new LabelRenderer("name");
    r.setRoundedCorner(8, 8);

    vis.setRendererFactory(new DefaultRendererFactory(r));

    // -- 4. the processing actions ---------------------------------------

    // create our nominal color palette
    // pink for classes, baby blue for packages
    int[] palette = ColorLib.getCoolPalette();
    // create a metric palette
    int[] mPalette = ColorLib.getInterpolatedPalette(0xFF00AA6D, 0xFFFFAA6D);

    // TODO replace
    int[] mPalette2 = new int[mPalette.length + 1];
    mPalette2[0] = Color.lightGray.getRGB();
    for (int i = 1; i < mPalette.length; i++) mPalette2[i] = mPalette[i];

    // map nominal data values to colors using our provided palette
    DataColorAction fill =
        new DataColorAction(
            "graph.nodes", "type", Constants.NOMINAL, VisualItem.FILLCOLOR, palette);
    DataColorAction fillMetrics =
        new DataColorAction(
            "graph.nodes",
            "metricMeasurement",
            Constants.NUMERICAL,
            VisualItem.FILLCOLOR,
            mPalette2);
    // use black for node text
    ColorAction text = new ColorAction("graph.nodes", VisualItem.TEXTCOLOR, ColorLib.gray(0));
    // use light grey for edges
    ColorAction edges = new ColorAction("graph.edges", VisualItem.STROKECOLOR, ColorLib.gray(200));

    // create an action list containing all color assignments
    ActionList colour = new ActionList();
    colour.add(fillMetrics);
    colour.add(text);
    colour.add(edges);

    // create an action list with an animated layout
    ActionList layout = new ActionList(Activity.INFINITY);
    // layout.add(new ForceDirectedLayout("graph"));
    layout.add(new NodeLinkTreeLayout("graph"));
    layout.add(new RepaintAction());

    // add the actions to the visualisation
    vis.putAction("colour", colour);
    vis.putAction("layout", layout);

    // -- 5. the display and interactive controls -------------------------

    display.setVisualization(vis);

    // -- 6. launch the visualization -------------------------------------

    vis.run("colour");
    vis.run("layout");
  }