Java “绘制”面板渲染不正确
下面是正在发生的事情: 我想制作一个非常基本的绘画程序来练习使用绘画方法,处理图形,使用工具栏等等。我已经读了很多关于如何做这些事情的书,我确信我遗漏了一行重要的代码,因为paintpanel本身正在呈现一个不应该存在的JMenu。我用actionListeners设置了一个JMenu,但是呈现为extra的JMenu不起任何作用,无法与之交互。这是一张照片: 如下图所示,我可以在菜单上画画,但它仍然没有任何反应。另外,这一次你可以看到一个radom按钮,从程序中的前一个窗口是出于某种原因添加的 这是按钮的来源: 我不知道如何解决这个问题,下面是相关类的代码: 这是画这幅画的面板。 包装油漆工Java “绘制”面板渲染不正确,java,swing,graphics,jpanel,paintcomponent,Java,Swing,Graphics,Jpanel,Paintcomponent,下面是正在发生的事情: 我想制作一个非常基本的绘画程序来练习使用绘画方法,处理图形,使用工具栏等等。我已经读了很多关于如何做这些事情的书,我确信我遗漏了一行重要的代码,因为paintpanel本身正在呈现一个不应该存在的JMenu。我用actionListeners设置了一个JMenu,但是呈现为extra的JMenu不起任何作用,无法与之交互。这是一张照片: 如下图所示,我可以在菜单上画画,但它仍然没有任何反应。另外,这一次你可以看到一个radom按钮,从程序中的前一个窗口是出于某种原因添加的
import java.awt.Color;
import java.awt.Graphics;
import java.awt.event.MouseEvent;
import javax.swing.JPanel;
import javax.swing.event.MouseInputListener;
@SuppressWarnings("serial")
public class PaintPanel extends JPanel implements MouseInputListener
{
//These two values will be used to determine where the mouse is and thus where to paint...stuff...
public int xCoordinate, yCoordinate = -10;
static Color currentColor = Color.black;
public PaintPanel()
{
//These two methods simply attaches the mouse listener methods listed below to the actual panel.
addMouseListener(this);
addMouseMotionListener(this);
}
//This method is an overwritten version of the default paint method. It's job is to render custom graphics
//objects on the screen. The Graphics g argument is the item responsible for doing the actual rendering.
@Override
public void paintComponent(Graphics g)
{
// super.paintComponent(g);
g.setColor(currentColor);
g.fillRect(xCoordinate, yCoordinate, 10, 10);
}
@Override
//This method, added because of the MouseInputListener implementation, is used when a user clicks the left mouse button.
public void mouseClicked(MouseEvent e)
{
xCoordinate = e.getX();
yCoordinate = e.getY();
repaint();
}
@Override
public void mouseEntered(MouseEvent arg0)
{
// TODO Auto-generated method stub
}
@Override
public void mouseExited(MouseEvent arg0)
{
// TODO Auto-generated method stub
}
@Override
public void mousePressed(MouseEvent arg0)
{
// TODO Auto-generated method stub
}
@Override
public void mouseReleased(MouseEvent arg0)
{
// TODO Auto-generated method stub
}
@Override
//This method, added because of the MouseInputListener implementation, is used when a user presses and holds the
//left mouse button while moving the mouse.
public void mouseDragged(MouseEvent e)
{
xCoordinate = e.getX();
yCoordinate = e.getY();
repaint();
}
@Override
public void mouseMoved(MouseEvent arg0)
{
// TODO Auto-generated method stub
}
public static void changeColor(Color color)
{
currentColor = color;
}
}
这是添加到PaintPanel、菜单和稍后的其他按钮等中的主类
package painter;
import java.awt.BorderLayout;
import javax.swing.JFrame;
import javax.swing.JMenuBar;
import javax.swing.JPanel;
import painter.menu.FileMenu;
import painter.menu.ToolsMenu;
@SuppressWarnings("serial")
//This class will do the job of bringing together all the various sub-classes and rendering everything.
public class MainPainterGUI extends JFrame
{
private JPanel menuPanel;
private JMenuBar menuBar;
//These values are going to be used to set an initial window size.
private final short WINDOW_HEIGHT = 1000;
private final short WINDOW_WIDTH = 1000;
//This constructor will do the actual creation of the window.
public MainPainterGUI()
{
//This does the same thing that setTitle does.
super("Painter");
//setTitle("Painter");
//This method will set what the window is supposed to do when the red x is clicked.
//Technically, the value passed is an integer.
setDefaultCloseOperation(EXIT_ON_CLOSE);
//Obviously this method sets the initial size of the window. It can be changed by the user however.
setSize(WINDOW_WIDTH,WINDOW_HEIGHT);
//This method sets the center of the window relative to whatever is passed. In this case, null makes
//the window appear in the center of the desktop regardless of the size.
setLocationRelativeTo(null);
menuPanel = new JPanel();
menuBar = new JMenuBar();
menuBar.add(new FileMenu());
menuBar.add(new ToolsMenu());
menuPanel.add(menuBar);
//The add method simply attaches a component to whatever is calling, like a frame or another panel.
//The BorderLayout is needed to use the draggable toolbar.
add(new PaintPanel(), BorderLayout.CENTER);
add(menuPanel, BorderLayout.NORTH);
//This will allow the window to be seen. Make sure this method is last, as if
//a component is created afterwards it may not be visible.
setVisible(true);
}
}
这两个类应该是与当前问题相关的唯一类,但是如果需要其他类,请告诉我。我只是不想在帖子里塞满无用的信息
下面是我已经尝试过的:
正如您在PaintPanel类中看到的,我添加了一个super.paintComponent(g);方法调用。然而,虽然这完全解决了我的问题,但它一次只绘制一个黑色正方形。我可以想象,因为它会用一个paint调用覆盖面板,然后每次调用repoint时都会绘制正方形
这是一张添加了super.paintComponent(g)的照片:
我不确定这是否重要,但我使用的是Windows10
感谢您提供的任何帮助。我认为您需要调用
.repaint()
以减少UI的故障。您不是在调用super.paintComponent方法,而是在注释它——这是危险的代码,不应该这样做。如果希望图像保持不变,请将点放入ArrayList中,然后在paintComponent中绘制点的ArrayList。或者绘制一个BuffereImage,然后在paintComponent方法中绘制它。并始终调用super的paintComponent方法。有一些工作示例,向您展示了如何通过使用上面建议的列表
或缓冲图像
来持久绘制。@HovercraftFullOfEels我在测试时注释掉了super.paintComponent(g)。我的代码中实际上有。如果我从不调用repaint(),它就不会绘制任何东西。至少它不在您给出的代码中,除了在单击处理程序中。您应该在更改UI后调用它。