使用JPanel在GUI中相互覆盖图层

时间:2014-09-20 04:01:17

标签: java swing user-interface jpanel

我无法制作简单计算器的布局。发生的事情是,除了我的减去按钮保留为背景之外,一切看起来都很好,我必须猜测我的其他按钮能够点击它们的位置。当我点击它们时,我能够看到它们,直到我取消它们。有没有什么办法解决这一问题?我不会发布这个问题不需要的数学算法。

import javax.swing.*;

import java.awt.*;
import java.awt.event.*;

public class GUIcalc extends JFrame implements ActionListener {

    private JPanel panel;
    private JPanel buttonpanel;
    private JPanel text;
    private JLabel sumfield;
    private BorderLayout layout;
    private GridLayout grid;
    private Container container;
    private boolean toggle=true;
    private float sum;
    private int num1;
    private int num2;
    JButton one = new JButton("1");
    JButton two = new JButton("2");
    JButton three = new JButton("3");
    JButton four = new JButton("4");
    JButton five = new JButton("5");
    JButton six = new JButton("6");
    JButton seven = new JButton("7");
    JButton eight = new JButton("8");
    JButton nine = new JButton("9");
    JButton zero = new JButton("0");
    JButton multi = new JButton("*");
    JButton divide = new JButton("/");
    JButton equal = new JButton("=");
    JButton add = new JButton("+");
    JButton subtract = new JButton("-");
    JButton deci = new JButton("."); 
    private final Font number= new Font("monspaced", Font.ITALIC, 20);
    JFrame guiFrame;
    private int counter;

    /**
     * @param args
     */
    public GUIcalc() {

        super("Calculator");    
        sumfield = new JLabel(""+sum);
        sumfield.setLocation(0, 0);
        sumfield.setSize(245, 45);
         add(sumfield);
        seven=new JButton("7");
        seven.setLocation(0,50);
        seven.setSize(50, 50);
        seven.addActionListener(this);
        add(seven);
        eight=new JButton("8");
        eight.setLocation(55,50);
        eight.setSize(50, 50);
        eight.addActionListener(this);
        add(eight);
        nine=new JButton("9");
        nine.setLocation(110,50);
        nine.setSize(50, 50);
        nine.addActionListener(this);
        add(nine);
        divide=new JButton("/");
        divide.setLocation(165,50);
        divide.setSize(50, 50);
        divide.addActionListener(this);
        add(divide);
        six=new JButton("6");
        six.setLocation(0,105);
        six.setSize(50, 50);
        six.addActionListener(this);
        add(six);
        five=new JButton("5");
        five.setLocation(55,105);
        five.setSize(50, 50);
        five.addActionListener(this);
        add(five);  
        four=new JButton("4");
        four.setLocation(110,105);
        four.setSize(50, 50);
        four.addActionListener(this);
        add(four);
        multi=new JButton("*");
        multi.setLocation(165,105);
        multi.setSize(50, 50);
        multi.addActionListener(this);
        add(multi);
        three=new JButton("3");
        three.setLocation(0,165);
        three.setSize(50, 50);
        three.addActionListener(this);
        add(three);
        two=new JButton("2");
        two.setLocation(55,165);
        two.setSize(50, 50);
        two.addActionListener(this);
        add(two);
        one=new JButton("1");
        one.setLocation(110,165);
        one.setSize(50, 50);
        one.addActionListener(this);
        add(one);
        add=new JButton("+");
        add.setLocation(165,165);
        add.setSize(50, 50);
        add.addActionListener(this);
        add(add);
        zero=new JButton("0");
        zero.setLocation(0,220);
        zero.setSize(50, 50);
        zero.addActionListener(this);
        add(zero);      
        deci=new JButton(".");
        deci.setLocation(55,220);
        deci.setSize(50, 50);
        deci.addActionListener(this);
        add(deci);
        equal=new JButton("=");
        equal.setLocation(110,220);
        equal.setSize(50, 50);
        equal.addActionListener(this);
        add(equal);
        subtract=new JButton("-");
        subtract.setLocation(165,220);
        subtract.setSize(50, 50);
        subtract.addActionListener(this);
        add(subtract);
   }

1 个答案:

答案 0 :(得分:3)

您的问题在于您尝试在使用BorderLayout的容器(JFrame的contentPane)中设置组件的绝对位置和大小。快速简便的解决方案是通过setLayout(null)

使JFrame contentPane的布局为null

虽然这很简单,而且很有效,但它也是错误的,因为它会迫使你创建一个在某个屏幕分辨率下在一个平台上看起来很好的严格的GUI,它看起来很糟糕其他决议或其他平台几乎不可能根据需要进行修改。更好的解决方案是使用布局管理器。坚持一个这样的例子......


修改
例如,如果......

  • 您的主GUI使用了BorderLayout
  • 您添加了显示数字的JTextField到主GUI BorderLayout.NORTH,也称为BorderLayout.PAGE_START
  • 为按钮创建一个JPanel,比如名为btnPanel,并将其添加到主GUI BorderLayout.CENTER。
  • 给btnPanel一个GridLayout大小以接受所有按钮。
  • 在创建JBttons时将其添加到btnPanel。
  • 不是设置JButton的大小,而是为什么不设置更大的字体,让按钮和GUI大小本身以容纳更大的字体。

例如,以这种方式完成的代码如下所示:

enter image description here

import java.awt.BorderLayout;
import java.awt.Font;
import java.awt.GridLayout;

import javax.swing.*;

public class GUIcalc2 extends JPanel {
   private static final String[][] BTN_TEXTS = { 
      { "7", "8", "9", "/" },
      { "6", "5", "4", "*" }, 
      { "3", "2", "1", "+" }, 
      { "0", ".", "=", "-" } };
   private static final int GAP = 3;
   private static final float TF_SIZE = 18f;
   private static final float BTN_SIZE = 24f;
   private JButton[][] buttons = new JButton[BTN_TEXTS.length][BTN_TEXTS[0].length];
   private JTextField textField = new JTextField(10);

   public GUIcalc2() {
      textField.setFont(textField.getFont().deriveFont(TF_SIZE));
      JPanel btnPanel = new JPanel(new GridLayout(BTN_TEXTS.length, 
            BTN_TEXTS[0].length, GAP, GAP));
      for (int row = 0; row < BTN_TEXTS.length; row++) {
         for (int col = 0; col < BTN_TEXTS[0].length; col++) {
            JButton btn = new JButton(BTN_TEXTS[row][col]);
            // add ActionLIstener here
            btn.setFont(btn.getFont().deriveFont(Font.BOLD, BTN_SIZE));
            btnPanel.add(btn);

            buttons[row][col] = btn;
         }
      }

      setBorder(BorderFactory.createEmptyBorder(GAP, GAP, GAP, GAP));
      setLayout(new BorderLayout(GAP, GAP));
      add(textField, BorderLayout.PAGE_START);
      add(btnPanel, BorderLayout.CENTER);
   }

   private static void createAndShowGui() {
      GUIcalc2 mainPanel = new GUIcalc2();

      JFrame frame = new JFrame("Calc");
      frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
      frame.getContentPane().add(mainPanel);
      frame.pack();
      frame.setLocationByPlatform(true);
      frame.setVisible(true);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            createAndShowGui();
         }
      });
   }
}

现在为了使用布局管理器的代码之美,假设您现在想在顶部添加一行按钮来执行内存功能,例如内存清除,内存替换,内存添加,...所有你需要的do(从GUI视图的角度来看)是添加另一行String常量:

private static final String[][] BTN_TEXTS = { 
   {"MC", "MR", "MS", "M+"},  // new line !
   { "7", "8", "9", "/" },
   { "6", "5", "4", "*" }, 
   { "3", "2", "1", "+" }, 
   { "0", ".", "=", "-" } };

这样做,GUI有机会:

enter image description here

请注意,所有按钮都会调整大小以允许包含在顶行中的较大文本字符串,并且无需编写任何其他代码即可执行此操作。

尝试使用与您的代码类似的操作,并注意您必须更改所添加组件下方或右侧的所有组件的位置,以及错误和错误的风险倍增。< / p>

当然你还需要添加逻辑代码,但这是另一个讨论的主题。