Ausblenden einer Swing-Komponente ohne erneute Validierung des Layouts?

Wenn ich einen JFrame mit einigen Komponenten und einem Layout-Manager eingerichtet habe, der anfangs einwandfrei aussieht, und später aufgrund einer bestimmten Bedingung (z. B. durch Klicken auf eine Schaltfläche) eine dieser Komponenten verstecke, mischt der Layout-Manager alle Komponenten nochmal

Siehe Beispielcode - anfänglich erscheinen 3 Schaltflächen. Wenn Sie auf die Schaltfläche Ausblenden klicken, wird die Schaltfläche Ausblenden ausgeblendet, die beiden äußeren Schaltflächen werden jedoch zusammengedrückt. Wenn Sie auf die Show-Schaltfläche klicken, werden sie wieder auseinandergezogen, um Platz zu schaffen. Wie kann ich das verhindern, sodass Komponenten nach dem Aufruf von pack () dort verbleiben, wo sie sind, egal, ob sie später ausgeblendet werden?

In meinem realen Code mache ich das mit GridBagLayout, habe aber FlowLayout im folgenden Beispiel verwendet, weil es einfacher und weniger Code ist und genau dasselbe Verhalten zeigt.

Ich kann mir nur unangenehme Möglichkeiten vorstellen, wie z. B. .setEnabled (false) anstelle von .setVisible (false) zu verwenden und dann die paintComponent () -Methode der Komponente zu überschreiben, um die Komponente nicht zu zeichnen, wenn sie deaktiviert ist.

Es scheint das genau entgegengesetzte Problem zu hier -Hide eine Schaltfläche aus dem Layout in Java Swing - wo beschwert sich, dass versteckte Schaltflächenmache nimmt immer noch Platz in Anspruch :) Aber es gibt dort keinen Beispielcode, der zeigt, dass es auf diese Weise funktioniert.

Vielen Dank für alle Vorschläge:)

Beispiel

import java.awt.FlowLayout;
import java.awt.event.ActionEvent;

import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;

public class RevalidateWhenSetChildInvisibleExample
{
    private JButton button1;
    private JButton button2;
    private JButton button3;

    public void run ()
    {
        // Set up action
        Action hideButtonAction = new AbstractAction ()
        {
            @Override
            public void actionPerformed (ActionEvent e)
            {
                button2.setVisible (false);
            }
        };
        hideButtonAction.putValue (Action.NAME, "Hide");

        Action showButtonAction = new AbstractAction ()
        {
            @Override
            public void actionPerformed (ActionEvent e)
            {
                button2.setVisible (true);
            }
        };
        showButtonAction.putValue (Action.NAME, "Show");

        // Set up buttons
        button1 = new JButton ("Dummy");
        button2 = new JButton (hideButtonAction);
        button3 = new JButton (showButtonAction);

        // Set up content pane
        JPanel contentPane = new JPanel ();
        contentPane.setLayout (new FlowLayout ());
        contentPane.add (button1);
        contentPane.add (button2);
        contentPane.add (button3);

        // Set up frame
        JFrame frame = new JFrame ();
        frame.setContentPane (contentPane);
        frame.pack ();
        frame.setVisible (true);
    }

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

Antworten auf die Frage(2)

Ihre Antwort auf die Frage