Revision: 962
Author: allain.lalonde
Date: Thu Jan 28 07:04:37 2010
Log: Made PSwing.setVisible lazily call its component's setVisible method
depending on its current visibility. This should stop the stack overflow
being experienced by Chris Malley. Since I have been unable to reproduce
it, I can't test it.
http://code.google.com/p/piccolo2d/source/detail?r=962
Modified:
/piccolo2d.java/trunk/extras/src/main/java/edu/umd/cs/piccolox/pswing/PSwing.java
/piccolo2d.java/trunk/extras/src/test/java/edu/umd/cs/piccolox/pswing/PSwingTest.java
=======================================
---
/piccolo2d.java/trunk/extras/src/main/java/edu/umd/cs/piccolox/pswing/PSwing.java
Wed Jan 27 13:24:26 2010
+++
/piccolo2d.java/trunk/extras/src/main/java/edu/umd/cs/piccolox/pswing/PSwing.java
Thu Jan 28 07:04:37 2010
@@ -442,7 +442,10 @@
/** {...@inheritdoc} */
public void setVisible(final boolean visible) {
super.setVisible(visible);
- component.setVisible(visible);
+
+ if (component.isVisible() != visible) {
+ component.setVisible(visible);
+ }
}
/**
=======================================
---
/piccolo2d.java/trunk/extras/src/test/java/edu/umd/cs/piccolox/pswing/PSwingTest.java
Wed Jan 27 13:34:51 2010
+++
/piccolo2d.java/trunk/extras/src/test/java/edu/umd/cs/piccolox/pswing/PSwingTest.java
Thu Jan 28 07:04:37 2010
@@ -44,297 +44,300 @@
import edu.umd.cs.piccolo.util.PPaintContext;
public class PSwingTest extends TestCase {
- public void setUp() {
- RepaintManager.setCurrentManager(new PSwingRepaintManager());
- }
-
- public void testConstructorFailsOnNullComponent() {
- try {
- new PSwing(null);
- }
- catch (final NullPointerException e) {
- // expected
- }
- }
-
- public void testPSwingRegistersItselfWithComponent() {
- final JPanel panel = new JPanel();
- final PSwing pSwing = new PSwing(panel);
-
- assertEquals(pSwing,
panel.getClientProperty(PSwing.PSWING_PROPERTY));
- }
-
- public void testGetComponentReturnsValidComponent() {
- final JPanel panel = new JPanel();
- final PSwing pSwing = new PSwing(panel);
- assertEquals(panel, pSwing.getComponent());
- }
-
- public void testPSwingResizesItselfWhenComponentIsResized() {
- final boolean[] reshaped = new boolean[1];
- final JPanel panel = new JPanel();
-
- new PSwing(panel) {
- public void updateBounds() {
- super.updateBounds();
-
- reshaped[0] = true;
- }
- };
- panel.setSize(100, 100);
- assertTrue(reshaped[0]);
- }
-
- public void testPSwingDelegatesPaintingToItsComponent() throws
IOException {
- final JPanel panel = new JPanel();
- final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
- panel.setBackground(Color.RED);
- panel.setPreferredSize(new Dimension(100, 100));
-
- final BufferedImage img = pSwing.paintComponent();
-
- assertEquals(Color.RED.getRGB(), img.getRGB(50, 50));
- }
-
- public void testHidingComponentHidesPSwing() {
- final JPanel panel = new JPanel();
- final PSwing pSwing = new PSwing(panel);
- panel.setPreferredSize(new Dimension(100, 100));
- pSwing.setBounds(0, 0, 00, 100);
- panel.setVisible(false);
-
- // Wow, do I hate this chunk of code. Turns out that the event
dispatch
- // thread needs time to push the component hidden method before
this
- // test passes
- // There has to be a way of forcing this without a sleep
- assertDelayedSuccess("setting component to invisible did not
reflect in associated PSwing", 500,
- new Predicate() {
-
- public boolean isTrue() {
- return !pSwing.getVisible();
- }
- });
-
- }
-
- public void
testAddingSwingComponentToWrappedHierarchyMakesItNotDoubleBuffer() {
- final JPanel panel = new JPanel();
- final PSwing pSwing = new PSwing(panel);
- final JComponent child = new JLabel("Test Component");
- child.setDoubleBuffered(true);
- panel.add(child);
- assertFalse(child.isDoubleBuffered());
- }
-
- public void assertDelayedSuccess(String message, int delay, Predicate
p) {
- int remainingTries = delay / 50;
- while (remainingTries > 0) {
- if (p.isTrue()) {
- return;
- }
- remainingTries--;
- try {
- Thread.sleep(50);
- }
- catch (InterruptedException e) {
- // do nothing
- }
- }
- fail(message);
- }
-
- public void assertDelayedSuccess(int delay, Predicate p) {
- assertDelayedSuccess("Failed asserting delayed success", delay, p);
- }
-
- private interface Predicate {
- boolean isTrue();
- }
-
- public void testHidingPNodeHidesComponent() {
- final JPanel panel = new JPanel();
- final PSwing pSwing = new PSwing(panel);
- pSwing.setVisible(false);
- assertFalse(panel.isVisible());
- }
-
- public void testPaintTooSmallPaintsGreek() {
- final JPanel panel = new JPanel();
- panel.setBounds(0, 0, 100, 100);
- final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
-
- BufferedImage image = new BufferedImage(100, 100,
BufferedImage.TYPE_INT_RGB);
- Graphics2D graphics = image.createGraphics();
- graphics.setTransform(AffineTransform.getScaleInstance(0.01,
0.01));
- PPaintContext paintContext = new PPaintContext(graphics);
-
- pSwing.paint(paintContext);
- assertTrue(pSwing.isPaintedGreek());
- assertFalse(pSwing.isPaintedComponent());
-
- }
-
- public void testPaintBigPaintsComponent() {
- final JPanel panel = new JPanel();
- panel.setBounds(0, 0, 100, 100);
- final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
-
- BufferedImage image = new BufferedImage(100, 100,
BufferedImage.TYPE_INT_RGB);
- Graphics2D graphics = image.createGraphics();
- graphics.setTransform(AffineTransform.getScaleInstance(5, 5));
- PPaintContext paintContext = new PPaintContext(graphics);
-
- pSwing.paint(paintContext);
- assertFalse(pSwing.isPaintedGreek());
- assertTrue(pSwing.isPaintedComponent());
- }
-
- public void testGreekThresholdIsHonoured() {
- final JPanel panel = new JPanel();
- panel.setBounds(0, 0, 100, 100);
- final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
- pSwing.setGreekThreshold(2);
- BufferedImage image = new BufferedImage(100, 100,
BufferedImage.TYPE_INT_RGB);
- Graphics2D graphics = image.createGraphics();
- PPaintContext paintContext = new PPaintContext(graphics);
-
- pSwing.paint(paintContext);
- assertTrue(pSwing.isPaintedGreek());
- assertFalse(pSwing.isPaintedComponent());
- }
-
- public void testGreekThresholdIsPersisted() {
- final JPanel panel = new JPanel();
- final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
- pSwing.setGreekThreshold(2);
- assertEquals(2, pSwing.getGreekThreshold(), Double.MIN_VALUE);
- pSwing.setGreekThreshold(0.5);
- assertEquals(0.5, pSwing.getGreekThreshold(), Double.MIN_VALUE);
- }
-
- public void testAssertSettingJLabelWidthTooSmallGrowsIt() {
- final JLabel label = new JLabel("Hello");
- PSwingCanvas canvas = new PSwingCanvas();
- canvas.setBounds(0, 0, 100, 100);
- final MockPaintingPSwing swing = new MockPaintingPSwing(label);
- assertDelayedSuccess(500,
- new Predicate() {
-
- public boolean isTrue() {
- return label.getMinimumSize().getWidth() != 0;
- }
- });
- swing.setWidth(10);
- canvas.getLayer().addChild(swing);
- canvas.doLayout();
- // While paint, it uses the graphics element to determine the
font's
- // display size and hence determine minimum size of JLabel.
- swing.paint();
-
- assertFalse(10 == swing.getWidth());
- }
-
- public void testAssertSettingJButtonWidthTooSmallGrowsIt() {
- JButton label = new JButton("Hello");
- PSwingCanvas canvas = new PSwingCanvas();
- canvas.setBounds(0, 0, 100, 100);
- MockPaintingPSwing swing = new MockPaintingPSwing(label);
- assertFalse(label.getMinimumSize().getWidth() == 0);
- swing.setWidth(10);
- canvas.getLayer().addChild(swing);
- canvas.doLayout();
- // While paint, it uses the graphics element to determine the
font's
- // display size and hence determine minimum size of JLabel.
- swing.paint();
- assertFalse(10 == swing.getWidth());
- }
-
- public void
testPSwingAttachesItselfToItsCanvasWhenAddedToItsSceneGraph() {
- PSwingCanvas canvas1 = new PSwingCanvas();
- PSwing label = new PSwing(new JLabel("Hello"));
- assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
- canvas1.getLayer().addChild(label);
- assertEquals(1, canvas1.getSwingWrapper().getComponentCount());
- }
-
- public void testPSwingRemovesItselfFromItsCanvasWhenRemovedFromScene()
{
- PSwingCanvas canvas1 = new PSwingCanvas();
- PSwing label = new PSwing(new JLabel("Hello"));
- canvas1.getLayer().addChild(label);
- assertEquals(1, canvas1.getSwingWrapper().getComponentCount());
- label.removeFromParent();
- assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
- }
-
- public void testPSwingReattachesItselfWhenMovedFromCanvasToCanvas() {
- PSwingCanvas canvas1 = new PSwingCanvas();
- PSwingCanvas canvas2 = new PSwingCanvas();
- PSwing label = new PSwing(new JLabel("Hello"));
- canvas1.getLayer().addChild(label);
- canvas2.getLayer().addChild(label);
- assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
- assertEquals(1, canvas2.getSwingWrapper().getComponentCount());
- }
-
- public void testPSwingRegistersWithCanvasThroughoutItsLifeCycle() {
- PSwingCanvas canvas = new PSwingCanvas();
- PSwing label = new PSwing(new JLabel("Hello"));
-
- canvas.getLayer().addChild(label);
- assertEquals(1, canvas.getSwingWrapper().getComponentCount());
-
- label.removeFromParent();
- assertEquals(0, canvas.getSwingWrapper().getComponentCount());
-
- canvas.getLayer().addChild(label);
- assertEquals(1, canvas.getSwingWrapper().getComponentCount());
- }
-
- public class MockPaintingPSwing extends PSwing {
- private boolean paintedGreek;
- private boolean paintedComponent;
-
- public MockPaintingPSwing(JComponent component) {
- super(component);
- }
-
- public void paintOnto(BufferedImage image) {
- PPaintContext paintContext = new
PPaintContext(image.createGraphics());
- paint(paintContext);
- }
-
- public BufferedImage paint() {
- BufferedImage image = new BufferedImage((int) getWidth(),
(int) getHeight(), BufferedImage.TYPE_INT_RGB);
- paintOnto(image);
- return image;
- }
-
- public BufferedImage paintComponent() {
- BufferedImage image = new BufferedImage((int) getWidth(),
(int) getHeight(), BufferedImage.TYPE_INT_RGB);
- paintComponentOnto(image);
- return image;
- }
-
- public void paintComponentOnto(BufferedImage image) {
- paint(image.createGraphics());
- }
-
- public void paint(Graphics2D paintContext) {
- super.paint(paintContext);
- paintedComponent = true;
- }
-
- public void paintAsGreek(Graphics2D paintContext) {
- super.paintAsGreek(paintContext);
- paintedGreek = true;
- }
-
- public boolean isPaintedGreek() {
- return paintedGreek;
- }
-
- public boolean isPaintedComponent() {
- return paintedComponent;
- }
- }
-}
+ public void setUp() {
+ RepaintManager.setCurrentManager(new PSwingRepaintManager());
+ }
+
+ public void testConstructorFailsOnNullComponent() {
+ try {
+ new PSwing(null);
+ } catch (final NullPointerException e) {
+ // expected
+ }
+ }
+
+ public void testPSwingRegistersItselfWithComponent() {
+ final JPanel panel = new JPanel();
+ final PSwing pSwing = new PSwing(panel);
+
+ assertEquals(pSwing,
panel.getClientProperty(PSwing.PSWING_PROPERTY));
+ }
+
+ public void testGetComponentReturnsValidComponent() {
+ final JPanel panel = new JPanel();
+ final PSwing pSwing = new PSwing(panel);
+ assertEquals(panel, pSwing.getComponent());
+ }
+
+ public void testPSwingResizesItselfWhenComponentIsResized() {
+ final boolean[] reshaped = new boolean[1];
+ final JPanel panel = new JPanel();
+
+ new PSwing(panel) {
+ public void updateBounds() {
+ super.updateBounds();
+
+ reshaped[0] = true;
+ }
+ };
+ panel.setSize(100, 100);
+ assertTrue(reshaped[0]);
+ }
+
+ public void testPSwingDelegatesPaintingToItsComponent() throws
IOException {
+ final JPanel panel = new JPanel();
+ final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
+ panel.setBackground(Color.RED);
+ panel.setPreferredSize(new Dimension(100, 100));
+
+ final BufferedImage img = pSwing.paintComponent();
+
+ assertEquals(Color.RED.getRGB(), img.getRGB(50, 50));
+ }
+
+ public void testHidingComponentHidesPSwing() {
+ final JPanel panel = new JPanel();
+ final PSwing pSwing = new PSwing(panel);
+ panel.setPreferredSize(new Dimension(100, 100));
+ pSwing.setBounds(0, 0, 00, 100);
+ panel.setVisible(false);
+
+ // Wow, do I hate this chunk of code. Turns out that the event
dispatch
+ // thread needs time to push the component hidden method before
this
+ // test passes
+ // There has to be a way of forcing this without a sleep
+ assertDelayedSuccess(
+ "setting component to invisible did not reflect in
associated PSwing",
+ 500, new Predicate() {
+
+ public boolean isTrue() {
+ return !pSwing.getVisible();
+ }
+ });
+ }
+
+ public void testHidingPNodeHidesComponent() {
+ final JPanel panel = new JPanel();
+ final PSwing pSwing = new PSwing(panel);
+ pSwing.setVisible(false);
+ assertFalse(panel.isVisible());
+ }
+
+ public void
testAddingSwingComponentToWrappedHierarchyMakesItNotDoubleBuffer() {
+ final JPanel panel = new JPanel();
+ final PSwing pSwing = new PSwing(panel);
+ final JComponent child = new JLabel("Test Component");
+ child.setDoubleBuffered(true);
+ panel.add(child);
+ assertFalse(child.isDoubleBuffered());
+ }
+
+ public void assertDelayedSuccess(String message, int delay, Predicate
p) {
+ int remainingTries = delay / 50;
+ while (remainingTries > 0) {
+ if (p.isTrue()) {
+ return;
+ }
+ remainingTries--;
+ try {
+ Thread.sleep(50);
+ } catch (InterruptedException e) {
+ // do nothing
+ }
+ }
+ fail(message);
+ }
+
+ public void assertDelayedSuccess(int delay, Predicate p) {
+ assertDelayedSuccess("Failed asserting delayed success", delay,
p);
+ }
+
+ private interface Predicate {
+ boolean isTrue();
+ }
+
+ public void testPaintTooSmallPaintsGreek() {
+ final JPanel panel = new JPanel();
+ panel.setBounds(0, 0, 100, 100);
+ final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
+
+ BufferedImage image = new BufferedImage(100, 100,
+ BufferedImage.TYPE_INT_RGB);
+ Graphics2D graphics = image.createGraphics();
+ graphics.setTransform(AffineTransform.getScaleInstance(0.01,
0.01));
+ PPaintContext paintContext = new PPaintContext(graphics);
+
+ pSwing.paint(paintContext);
+ assertTrue(pSwing.isPaintedGreek());
+ assertFalse(pSwing.isPaintedComponent());
+
+ }
+
+ public void testPaintBigPaintsComponent() {
+ final JPanel panel = new JPanel();
+ panel.setBounds(0, 0, 100, 100);
+ final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
+
+ BufferedImage image = new BufferedImage(100, 100,
+ BufferedImage.TYPE_INT_RGB);
+ Graphics2D graphics = image.createGraphics();
+ graphics.setTransform(AffineTransform.getScaleInstance(5, 5));
+ PPaintContext paintContext = new PPaintContext(graphics);
+
+ pSwing.paint(paintContext);
+ assertFalse(pSwing.isPaintedGreek());
+ assertTrue(pSwing.isPaintedComponent());
+ }
+
+ public void testGreekThresholdIsHonoured() {
+ final JPanel panel = new JPanel();
+ panel.setBounds(0, 0, 100, 100);
+ final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
+ pSwing.setGreekThreshold(2);
+ BufferedImage image = new BufferedImage(100, 100,
+ BufferedImage.TYPE_INT_RGB);
+ Graphics2D graphics = image.createGraphics();
+ PPaintContext paintContext = new PPaintContext(graphics);
+
+ pSwing.paint(paintContext);
+ assertTrue(pSwing.isPaintedGreek());
+ assertFalse(pSwing.isPaintedComponent());
+ }
+
+ public void testGreekThresholdIsPersisted() {
+ final JPanel panel = new JPanel();
+ final MockPaintingPSwing pSwing = new MockPaintingPSwing(panel);
+ pSwing.setGreekThreshold(2);
+ assertEquals(2, pSwing.getGreekThreshold(), Double.MIN_VALUE);
+ pSwing.setGreekThreshold(0.5);
+ assertEquals(0.5, pSwing.getGreekThreshold(), Double.MIN_VALUE);
+ }
+
+ public void testAssertSettingJLabelWidthTooSmallGrowsIt() {
+ final JLabel label = new JLabel("Hello");
+ PSwingCanvas canvas = new PSwingCanvas();
+ canvas.setBounds(0, 0, 100, 100);
+ final MockPaintingPSwing swing = new MockPaintingPSwing(label);
+ assertDelayedSuccess(500, new Predicate() {
+
+ public boolean isTrue() {
+ return label.getMinimumSize().getWidth() != 0;
+ }
+ });
+ swing.setWidth(10);
+ canvas.getLayer().addChild(swing);
+ canvas.doLayout();
+ // While paint, it uses the graphics element to determine the
font's
+ // display size and hence determine minimum size of JLabel.
+ swing.paint();
+
+ assertFalse(10 == swing.getWidth());
+ }
+
+ public void testAssertSettingJButtonWidthTooSmallGrowsIt() {
+ JButton label = new JButton("Hello");
+ PSwingCanvas canvas = new PSwingCanvas();
+ canvas.setBounds(0, 0, 100, 100);
+ MockPaintingPSwing swing = new MockPaintingPSwing(label);
+ assertFalse(label.getMinimumSize().getWidth() == 0);
+ swing.setWidth(10);
+ canvas.getLayer().addChild(swing);
+ canvas.doLayout();
+ // While paint, it uses the graphics element to determine the
font's
+ // display size and hence determine minimum size of JLabel.
+ swing.paint();
+ assertFalse(10 == swing.getWidth());
+ }
+
+ public void testPSwingAttachesItselfToItsCanvasWhenAddedToItsSceneGraph()
{
+ PSwingCanvas canvas1 = new PSwingCanvas();
+ PSwing label = new PSwing(new JLabel("Hello"));
+ assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
+ canvas1.getLayer().addChild(label);
+ assertEquals(1, canvas1.getSwingWrapper().getComponentCount());
+ }
+
+ public void testPSwingRemovesItselfFromItsCanvasWhenRemovedFromScene() {
+ PSwingCanvas canvas1 = new PSwingCanvas();
+ PSwing label = new PSwing(new JLabel("Hello"));
+ canvas1.getLayer().addChild(label);
+ assertEquals(1, canvas1.getSwingWrapper().getComponentCount());
+ label.removeFromParent();
+ assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
+ }
+
+ public void testPSwingReattachesItselfWhenMovedFromCanvasToCanvas() {
+ PSwingCanvas canvas1 = new PSwingCanvas();
+ PSwingCanvas canvas2 = new PSwingCanvas();
+ PSwing label = new PSwing(new JLabel("Hello"));
+ canvas1.getLayer().addChild(label);
+ canvas2.getLayer().addChild(label);
+ assertEquals(0, canvas1.getSwingWrapper().getComponentCount());
+ assertEquals(1, canvas2.getSwingWrapper().getComponentCount());
+ }
+
+ public void testPSwingRegistersWithCanvasThroughoutItsLifeCycle() {
+ PSwingCanvas canvas = new PSwingCanvas();
+ PSwing label = new PSwing(new JLabel("Hello"));
+
+ canvas.getLayer().addChild(label);
+ assertEquals(1, canvas.getSwingWrapper().getComponentCount());
+
+ label.removeFromParent();
+ assertEquals(0, canvas.getSwingWrapper().getComponentCount());
+
+ canvas.getLayer().addChild(label);
+ assertEquals(1, canvas.getSwingWrapper().getComponentCount());
+ }
+
+ public class MockPaintingPSwing extends PSwing {
+ private boolean paintedGreek;
+ private boolean paintedComponent;
+
+ public MockPaintingPSwing(JComponent component) {
+ super(component);
+ }
+
+ public void paintOnto(BufferedImage image) {
+ PPaintContext paintContext = new PPaintContext(image
+ .createGraphics());
+ paint(paintContext);
+ }
+
+ public BufferedImage paint() {
+ BufferedImage image = new BufferedImage((int)
getWidth(),
+ (int) getHeight(),
BufferedImage.TYPE_INT_RGB);
+ paintOnto(image);
+ return image;
+ }
+
+ public BufferedImage paintComponent() {
+ BufferedImage image = new BufferedImage((int)
getWidth(),
+ (int) getHeight(),
BufferedImage.TYPE_INT_RGB);
+ paintComponentOnto(image);
+ return image;
+ }
+
+ public void paintComponentOnto(BufferedImage image) {
+ paint(image.createGraphics());
+ }
+
+ public void paint(Graphics2D paintContext) {
+ super.paint(paintContext);
+ paintedComponent = true;
+ }
+
+ public void paintAsGreek(Graphics2D paintContext) {
+ super.paintAsGreek(paintContext);
+ paintedGreek = true;
+ }
+
+ public boolean isPaintedGreek() {
+ return paintedGreek;
+ }
+
+ public boolean isPaintedComponent() {
+ return paintedComponent;
+ }
+ }
+}
--
Piccolo2D Developers Group: http://groups.google.com/group/piccolo2d-dev?hl=en