web-dev-qa-db-ja.com

GridLayoutJFrameを使用したJPanels内のJButton

サイズNxNのGridLayoutに設定されているJFrameが1つあります。 Nは、プログラムの開始時にコマンドラインとしてユーザーによって指定されます。 NxNパターンのJButtonは、JPanelsのウィンドウに追加され、GridLayoutによって場所が設定されます(私は思います)。

GridLayoutを使用するには、各JButtonに独自のJPanelが必要ですか?すべてのボタンに1つのJPanelを設定し、JPanelをJButtonのGridLayoutに設定できるという印象を受けています。ボタン配列の左側に別のJPanelを追加して、ボタンクリック(JLabel)と同じ左側のJPanel内のリセットボタンを表示したいと思います。

これが私のコード(の一部)です。ここで、Nはユーザーによって指定され、systemは私のバックグラウンドプロセスクラスであり、ButtonEventはActionListener/actionPerformedのクラスです。

JFrame window = new JFrame("");
GridLayout layout = new GridLayout(N,N);
window.setLayout(layout);

for (int row = 0; row < N; row++){
    for (int col = 0; col < N; col++){
        JPanel panel = new JPanel();
        JButton b = new JButton ("("+row+","+col+")");
        window.add(b).setLocation(row, col);
        panel.add(b);
        b.addActionListener(new ButtonEvent(b, system, row, col));
        window.add(panel);
    }
}

window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.pack();
window.setVisible(true);

そしてこれは私が持っているものです(N = 4):

http://i.imgur.com/nbQoM.png

これが(おおよそ)私が探しているものです(N = 4):

http://i.imgur.com/SiVWO.png

私が必要/欲しいのは、上記のように大まかに設定された2つ(またはそれ以上)のJPanelだけであり、私が試したすべてのレイアウトマネージャーはGridLayoutレイアウトJFrameでNiceをプレイしません。

8
Avertheus

ここでこのコード例を試してください:

import Java.awt.*;
import Java.awt.event.*;
import javax.swing.*;

public class LayoutExample extends JFrame
{
    private static final String INITIAL_TEXT = "Nothing Pressed";
    private static final String ADDED_TEXT = " was Pressed";
    private JLabel positionLabel;
    private JButton resetButton;
    private static int gridSize = 4;

    public LayoutExample()
    {
        super("Layout Example");
    }

    private void createAndDisplayGUI()
    {       
        setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);

        JPanel contentPane = new JPanel();
        contentPane.setLayout(new FlowLayout(FlowLayout.LEFT, 20, 20));
        contentPane.setBorder(BorderFactory.createLineBorder(Color.DARK_GRAY, 2));

        JPanel leftPanel = new JPanel();
        leftPanel.setBorder(BorderFactory.createLineBorder(Color.DARK_GRAY, 2));
        leftPanel.setLayout(new BoxLayout(leftPanel, BoxLayout.Y_AXIS));    
        JPanel labelPanel = new JPanel();
        positionLabel = new JLabel(INITIAL_TEXT, JLabel.CENTER);
        JPanel buttonLeftPanel = new JPanel();
        resetButton = new JButton("Reset");
        resetButton.addActionListener(new ActionListener()
        {
            public void actionPerformed(ActionEvent ae)
            {
                positionLabel.setText(INITIAL_TEXT);
            }
        });
        labelPanel.add(positionLabel);
        buttonLeftPanel.add(resetButton);
        leftPanel.add(labelPanel);
        leftPanel.add(buttonLeftPanel);

        contentPane.add(leftPanel);

        JPanel buttonPanel = new JPanel();
        buttonPanel.setLayout(new GridLayout(gridSize, gridSize, 10, 10));
        for (int i = 0; i < gridSize; i++)
        {
            for (int j = 0; j < gridSize; j++)
            {
                JButton button = new JButton("(" + i + ", " + j + ")");
                button.setActionCommand("(" + i + ", " + j + ")");
                button.addActionListener(new ActionListener()
                {
                    public void actionPerformed(ActionEvent ae)
                    {
                        JButton but = (JButton) ae.getSource();
                        positionLabel.setText(
                            but.getActionCommand() + ADDED_TEXT);                           
                    }
                });
                buttonPanel.add(button);
            }
        }
        contentPane.add(buttonPanel);

        setContentPane(contentPane);
        pack();
        setLocationByPlatform(true);
        setVisible(true);
    }

    public static void main(String[] args)
    {
        if (args.length > 0)
        {
            gridSize = Integer.parseInt(args[0]);
        }
        SwingUtilities.invokeLater(new Runnable()
        {
            public void run()
            {
                new LayoutExample().createAndDisplayGUI();
            }
        });
    }
}

出力:

StartAfter Click

14
nIcE cOw

GridLayoutを使用するには、各JButtonに独自のJPanelが必要ですか?

いいえ。JFrameのAddとsetLayoutは、見た目どおりには機能しません。 JFrameはトップレベルのコンテナであり、JPanelsでコンテンツを整理することをお勧めします。

パネルは次の形式で整理する必要があります。

----JPanel----------------------------|
| ---LeftPanel---  ---ButtonsPanel--- |
| |             |  |                | |
| |             |  |                | |
| |             |  | GridLayout(N,N)| |
| |             |  |                | |
| |             |  |                | |
| ---------------  ------------------ |
---------------------------------------

次に、JPanelをJFrameに追加します。また、パネルを別々のクラスに配置します。

class BPanel extends JPanel {
    public BPanel() {
        GridLayout layout = new GridLayout(N,N, hgap, vgap);
        setLayout(layout);
        for (int row = 0; row < N; row++){
            for (int col = 0; col < N; col++){
                JButton b = new JButton ("("+row+","+col+")");
                add(b).setLocation(row, col);
                b.addActionListener(new ButtonEvent(b, system, row, col));
            }
        }
    }
}
class LeftPanel extends JPanel {
....
}

class MainFrame extends JFrame {
    public MainFrame() {
        JPanel p = new JPanel();
        p.add(new LeftPanel());
        p.add(newButtonsPanel());
        add(p);
    }
}
7
KrHubert

各ボタン(またはボタンのグループ)に独自のパネルを与えることの利点の1つは、ネストされたパネルが異なるレイアウトを持つことができることです。この では、ネストされた各ButtonPanelにはデフォルトのFlowLayoutがあるため、囲んでいるコンテナのサイズが変更されても、ボタンのサイズは一定のままです。

4
trashgod