【问题标题】:Java drawRect() method has weird/wrong sizingJava drawRect() 方法具有奇怪/错误的大小
【发布时间】:2020-07-13 17:33:07
【问题描述】:

所以,我试图在 JPanel (Rect) 上绘制一个矩形,然后将其添加到我的主 JFrame。矩形应该在我的窗口中间,但它却在窗口之外。

我尝试过的事情:

  • 将 JPanel 添加到 JFrame,然后将 Rect 添加到 JPanel,没有任何变化。
  • 将 JFrames 布局设置为 null,矩形消失不见。

相关代码:

Main.java

package sudoku_solver;

public class Main
{
    public static void main(String[] args)
    {
        int[][] board = Board.getBoard();
        Solver solver = new Solver(board);
        Interface gui = new Interface();

        gui.createFrame();
        gui.drawGrid(board);

        solver.solve();
        solver.print();
    }
}

Interface.java

package sudoku_solver;

import java.awt.*;
import javax.swing.*;

public class Interface
{
    private static class Rect extends JPanel
    {
        private static final long serialVersionUID = 1L;

        int x;
        int y;
        int rectWidth;
        int rectHeight;
        Color color;

        public Rect(int _x, int _y, int _rectWidth, int _rectHeight, Color _color)
        {
            x = _x;
            y = _y;
            rectWidth = _rectWidth;
            rectHeight = _rectHeight;
            color = _color;
        }

        @Override
        protected void paintComponent(Graphics g)
        {
            super.paintComponent(g);
            Graphics2D g2d = (Graphics2D) g;                                                                           
            g2d.drawRect(x, y, rectWidth, rectHeight);
            g2d.setColor(color);
        }
    }

    static JFrame frame;
    static int windowWidth = 580;
    static int windowHeight = 580;
    static int cellSize = windowWidth / 9;

    public void createFrame()
    {
        frame = new JFrame("Sudoku");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(windowWidth, windowHeight);
        frame.setVisible(true);
    }

    public void drawGrid(int[][] bo)
    {
        drawBorder();
    }

    private static void drawBorder()
    {
        Rect rect = new Rect(20, 20, windowWidth - 20, windowHeight - 20, Color.black);
        frame.add(rect);
    }
}

输出:

试图找到其他有同样问题的人,但找不到任何人。谢谢!

【问题讨论】:

    标签: java swing user-interface awt


    【解决方案1】:

    问题在于您正试图控制框架的大小。这不是 Swing 的工作方式。请记住,框架大小包括标题栏和边框。因此,添加到框架的面板大小永远不会与框架的大小相同。

    相反,您可以控制添加到框架的组件的大小。然后框架将根据这些组件适当地调整大小。

    static int windowWidth = 580;
    static int cellSize = windowWidth / 9;
    

    为什么你会选择 580 的宽度。你如何让单元格大小相等,因为 9 不等于 580。

    因此,您应该指定您的单元格大小。然后在面板中乘以 9 以获得面板的首选尺寸。

    Rect rect = new Rect(20, 20, windowWidth - 20, windowHeight - 20, Color.black);
    

    另外,不要在 4 个不同的地方硬编码值 20。同样,您可能对类行“borderSize”有一个参数。然后在内部使用这个值。

    因此,您的 Rect 类的参数可能类似于: 公共矩形(int cellSize,intborderSize,Color _color) 现在您需要实现类的getPreferredSize() 方法,以便组件可以计算自己的首选大小。比如:

    @Override
    public Dimension getPreferredSize()
    {
        int size = (cellSize * 9) + (borderSize * 2);
        return new Dimension(size, size);
    }
    

    现在,当您进行自定义绘画时,所有绘画都是相对于面板完成的。比如:

        @Override
        protected void paintComponent(Graphics g)
        {
            super.paintComponent(g);
            Graphics2D g2d = (Graphics2D) g;                                                                           
            int size = (cellSize * 9);
            g2d.drawRect(borderSize, borderSize, size, size);
            g2d.setColor(color);
        }
    

    所以当你创建一个你会使用的类的实例时:

     public void createFrame()
    {
        Rect rect = new Rect(50, 20, Color.black);
        frame = new JFrame("Sudoku");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(rect);
        frame.pack();
        //frame.setSize(windowWidth, windowHeight);
        frame.setVisible(true);
    }
    

    【讨论】:

    • cellSize 与我正在尝试绘制的当前 Rect 没有任何关系,但注释“相反,您可以控制添加到框架中的组件的大小。”让我弄清楚了,所以我会接受答案,即使它有很多与问题无关的信息。
    • @alekala cellSize 与我正在尝试绘制的当前 Rect 没有任何关系 - 确实如此,或者至少如果你设计你的正确编码。在我看来,您正试图在 Suduko 板周围画一个边框。所以是的,单元格大小是相关的,因为它应该全部绑定在一起,这样您就可以轻松更改单元格大小并自动调整边框大小。
    • 事实上您可能甚至不需要进行自定义绘画。您可以在面板中添加一个边框。阅读How to Use Borders 上的 Swing 教程以获取更多信息。
    【解决方案2】:

    你写:

    new Rect(20, 20, windowWidth - 20, windowHeight - 20, Color.black);
    

    应该是

    new Rect(20, 20, windowWidth - 40, windowHeight - 40, Color.black);
    

    因为,第一个点表示开始本地化,第三个和第四个表示你的矩形应该有多长。所以既然你拿走了20,但它应该是40,因为你只从左边拿走了,忘记了框架的右边。

    【讨论】:

    • 这是正确的,但现在是output。所以显然还是有问题。
    • @alekala 所以还是有问题。 - 正如我的回答中所解释的那样。
    猜你喜欢
    • 2013-11-15
    • 1970-01-01
    • 1970-01-01
    • 2012-09-06
    • 1970-01-01
    • 2010-09-19
    • 1970-01-01
    • 2012-05-03
    • 1970-01-01
    相关资源
    最近更新 更多