Code Comments
Programming Forum and web based access to our favorite programming groups.I'm trying to draw a grid on a JLayeredPane. My JPane contains a menu,
a toolbar and the layered pane.
What happens is the grid flashes briefly on the screen then disappears.
Then, when I resize the window by dragging the border the grid flashes
and flickers, but ultimately disappears when I stop dragging.
I'd know what to look for in Windows/C++, but I'm pretty new to Java
and I'm stuck.
Here's the relevant code:
public void paintComponent(Graphics g) {
// Override paint component to be able to superimpose grid
super.paintComponent(g); // paint background
if (!gridShowing) {
return;
}
Graphics2D g2 = (Graphics2D)layeredPane.getGraphics(); //
(Graphics2D)g;
g2.drawImage(grid, null, 0, 0);
}
public void showGrid() {
gridShowing = !gridShowing;
if (gridShowing) {
if (grid == null) {
// Create the grid image
int x,y;
int w = layeredPane.getWidth();
int h = layeredPane.getHeight();
grid = (BufferedImage)(this.createImage(w,h));
Graphics2D gc = grid.createGraphics();
gc.setColor( Color.red );
for ( x=0; x<w; x+=10 ) {
gc.drawLine( x, 0, x, h );
}
for ( y=0; y<h; y+=10 ) {
gc.drawLine( 0, y, w, y );
}
}
}
layeredPane.repaint();
}
Thanks for any help.
--gary
Post Follow-up to this messagefiziwig wrote:
...
> What happens is the grid flashes briefly on the screen then disappears.
> Then, when I resize the window by dragging the border the grid flashes
> and flickers, but ultimately disappears when I stop dragging.
...
> Here's the relevant code:
...hmmm. Famous last words.
> public void paintComponent(Graphics g) {
> // Override paint component to be able to superimpose grid
> super.paintComponent(g); // paint background
> if (!gridShowing) {
> return;
> }
> Graphics2D g2 = (Graphics2D)layeredPane.getGraphics(); //
> (Graphics2D)g;
It is odd that you should have commented out the correct way
of going about this - using the Graphics object you were given.
(I am guessing) you need to override the paintComponent()
method of your layeredPane to draw the grid, then leave the
main paintComponent() method as it is (I.E. do not override
it at all).
Andrew T.
Post Follow-up to this messageandrewtho...@gmail.com wrote: > fiziwig wrote: > ... > ... > > ...hmmm. Famous last words. > > > It is odd that you should have commented out the correct way > of going about this - using the Graphics object you were given. > > (I am guessing) you need to override the paintComponent() > method of your layeredPane to draw the grid, then leave the > main paintComponent() method as it is (I.E. do not override > it at all). > > Andrew T. I tried the commented out code originally but the only place the grid showed up was behind the toolbar when I resized the window to be wider than the width of the toolbar. It didn't show up in the layered pane at all. Right after lunch I'll try what you suggest and override JLayeredPane's painComponent() and see what happens. Thanks. --gary
Post Follow-up to this messagefiziwig wrote:
>
> What happens is the grid flashes briefly on the screen then disappears.
> Then, when I resize the window by dragging the border the grid flashes
> and flickers, but ultimately disappears when I stop dragging.
I take it this code is in a subclass of JLayeredPane?
> public void paintComponent(Graphics g) {
> // Override paint component to be able to superimpose grid
> super.paintComponent(g); // paint background
> if (!gridShowing) {
> return;
> }
> Graphics2D g2 = (Graphics2D)layeredPane.getGraphics(); //
> (Graphics2D)g;
> g2.drawImage(grid, null, 0, 0);
> }
You are probably going to fall foul of Swing's double buffering and
optimised drawing with this. See, for instance
JComponent.isOptimizedDrawingEnabled.
http://download.java.net/jdk6/docs/... />
ingEnabled()
A better approach than subclassing JLayeredPane is to subclass
JComponent, set it to non-opaque and add to an unsubclassed JLayeredPane
as a "glass pane".
> public void showGrid() {
> gridShowing = !gridShowing;
> if (gridShowing) {
> if (grid == null) {
> // Create the grid image
> int x,y;
> int w = layeredPane.getWidth();
This isn't going to work so well when it's resized.
Tom Hawtin
--
Unemployed English Java programmer
http://jroller.com/page/tackline/
Post Follow-up to this messageThomas Hawtin wrote: > fiziwig wrote: <snip> > A better approach than subclassing JLayeredPane is to subclass > JComponent, set it to non-opaque and add to an unsubclassed JLayeredPane > as a "glass pane". > A good thought, but JLayeredPane doesn't have the setGlassPane() method, and if I use the JFrame's setGlassPane() then the grid flashes briefly as before, but remains visible superimposed on the window caption bar, and nowhere else. > > This isn't going to work so well when it's resized. Yes, I know. I just want to get is visible and working first. I'll worry about resizing after I get over this major hurdle. What's odd is I can create a JLabel with an Icon from a jpg with a grid and add it as a transparent layer and that works fine. But that's definitely not resizable. I tried creating an image in a JLabel but that did the same flashy thing and then vanished. This ought to be easy! Java makes the hard thing really easy, but sometimes it seems to make the easy things really hard! ;-) In C++ it would have taken four times as long to get where I am on this project. That's the good news. BUT... adding the grid would have taken me tens minutes in C++, not half a day. AARRGGHH! --gary > Tom Hawtin > -- > Unemployed English Java programmer > http://jroller.com/page/tackline/
Post Follow-up to this message
fiziwig wrote:
> I'm trying to draw a grid on a JLayeredPane. My JPane contains a menu,
> a toolbar and the layered pane.
>
> What happens is the grid flashes briefly on the screen then disappears.
> Then, when I resize the window by dragging the border the grid flashes
> and flickers, but ultimately disappears when I stop dragging.
>
FWIW: Here's the solution I found after trying about 12 different
approaches, including subclassing JComponent (which didn't work right),
and using a glass pane on my JFrame, which put the grid on the caption
bar as well.
Here's what DID work: I replaced my JLayeredPane with this class:
class GridPane extends JLayeredPane {
private BufferedImage grid;
private boolean gridShowing;
private int width,height;
public GridPane() {
super();
gridShowing = false;
width = 1024; // default sizes. The grid image will only be
created
height = 768; // once unless the window is resized to bigger
than this
}
public void paintComponent(Graphics g) {
// Override paint component to be able to superimpose grid
super.paintComponent(g); // paint background
if (!gridShowing) {
return;
}
Graphics2D g2 = (Graphics2D)g;
g2.drawImage(grid, null, 0, 0);
}
public void showGrid(boolean value) {
gridShowing = value;
if (grid==null) {
makeGrid();
}
}
public void setSize( Dimension d ) {
super.setSize( d );
gridResize();
}
public void setSize( int w, int h ) {
super.setSize( w, h );
gridResize();
}
public void setBounds( int x, int y, int w, int h ) {
super.setBounds( x, y, w, h );
gridResize();
}
private void gridResize() {
if ((getWidth()>width)||(getHeight()>height)) {
// window has exceeded max size. redraw grid bigger
makeGrid();
}
}
private void makeGrid() {
// build a grid image at least as big as the window, but no
less than 1024x768
// This prevents having to create fresh images over and over
while dragging
// the edge of the window to resize, thus preventing the
garbage collector from
// having a nervous breakdown.
int x,y;
width = getWidth();
if (width<1024) {
width = 1024;
}
height = getHeight();
if (height<768) {
height = 768;
}
grid = (BufferedImage)(createImage(width,height
));
Graphics2D gc = grid.createGraphics();
gc.setColor( new Color(0xd0d0ff));
for (x=0; x<width; x+=10) {
gc.drawLine(x, 0, x, height);
}
for (y=0; y<height; y+=10) {
gc.drawLine(0, y, width, y);
}
}
}
--gary
Post Follow-up to this message> public void paintComponent(Graphics g) {
> // Override paint component to be able to superimpose grid
> super.paintComponent(g); // paint background
> if (!gridShowing) {
> return;
> }
> Graphics2D g2 = (Graphics2D)g;
> g2.drawImage(grid, null, 0, 0);
> }
>
> public void showGrid(boolean value) {
> gridShowing = value;
>
> if (grid==null) {
> makeGrid();
> }
> }
why don't you make small grid image (e.g.100x100) and paint it tiled?
This has advantage that you don't have to recreate image
on window resize and also saves memory.
int tileSize = 100; //
paintGrid(Graphics g) {
int width = getWidth();
int height = getHeight();
int w = width / tileSize + 1;
int h = height / tileSize + 1;
for(int i = 0; i < h; i++) {
for(int j = 0; j < w; j++) {
g.drawImage(grid, tileSize * w - 5, tileSize * h - 5, null);
}
}
}
public void paintComponent(Graphics g) {
// Override paint component to be able to superimpose grid
super.paintComponent(g); // paint background
if (!gridShowing) {
return;
}
paintGrid(g);
}
private void makeGrid() {
grid = (BufferedImage)(createImage(tileSize , tileSize ));
Graphics2D gc = grid.createGraphics();
gc.setColor( new Color(0xd0d0ff));
for (x=5; x<tileSize ; x+=10) {
gc.drawLine(x, 0, x, tileSize );
}
for (y=5; y<tileSize ; y+=10) {
gc.drawLine(0, y, tileSize , y);
}
gc.dispose();
}
}
Andrey
--
http://uio.imagero.com Unified I/O for Java
http://reader.imagero.com Java image reader
http://jgui.imagero.com Java GUI components and utilities
Post Follow-up to this messagefiziwig wrote: > > A good thought, but JLayeredPane doesn't have the setGlassPane() > method, and if I use the JFrame's setGlassPane() then the grid flashes > briefly as before, but remains visible superimposed on the window > caption bar, and nowhere else. I meant the concept of a glass pane. That is a non-opaque component with no mouse listeners layered over other components, which JLayeredPane does support. Tom Hawtin -- Unemployed English Java programmer http://jroller.com/page/tackline/
Post Follow-up to this messageAndrey Kuznetsov wrote: > > why don't you make small grid image (e.g.100x100) and paint it tiled? > This has advantage that you don't have to recreate image > on window resize and also saves memory. As it's only a few lines, I would think avoiding the image all together would work better. Tom Hawtin -- Unemployed English Java programmer http://jroller.com/page/tackline/
Post Follow-up to this message>> why don't you make small grid image (e.g.100x100) and paint it tiled? > > As it's only a few lines, I would think avoiding the image all together > would work better. I agree, if you have only a few lines, you should draw it directly. Andrey -- http://uio.imagero.com Unified I/O for Java http://reader.imagero.com Java image reader http://jgui.imagero.com Java GUI components and utilities
Post Follow-up to this message
Show a Printable Version
Email This Page to Someone!
Receive updates to this thread
Powered by vBulletin
Copyright 2000-2006 Jelsoft Enterprises Limited.