Обновите максимизированные границы JFrame, сохраняя их максимизированными - PullRequest
3 голосов
/ 08 февраля 2012

Можно ли обновить максимизированные границы JFrame (видимым образом) после вызова setMaximizedBounds (), пока JFrame максимизируется?

// I do not have access to / cannot change the following lines
JFrame frame = new JFrame();
frame.setVisible(true);
frame.setExtendedState(JFrame.MAXIMIZED_BOTH); 
// frame fills the whole screen at this point

// My code:
frame.setMaximizedBounds(newBounds);

В настоящее время я делаю следующее, чтобы обновить местоположение и размер JFrame:

frame.setExtendedState(JFrame.NORMAL);
frame.setExtendedState(JFrame.MAXIMIZED_BOTH); 

, но это приводит к тому, что окно визуально восстанавливается, а затем снова максимизируется, но с правильными максимальными границами.

Я пробовал frame.doLayout() и frame.getContentPane().doLayout(), но фрейм необновить до новых границ.

РЕДАКТИРОВАТЬ SSCCE:

Адаптировано с здесь .

Как упоминалось в комментариях, JFrameфактически создается и инициализируется RCP NetBeans, поэтому я не могу переопределить его (как предлагается здесь ) в качестве обходного пути для ошибка Java 4737788 (для которой я пытаюсь создать обходной путь),Обходной путь работает, но я хотел бы избежать (взломать) восстановления и максимизации для обновления фрейма.

import java.awt.FlowLayout;
import java.awt.Frame;
import java.awt.GraphicsConfiguration;
import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JFrame;
import sun.java2d.SunGraphicsEnvironment;


public class MaximizedBoundsTest {

    public static void main(String[] args) {
        final JFrame frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(800, 600);
        frame.setLayout(new FlowLayout());
        frame.add(new JButton(new AbstractAction("Fix Maximized Bounds") {

            @Override
            public void actionPerformed(ActionEvent e) {
                // Workaround for http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4737788
                // to take Windows taskbar into account
                GraphicsConfiguration config = frame.getGraphicsConfiguration();
                Rectangle usableBounds = SunGraphicsEnvironment.getUsableBounds(config.getDevice());
                frame.setMaximizedBounds(usableBounds);

                // Hack to update frame size & location (is there a better way to do this?)
                frame.setExtendedState(Frame.NORMAL);
                frame.setExtendedState(Frame.MAXIMIZED_BOTH);
            }
        }));
        frame.setExtendedState(Frame.MAXIMIZED_BOTH);
        frame.setUndecorated(true);
        frame.setVisible(true);
    }
}

1 Ответ

3 голосов
/ 08 февраля 2012

Редактировать: О, не видел, что вы не можете переопределить создание фрейма, и уже нашел это решение. В этом случае я бы проверил / отправил сообщение об ошибке в Netbeans, как переопределить создание JFrame.

Вот мой обходной путь для этой ошибки. PortingUtils в Jide OSS, и я считаю, что не использует закрытый API, но вы можете использовать свой собственный расчет границ там.

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;

import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JFrame;


public class TestUndecoratedFrame {

    public static void main(String[] args) {
        final JFrame frame = new JFrame() {
            @Override
            public synchronized void setExtendedState(int state) {
                // undecorated covers task bar - http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4737788
                if (isUndecorated()
                        && (state & MAXIMIZED_BOTH) == MAXIMIZED_BOTH) {
                    super.setMaximizedBounds(com.jidesoft.utils.PortingUtils.getScreenBounds(this, true));
                }
                super.setExtendedState(state);
            }
        };
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(800, 600);
        frame.setUndecorated(true);
        frame.getContentPane().add(new JButton(new AbstractAction("Toggle maximize") {
            @Override
            public void actionPerformed(ActionEvent e) {
                int state = frame.getExtendedState();
                if((state & JFrame.MAXIMIZED_BOTH) == JFrame.MAXIMIZED_BOTH) {
                    frame.setExtendedState(JFrame.NORMAL);
                }
                else {
                    frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
                }
            }
        }), BorderLayout.PAGE_END);
        frame.setVisible(true);
    }
}
...