Reputation: 53
I've run into a bit of a wall here. I read elsewhere while trying to fix this issue that you are never supposed to getGraphics(). The problem is, I can't use the provided Graphics context from the paint() / paintComponent() methods. I require it to only call my generate(Graphics g) function once, and I can not provide Graphics outside of the override functions.
Any tips? Trimmed for your convenience.
public class Main extends JPanel {
...
static JFrame displayFrame, inputFrame;
...
...
// Generator node list
ArrayList<Node> nodes = new ArrayList<Node>();
public static void main(String[] args) {
// Set up the frame
screenSize = Toolkit.getDefaultToolkit().getScreenSize();
displayFrame = new JFrame("City generator");
displayFrame.setSize(screenSize.width / 3, screenSize.width / 3);
displayFrame.setLocation(screenSize.width / 2 - displayFrame.getWidth()
/ 2, screenSize.height / 2 - displayFrame.getHeight() / 2);
displayFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
displayFrame.add(new Main());
// displayFrame.setUndecorated(true);
displayFrame.setBackground(Color.lightGray);
displayFrame.setVisible(true);
displayFrame.addMouseMotionListener(new MouseAdapter() {
public void mouseMoved(MouseEvent e) {
// Mouse movement events here
}
});
}
// Override function
public void paintComponent(Graphics g) {
super.paintComponent(g);
// Calls multiple times
generate(g);
}
private void generate(Graphics g) {
............................
Upvotes: 0
Views: 1020
Reputation: 347234
Instead of painting directly to the Graphics
context, you could generate a BufferedImage
image of what you want painted and paint to that instead...
private BufferedImage buffer;
public BufferedImage generate() {
if (buffer == null) {
buffer = new BufferedImage(getWidth(), getHeight(), BufferedImage.TYPE_IMAGE_ARGB);
Graphics2D g2d = buffer.createGraphics();
// Paint away...
g2d.dispose();
}
return buffer;
}
Then you would paint the result within the paintComponent
method...
public void paintComponent(Graphics g) {
super.paintComponent(g);
// Calls multiple times
BufferedImage img = generate();
g.drawImage(img, 0, 0, this);
}
As an example...
Upvotes: 1
Reputation: 1706
Why not just keep a boolean value to track if generate() has been called.
public boolean calledGenerate = false;
public void paintComponent(Graphics g) {
super.paintComponent(g);
if (!calledGenerate) generate(g);
}
void generate(Graphics g) {
calledGenerate = true;
....
}
also you are calling AWT/Swing code outside of the EDT which is a bad idea.
In your main function you normally should call:
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
//build your awt/swing objects here
}
});
What does generate() do though? There is probably a better way to do it.
Upvotes: 0