Java 为什么';难道我的JComboBox不在我的图纸上作画吗?

Java 为什么';难道我的JComboBox不在我的图纸上作画吗?,java,swing,Java,Swing,我正在用Java编写一个简单的画板,我有一些工具供用户使用:钢笔和橡皮擦。但用于选择工具的JComboBox不会出现,即使它已添加。我听说定制油漆会覆盖所有组件。如果这是真的,我怎样才能使JComboBox始终位于顶部 窗口图片: 这是我的密码: import java.awt.Color; import java.awt.FlowLayout; import java.awt.Graphics; import java.awt.Image; import java.awt.event.Mou

我正在用Java编写一个简单的画板,我有一些工具供用户使用:钢笔和橡皮擦。但用于选择工具的JComboBox不会出现,即使它已添加。我听说定制油漆会覆盖所有组件。如果这是真的,我怎样才能使JComboBox始终位于顶部

窗口图片:

这是我的密码:

import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.util.ArrayList;

import javax.swing.JComboBox;
import javax.swing.JFrame;


public class DrawFrame extends JFrame implements MouseMotionListener, Runnable {
    private static final long serialVersionUID = 1L;

    private Image dbi;
    private Graphics dbg;

    ArrayList<Integer> px = new ArrayList<Integer>();
    ArrayList<Integer> py = new ArrayList<Integer>();

    int mx;
    int my;

    @SuppressWarnings("rawtypes")
    JComboBox tool = new JComboBox();

    @SuppressWarnings("unchecked")
    public DrawFrame() {

        setSize(480, 480);
        setTitle("ScratchPad _14");
        setLayout(new FlowLayout());
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setResizable(false);
        setBackground(Color.WHITE);
        setOpacity(1);

        tool.addItem("Pen");
        tool.addItem("Eraser");

        tool.setEnabled(true);

        add(tool);

        setVisible(true);

        addMouseMotionListener(this);

    }

    /*@Override
    public void mouseClicked(MouseEvent arg0) {
        // TODO Auto-generated method stub

    }

    @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

    }*/

    public static void main(String[] args) {
        // TODO Auto-generated method stub

        DrawFrame df = new DrawFrame();
        Thread t = new Thread(df);

        t.start();

    }

    public void paint(Graphics g) {

        dbi = createImage(getWidth(), getHeight());
        dbg = dbi.getGraphics();
        draw(dbg);
        g.drawImage(dbi, 0, 0, null);

    }

    private void draw(Graphics g) {
        // TODO Auto-generated method stub

        super.paint(g);

        g.setColor(getBackground());
        g.fillRect(0, 0, getWidth(), getHeight());

        g.setColor(Color.BLACK);
        for (int i = 0; i < px.size(); i++) {

            g.fillOval(px.get(i), py.get(i), 3, 3);

        }

        g.setColor(Color.BLUE);
        g.drawString("(" + mx + ", " + my + ")", mx + 10, my - 5);

        repaint();

    }

    @Override
    public void run() {
        // TODO Auto-generated method stub

        while(true) {

            try {
                Thread.sleep(5);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }

        }

    }

    @Override
    public void mouseDragged(MouseEvent m) {
        // TODO Auto-generated method stub

        int x = m.getX();
        int y = m.getY();

        mx = x;
        my = y;

        px.add(x);
        py.add(y);

    }

    @Override
    public void mouseMoved(MouseEvent m) {
        // TODO Auto-generated method stub

        int x = m.getX();
        int y = m.getY();

        mx = x;
        my = y;

    }

}
导入java.awt.Color;
导入java.awt.FlowLayout;
导入java.awt.Graphics;
导入java.awt.Image;
导入java.awt.event.MouseEvent;
导入java.awt.event.MouseMotionListener;
导入java.util.ArrayList;
导入javax.swing.JComboBox;
导入javax.swing.JFrame;
公共类DrawFrame扩展JFrame实现MouseMotionListener,Runnable{
私有静态最终长serialVersionUID=1L;
私有图像dbi;
专用图形数据库;
ArrayList px=新的ArrayList();
ArrayList py=新的ArrayList();
int-mx;
intmy;
@抑制警告(“原始类型”)
JComboBox工具=新的JComboBox();
@抑制警告(“未选中”)
公共抽框(){
设置大小(480480);
设置标题(“草稿行14”);
setLayout(新的FlowLayout());
setDefaultCloseOperation(关闭时退出);
可设置大小(假);
挫折地面(颜色:白色);
毛不透明度(1);
工具。附件(“笔”);
工具添加项(“橡皮擦”);
tool.setEnabled(真);
添加(工具);
setVisible(真);
addMouseMotionListener(此);
}
/*@凌驾
公共无效鼠标单击(鼠标事件arg0){
//TODO自动生成的方法存根
}
@凌驾
公共无效鼠标事件(鼠标事件arg0){
//TODO自动生成的方法存根
}
@凌驾
public void mouseexitted(MouseEvent arg0){
//TODO自动生成的方法存根
}
@凌驾
public void mousePressed(MouseEvent arg0){
//TODO自动生成的方法存根
}
@凌驾
公共无效MouseEvent arg0{
//TODO自动生成的方法存根
}*/
公共静态void main(字符串[]args){
//TODO自动生成的方法存根
DrawFrame df=新的DrawFrame();
螺纹t=新螺纹(df);
t、 start();
}
公共空间涂料(图g){
dbi=createImage(getWidth(),getHeight());
dbg=dbi.getGraphics();
绘制(dbg);
g、 drawImage(dbi,0,0,null);
}
私人空间绘制(图形g){
//TODO自动生成的方法存根
超级油漆(g);
g、 setColor(getBackground());
g、 fillRect(0,0,getWidth(),getHeight());
g、 设置颜色(颜色为黑色);
对于(int i=0;i

提前谢谢

因为您调用了
super.paint
,其中包括绘制子组件

super.paint(g);
然后用背景色填充整个帧,使用

g.setColor(getBackground());
g.fillRect(0, 0, getWidth(), getHeight());
抹掉之前画的那些

您应该避免覆盖顶级容器(如
JFrame
)的
paint
,除了您将在框架装饰下进行绘制并且它不是双缓冲区之外,这些容器实际上是由许多复合组件组成的,它们产生最终输出

相反,创建一个从扩展而来的自定义组件,类似于
JPanel
,并重写其
paintComponent
方法。把你的定制画放在这里

将组合框和自定义绘制面板分别添加到框架中

另外,不要从任何可能生成重新绘制事件的绘制方法调用任何东西(如调用
repaint
),这将建立一个无限循环,该循环将快速消耗您的CPU


查看更多详细信息

通常,不应覆盖JFrame的绘制方法。相反,您应该扩展JPanel,并在重写的
paintComponent
方法中绘制

class PaintPanel extends JPanel
{
    public PaintPanel()
    {
        setOpaque(false);
    }

    @Override 
    protected void paintComponent(Graphics g) 
    {
        // Paint what you have been painting 
        // in your "draw" method ...
        ...
        super.paintComponent(g);
    }
}
通常,
super.paintComponent(g)
调用应该是此类重写方法的第一个调用,但是由于您希望在自己绘制的所有内容之上绘制组合框,因此它必须是最后一个

其他问题:

  • 那根线是干什么用的
  • 你为什么要做手动双缓冲
  • 如果需要手动双缓冲,则不应在每次绘制调用中重新创建图像
稍微清理一下,还不“好”,但是。。。在某种程度上仍然类似于原始程序,至少:

import java.awt.Color;
import java.awt.Graphics;
import java.awt.GridLayout;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.util.ArrayList;

import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPanel;


public class DrawFrame extends JFrame implements MouseMotionListener {
    private static final long serialVersionUID = 1L;

    ArrayList<Integer> px = new ArrayList<Integer>();
    ArrayList<Integer> py = new ArrayList<Integer>();

    int mx;
    int my;

    @SuppressWarnings("rawtypes")
    JComboBox tool = new JComboBox();

    @SuppressWarnings("unchecked")
    public DrawFrame() {

        setSize(480, 480);
        setTitle("ScratchPad _14");
        setLayout(new GridLayout(1,1));
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setResizable(false);
        setBackground(Color.WHITE);
        setOpacity(1);

        tool.addItem("Pen");
        tool.addItem("Eraser");

        tool.setEnabled(true);

        JPanel paintPanel = new PaintPanel();
        paintPanel.add(tool);
        add(paintPanel);

        setVisible(true);

        paintPanel.addMouseMotionListener(this);

    }
    public static void main(String[] args) {
        DrawFrame df = new DrawFrame();
    }

    class PaintPanel extends JPanel
    {
        public PaintPanel()
        {
            setOpaque(false);
        }

        @Override 
        protected void paintComponent(Graphics g) 
        {
            g.setColor(getBackground());
            g.fillRect(0, 0, getWidth(), getHeight());

            g.setColor(Color.BLACK);
            for (int i = 0; i < px.size(); i++) {
                g.fillOval(px.get(i), py.get(i), 3, 3);
            }
            g.setColor(Color.BLUE);
            g.drawString("(" + mx + ", " + my + ")", mx + 10, my - 5);
            super.paintComponent(g);
        }
    }

    @Override
    public void mouseDragged(MouseEvent m) {
        int x = m.getX();
        int y = m.getY();

        mx = x;
        my = y;

        px.add(x);
        py.add(y);

        repaint();
    }

    @Override
    public void mouseMoved(MouseEvent m) {
        int x = m.getX();
        int y = m.getY();

        mx = x;
        my = y;

    }

}
导入java.awt.Color;
导入java.awt.Graphics;
导入java.awt.GridLayout;
导入java.awt.event.MouseEvent;
导入java.awt.event.MouseMotionListener;
导入java.util.ArrayList;
导入javax.swing.JComboBox;
导入javax.swing.JFrame;
导入javax.swing.JPanel;
公共类DrawFrame扩展JFrame实现MouseMotionListener{
私有静态最终长serialVersionUID=1L;
ArrayList px=新的ArrayList();
ArrayList py=新的ArrayList();
int-mx;
intmy;
@抑制警告(“原始类型”)
JComboBox t
@Override
public void paint(Graphics g) {
    super.paint(g);
    g.setColor(Color.BLACK);
    for (int i = 0; i < px.size(); i++) {
        g.fillOval(px.get(i), py.get(i), 3, 3);
    }

    g.setColor(Color.BLUE);
    g.drawString("(" + mx + ", " + my + ")", mx + 10, my - 5);
}

@Override
public void mouseDragged(MouseEvent m) {
    ...
    repaint(50L);
}