不明白是什么原理,棋盘的竖线有时会越过顶部边界,有时可以正确显示。import java.awt.Color;
import java.awt.Frame;
import java.awt.Graphics;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;public class Panel2 extends Frame {
    private final int margin_left = 10;
    private final int margin_top = 10;
    private final int block_size = 20;
    private final int board_dim = 15;
    
    public Panel2() {
        setTitle("五子棋游戏");
        setVisible(true);
        setLayout(null);
        setBounds(0, 0, 600, 600);
        addWindowListener(new WindowAdapter() {
            public void windowClosing(WindowEvent e) {
                System.exit(0);
            }
        });
        setBackground(Color.YELLOW);
    }    public void paint(Graphics g) {
        int i;
        for (i = 0; i < board_dim; i++) {
            // 横线 15*15的棋盘 
            int x1 = margin_left;
            int y1 = margin_top + i * block_size;
            int x2 = margin_left + block_size*(board_dim-1);
            int y2 = y1;
            g.drawLine(x1, y1, x2, y2);
        }
        for (i = 0; i < board_dim; i++) {
            // 竖线 15*15的棋盘 
            int x1 = margin_left + i * block_size;
            int y1 = margin_top;
            int x2 = x1;
            int y2 = margin_top + block_size*(board_dim-1);
            g.drawLine(x1, y1, x2, y2);
        }
        int radius = 3;
        int x1 = margin_left + board_dim/2*block_size;
        int y1 = margin_top + board_dim/2*block_size;
        g.fillOval(x1 - radius, y1 - radius, radius*2, radius*2);// 画点
        int shift = (board_dim/4+1)*block_size;
        g.fillOval(x1- shift - radius, y1 -shift - radius, radius*2, radius*2);
        g.fillOval(x1-shift - radius, y1 +shift - radius, radius*2, radius*2);
        g.fillOval(x1+shift - radius, y1 -shift - radius, radius*2, radius*2);
        g.fillOval(x1+shift - radius, y1 +shift - radius, radius*2, radius*2);
       
    }
    
    public static void main(String[] args) {
        Panel2 p = new Panel2();
    }
}请大家帮忙分析一下,啥原因呢

解决方案 »

  1.   

     setBounds(0, 0, 600, 600);   这个组建的600*600是整体大小,包含了边框 private final int margin_top = 50; 设置大一些就可以了
      

  2.   

    帮你改造了下
    先是Framepackage test;import java.awt.Color;
    import java.awt.event.WindowAdapter;
    import java.awt.event.WindowEvent;import javax.swing.JFrame;public class WuziFrame extends JFrame {
    private static final long serialVersionUID = 1L; public WuziFrame() {
            setTitle("五子棋游戏");
            
            setLayout(null);
            setBounds(0, 0, 600, 600);
            addWindowListener(new WindowAdapter() {
                public void windowClosing(WindowEvent e) {
                    System.exit(0);
                }
            });
            setBackground(Color.YELLOW);
            Panel1 panel1 = new Panel1();
            
            this.setContentPane(panel1);
        }
       
        public static void main(String[] args) {
         WuziFrame p = new WuziFrame();
            p.setVisible(true);
        }
    }下面是面板Panel1package test;
    import java.awt.Graphics;import javax.swing.JPanel;public class Panel1 extends JPanel {
    private static final long serialVersionUID = 1L;
    private final int margin_left = 10;
        private final int margin_top = 10;
        private final int block_size = 20;
        private final int board_dim = 15;
    public void paint(Graphics g) {
            int i;
            for (i = 0; i < board_dim; i++) {
                // 横线 15*15的棋盘 
                int x1 = margin_left;
                int y1 = margin_top + i * block_size;
                int x2 = margin_left + block_size*(board_dim-1);
                int y2 = y1;
                g.drawLine(x1, y1, x2, y2);
                System.out.println(x1+","+y1);
            }
            for (i = 0; i < board_dim; i++) {
                // 竖线 15*15的棋盘 
                int x1 = margin_left + i * block_size;
                int y1 = margin_top;
                int x2 = x1;
                int y2 = margin_top + block_size*(board_dim-1);
                g.drawLine(x1, y1, x2, y2);
            }
            int radius = 3;
            int x1 = margin_left + board_dim/2*block_size;
            int y1 = margin_top + board_dim/2*block_size;
            g.fillOval(x1 - radius, y1 - radius, radius*2, radius*2);// 画点
            int shift = (board_dim/4+1)*block_size;
            g.fillOval(x1- shift - radius, y1 -shift - radius, radius*2, radius*2);
            g.fillOval(x1-shift - radius, y1 +shift - radius, radius*2, radius*2);
            g.fillOval(x1+shift - radius, y1 -shift - radius, radius*2, radius*2);
            g.fillOval(x1+shift - radius, y1 +shift - radius, radius*2, radius*2);    }
    }
      

  3.   

    另外,awt里的Frame的边界是从标题栏算起,而swing中的JFrame是从内容面板算,这就是导致你画出来的表格显示不完整的原因,你用awt的Frame的话,就要把top上的距离设大一点
      

  4.   

    这个问题的解决方案是在setVisible方法后面(只有在此方法之后调用才有效)添加一些代码(需要把这些变量的final修饰符去掉):setVisible(true);
    Insets i = getInsets();
    margin_left += i.left;
    margin_top += i.top;
    repaint();
    原理如楼上所讲,paint中的graphics绘图原点在窗体的左上角(也算标题栏,在关闭按钮的左上边那个角)
    其度量方法就是获得窗体的Insets,表示上下左右边界的宽度。
    调用完以上方法后repaint()重绘窗体,使修改生效。最好的办法是不要直接在frame中绘图,而是extends某个componet,如panel等,重写它们的paint和update方法。它们的左上角一定会在窗体的里面的,而且易于通过布局控制大小和位置。另,现在不再推荐使用Frame,而是使用JFrame。
      

  5.   

    说实话,这个swing属于native的方案,将来趋势是html5建议使用html5来做界面啦。。方便有跨平台。
      

  6.   

    JFrame只是一个外框,里面有一个内容面板,你的JPanel添加到这个内容面板上,所以绘制的时候所有的内容不是画在JFrame上,而是画在JPanel上,你要用JPanel的大小作为边界条件。参考四楼的代码,虽然我没仔细看,但是大概是那个意思