/** @see prefuse.action.Action#run(double) */ public void run(double frac) { Graph g = (Graph) m_vis.getGroup(m_group); initSchema(g.getNodes()); m_origin = getLayoutAnchor(); NodeItem n = getLayoutRoot(); Params np = (Params) n.get(PARAMS); // calc relative widths and maximum tree depth // performs one pass over the tree m_maxDepth = 0; calcAngularWidth(n, 0); if (m_autoScale) setScale(getLayoutBounds()); if (!m_setTheta) calcAngularBounds(n); // perform the layout if (m_maxDepth > 0) layout(n, m_radiusInc, m_theta1, m_theta2); // update properties of the root node setX(n, null, m_origin.getX()); setY(n, null, m_origin.getY()); np.angle = m_theta2 - m_theta1; }
public void process(VisualItem item, double frac) { // if (item instanceof Node ){ // int dp = item.getDepth()+1; // double incfactor = NodeItem tn = ((EdgeItem) item).getTargetItem(); int nc = tn.getInt(NODECOUNT); if (nc == 1) { System.err.println("hiding___" + item); PrefuseLib.updateVisible(tn, false); PrefuseLib.updateVisible(item, false); } }
/* * Test method for 'prefuse.Visualization.getSourceTuple(VisualItem)' */ @Test public void testGetSourceTuple() { Assert.assertEquals(m_t0, m_vis.getSourceTuple(m_vt0)); Assert.assertEquals(m_n0, m_vis.getSourceTuple(m_vn0)); Assert.assertEquals(m_t0, m_vt0.getSourceTuple()); Assert.assertEquals(m_n0, m_vn0.getSourceTuple()); }
/* * Test method for 'prefuse.Visualization.getSourceData(String)' */ @Test public void testGetSourceData() { Assert.assertEquals(m_t, m_vis.getSourceData("t")); Assert.assertEquals(m_t, m_vt0.getSourceData()); Assert.assertEquals(m_g, m_vis.getSourceData("g")); Assert.assertEquals(m_g.getNodeTable(), m_vis.getSourceData("g.nodes")); Assert.assertEquals(m_g.getEdgeTable(), m_vis.getSourceData("g.edges")); Assert.assertEquals(m_g.getNodeTable(), m_vn0.getSourceData()); }
/** * Compute the layout. * * @param n the root of the current subtree under consideration * @param r the radius, current distance from the center * @param theta1 the start (in radians) of this subtree's angular region * @param theta2 the end (in radians) of this subtree's angular region */ protected void layout(NodeItem n, double r, double theta1, double theta2) { double dtheta = (theta2 - theta1); double dtheta2 = dtheta / 2.0; double width = ((Params) n.get(PARAMS)).width; double cfrac, nfrac = 0.0; Iterator childIter = sortedChildren(n); while (childIter != null && childIter.hasNext()) { NodeItem c = (NodeItem) childIter.next(); Params cp = (Params) c.get(PARAMS); cfrac = cp.width / width; if (c.isExpanded() && c.getChildCount() > 0) { layout(c, r + m_radiusInc, theta1 + nfrac * dtheta, theta1 + (nfrac + cfrac) * dtheta); } setPolarLocation(c, n, r, theta1 + nfrac * dtheta + cfrac * dtheta2); cp.angle = cfrac * dtheta; nfrac += cfrac; } }
// TODO: cache required protected int getEdgeIndex(EdgeItem e) { if (isIgnored(e)) { return -1; } NodeItem sourceItem = e.getSourceItem(); NodeItem targetItem = e.getTargetItem(); Iterator<EdgeItem> edges = sourceItem.edges(); // number of equal edges = same target and source int equalEdges = 0; // number of nearequal edges = same nodes, but any order target and source int sameEdges = 0; int edgeIndex = 0; int row = e.getRow(); while (edges.hasNext()) { EdgeItem edge = edges.next(); int edgeRow = edge.getRow(); if (isIgnored(edge)) { continue; } if (edge.getSourceItem() == sourceItem && edge.getTargetItem() == targetItem) { if (row == edgeRow) { edgeIndex = equalEdges; } equalEdges++; sameEdges++; } else if (edge.getSourceItem() == targetItem && edge.getTargetItem() == sourceItem) { sameEdges++; } } // draw the line straight if we found one edge if (lineForSingleEdge && edgeIndex == 0 && sameEdges == 1) { return -1; } else if (sameEdges > 1) { edgeIndex++; } return edgeIndex; }
/** * Computes relative measures of the angular widths of each expanded subtree. Node diameters are * taken into account to improve space allocation for variable-sized nodes. * * <p>This method also updates the base angle value for nodes to ensure proper ordering of nodes. */ private double calcAngularWidth(NodeItem n, int d) { if (d > m_maxDepth) m_maxDepth = d; double aw = 0; Rectangle2D bounds = n.getBounds(); double w = bounds.getWidth(), h = bounds.getHeight(); double diameter = d == 0 ? 0 : Math.sqrt(w * w + h * h) / d; if (n.isExpanded() && n.getChildCount() > 0) { Iterator childIter = n.children(); while (childIter.hasNext()) { NodeItem c = (NodeItem) childIter.next(); aw += calcAngularWidth(c, d + 1); } aw = Math.max(diameter, aw); } else { aw = diameter; } ((Params) n.get(PARAMS)).width = aw; return aw; }
/** * Calculates the angular bounds of the layout, attempting to preserve the angular orientation of * the display across transitions. */ private void calcAngularBounds(NodeItem r) { if (m_prevRoot == null || !m_prevRoot.isValid() || r == m_prevRoot) { m_prevRoot = r; return; } // try to find previous parent of root NodeItem p = m_prevRoot; while (true) { NodeItem pp = (NodeItem) p.getParent(); if (pp == r) { break; } else if (pp == null) { m_prevRoot = r; return; } p = pp; } // compute offset due to children's angular width double dt = 0; Iterator iter = sortedChildren(r); while (iter.hasNext()) { Node n = (Node) iter.next(); if (n == p) break; dt += ((Params) n.get(PARAMS)).width; } double rw = ((Params) r.get(PARAMS)).width; double pw = ((Params) p.get(PARAMS)).width; dt = -MathLib.TWO_PI * (dt + pw / 2) / rw; // set angular bounds m_theta1 = dt + Math.atan2(p.getY() - r.getY(), p.getX() - r.getX()); m_theta2 = m_theta1 + MathLib.TWO_PI; m_prevRoot = r; }
public Display getGraphDisplay( GraphLayoutType glType, final ExperimentPanel expPanel, String highlightName) { Display display = new Display(); int X = expPanel.getDetailWidth(); int Y = expPanel.getDetailHeight(); display.setSize(X, Y); // set display size // display.setHighQuality(true); // display.setPreferredSize(new Dimension(600,600)); display.addControlListener(new DragControl()); // drag items around display.addControlListener(new PanControl()); // pan with background left-drag display.addControlListener(new WheelZoomControl()); // zoom with vertical right-drag display.addControlListener( new ZoomToFitControl(Visualization.ALL_ITEMS, 50, 500, Control.MIDDLE_MOUSE_BUTTON)); display.addControlListener(new NeighborHighlightControl()); Visualization vis = new Visualization(); if (clusterGraph == null) { clusterGraph = this.toGraph(); } vis.add("graph", clusterGraph); LabelRenderer r = new LabelRenderer("name"); r.setHorizontalAlignment(Constants.CENTER); // r.setRoundedCorner(8, 8); // round the corners DefaultRendererFactory rf = new DefaultRendererFactory(r); rf.setDefaultEdgeRenderer(new EdgeRenderer(Constants.EDGE_TYPE_CURVE)); vis.setRendererFactory(rf); int[] palette = new int[] {ColorLib.rgb(255, 180, 180), ColorLib.rgb(190, 190, 255)}; DataColorAction fill = new DataColorAction( "graph.nodes", "type", Constants.NOMINAL, VisualItem.FILLCOLOR, palette); fill.add(VisualItem.FIXED, ColorLib.rgb(255, 100, 100)); fill.add(VisualItem.HIGHLIGHT, ColorLib.rgb(255, 200, 125)); int[] text_palette = new int[] {ColorLib.gray(0), ColorLib.gray(255)}; DataColorAction text = new DataColorAction( "graph.nodes", "indeterminate", Constants.NUMERICAL, VisualItem.TEXTCOLOR, text_palette); // ColorAction text = new ColorAction("graph.nodes", VisualItem.TEXTCOLOR, ColorLib.gray(0)); ColorAction edges = new ColorAction("graph.edges", VisualItem.STROKECOLOR, ColorLib.gray(200)); ActionList color = new ActionList(Activity.INFINITY); color.add(text); color.add(fill); color.add(edges); color.add(new RepaintAction()); if (highlightName != null) { String pred = "name='" + highlightName + "'"; Iterator iter = vis.items("graph.nodes", ExpressionParser.predicate(pred)); while (iter.hasNext()) { NodeItem ni = (NodeItem) iter.next(); highlightedItem = ni; ni.setFixed(true); Iterator iterEdge = ni.edges(); while (iterEdge.hasNext()) { EdgeItem eItem = (EdgeItem) iterEdge.next(); NodeItem nItem = eItem.getAdjacentItem(ni); if (eItem.isVisible()) { eItem.setHighlighted(true); nItem.setHighlighted(true); } } } } ActionList layout = new ActionList(); switch (glType) { case BALLOON_TREE: layout.add(new BalloonTreeLayout("graph")); break; case FORCE_DIRECTED: layout = new ActionList(Activity.INFINITY); layout.add(new ForceDirectedLayout("graph")); break; case NODE_LINK_TREE: layout.add(new NodeLinkTreeLayout("graph")); break; case RADIAL_TREE: layout.add(new RadialTreeLayout("graph")); break; } // layout.add(fill); layout.add(new RepaintAction()); vis.putAction("color", color); vis.putAction("layout", layout); display.setVisualization(vis); vis.run("color"); vis.run("layout"); // Rectangle2D bounds = vis.getBounds(Visualization.ALL_ITEMS); // GraphicsLib.expand(bounds, 50 + (int)(1/display.getScale())); // DisplayLib.fitViewToBounds(display,bounds,1); // vis.runAfter("layout",1000); Control shutoffHighlight = new HoverActionControl("color") { // public void itemEntered(VisualItem item, MouseEvent evt) { // } public void itemExited(VisualItem item, MouseEvent evt) { if (highlightedItem != null) { highlightedItem.setFixed(false); Iterator iterEdge = highlightedItem.edges(); while (iterEdge.hasNext()) { EdgeItem eItem = (EdgeItem) iterEdge.next(); NodeItem nItem = eItem.getAdjacentItem(highlightedItem); if (eItem.isVisible()) { eItem.setHighlighted(false); nItem.setHighlighted(false); } } highlightedItem = null; } } }; display.addControlListener(shutoffHighlight); Control selectItem = new FocusControl() { public void itemClicked(VisualItem item, MouseEvent evt) { if (item.isInGroup("graph.nodes")) { if (item.getString("type").equals("peptide")) { Peptide pep = minPeptides.get(item.getString("name")); expPanel.showPeptide(pep, true); } if (item.getString("type").equals("protein")) { Protein pro = minProteins.get(item.getString("name")); expPanel.showProtein(pro, true); } String pred = "name='" + item.getString("name") + "'"; Iterator iter = item.getVisualization().items("graph.nodes", ExpressionParser.predicate(pred)); while (iter.hasNext()) { NodeItem ni = (NodeItem) iter.next(); highlightedItem = ni; ni.setFixed(true); Iterator iterEdge = ni.edges(); while (iterEdge.hasNext()) { EdgeItem eItem = (EdgeItem) iterEdge.next(); NodeItem nItem = eItem.getAdjacentItem(ni); if (eItem.isVisible()) { eItem.setHighlighted(true); nItem.setHighlighted(true); } } } } } }; display.addControlListener(selectItem); final JPopupMenu menu = new JPopupMenu(); // Create and add a menu item // JMenuItem printItem = new JMenuItem("Print This"); // printItem.addActionListener(new java.awt.event.ActionListener() { // public void actionPerformed(java.awt.event.ActionEvent evt) { // PrintUtilities.printComponent(display); // } // }); // menu.add(printItem); // Set the component to show the popup menu display.addMouseListener( new MouseAdapter() { public void mousePressed(MouseEvent evt) { if (evt.isPopupTrigger()) { menu.show(evt.getComponent(), evt.getX(), evt.getY()); } } public void mouseReleased(MouseEvent evt) { if (evt.isPopupTrigger()) { menu.show(evt.getComponent(), evt.getX(), evt.getY()); } } }); display.pan(X / 2.0, Y / 2.0); return display; }
private Iterator sortedChildren(final NodeItem n) { double base = 0; // update base angle for node ordering NodeItem p = (NodeItem) n.getParent(); if (p != null) { base = normalize(Math.atan2(p.getY() - n.getY(), p.getX() - n.getX())); } int cc = n.getChildCount(); if (cc == 0) return null; NodeItem c = (NodeItem) n.getFirstChild(); if (!c.isStartVisible()) { // use natural ordering for previously invisible nodes return n.children(); } double angle[] = new double[cc]; final int idx[] = new int[cc]; for (int i = 0; i < cc; ++i, c = (NodeItem) c.getNextSibling()) { idx[i] = i; angle[i] = normalize(-base + Math.atan2(c.getY() - n.getY(), c.getX() - n.getX())); } ArrayLib.sort(angle, idx); // return iterator over sorted children return new Iterator() { int cur = 0; public Object next() { return n.getChild(idx[cur++]); } public boolean hasNext() { return cur < idx.length; } public void remove() { throw new UnsupportedOperationException(); } }; }