package ui.smallstep; import common.ProofNode; import common.ProofRule; import java.awt.Color; import java.awt.Dimension; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.Rectangle; import javax.swing.JViewport; import javax.swing.Scrollable; import smallstep.SmallStepProofNode; import ui.AbstractNode; import ui.AbstractView; public class SmallStepView extends AbstractView implements Scrollable { private Dimension requiredSize = new Dimension (); private Dimension availableSize = new Dimension(); public SmallStepView () { super(); this.setLayout(null); } public void setAvailableSize (Dimension size) { this.availableSize = size; relayout(); } private void determineCenter () { int center = 0; SmallStepNode node = (SmallStepNode)rootNode; node.prepareRuleSize(); center = node.getRuleSize().width; while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); node.prepareRuleSize(); Dimension size = node.getRuleSize(); if (size.width > center) { center = size.width; } } SmallStepNode.setCenter(center); } private void determineNodeExpressionSize () { SmallStepNode node = (SmallStepNode)rootNode; node.prepareExpressionSize(this.availableSize.width - SmallStepNode.getCenter() - 50); while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); node.prepareExpressionSize(this.availableSize.width - SmallStepNode.getCenter() - 50); } } private void determineBounds() { SmallStepNode node = (SmallStepNode)rootNode; int newY = node.setTop (25); while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); newY = node.setTop(newY); } } private void determinePreferredSize() { int maxWidth = 0, currentWidth = 0; SmallStepNode node = (SmallStepNode)rootNode; maxWidth = currentWidth = node.getX() + node.getWidth(); while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); currentWidth = node.getX() + node.getWidth(); if (currentWidth > maxWidth) { maxWidth = currentWidth; } } Dimension size = new Dimension (maxWidth + 25, node.getY () + node.getHeight () + 25); setPreferredSize (size); setSize(size); } private void determineButtons() { SmallStepNode node = (SmallStepNode)rootNode; node.placeMenuButtons(); while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); node.placeMenuButtons(); } } private int countNodes() { int numNodes = 1; AbstractNode aNode = rootNode; while (aNode.hasChildren()) { aNode = aNode.getFirstChild(); numNodes++; } return numNodes; } private void addNodes() { removeAll(); SmallStepNode node = (SmallStepNode)rootNode; node.reset(); add(node); while (node.hasChildren()) { node = (SmallStepNode)node.getFirstChild(); node.reset(); add(node); } } protected void relayout() { addNodes(); determineCenter(); doLayouting(); repaint(); } protected void doLayouting() { this.requiredSize.width = 0; this.requiredSize.height = 0; determineNodeExpressionSize(); determineBounds(); determineButtons(); determinePreferredSize(); } protected AbstractNode createNode (ProofNode node) { return new SmallStepNode (this, (SmallStepProofNode)node); } /** * Paints the content of the SmallStepView */ public void paintComponent (Graphics g) { g.setColor(Color.WHITE); g.fillRect(0, 0, getWidth(), getHeight()); } protected void nodeAdded (AbstractNode node) { if (getParent () instanceof JViewport) { JViewport vp = (JViewport)getParent(); // the viewport scroll to the rightmost position of // the bounds rectangle. // Use a hardcoded width of 10 pixels to prevent the // viewport from scrolling to the right. // // look like the visible rect is relative to the // current visible rect Rectangle bounds = node.getBounds(); bounds.x = 0; bounds.width = 10; vp.scrollRectToVisible(bounds); } } public Dimension getPreferredScrollableViewportSize() { return getPreferredSize(); } public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction) { return 75; } public boolean getScrollableTracksViewportHeight() { return false; } public boolean getScrollableTracksViewportWidth() { return false; } public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction) { return 25; } }