Я пишу приложение для просмотра изображений с центральной областью, содержащей изображение, плюс панели инструментов и т. Д. c. вокруг него.
Я выбрал GridBagLayout для необходимой мне гибкости, но как только главное окно уменьшается, вместо появления полос прокрутки вокруг изображения вся область прокрутки сворачивается до области 0x0px.
Ниже приведен минимальный код, иллюстрирующий это. Попробуйте оставить размеры 500x500 и уменьшить окно на несколько пикселей, перетащив один из его углов внутрь:
import javax.swing.*;
import java.awt.*;
public class ScrollTest3 {
private static final int IMG_WIDTH = 500; // 50 or 500 or 2000
private static final int IMG_HEIGHT = 500; // 50 or 500 or 2000
private static GridBagConstraints getScrollPaneConstraints() {
GridBagConstraints c = new GridBagConstraints();
c.gridx = 0;
c.gridy = 1;
c.weightx = 1;
c.weighty = 1;
// With the next line, shrinking the window makes scrollbars appear ok,
// ... but making it larger causes the scrollpane to stick at the top left
// Without the next line, enlarging the window keeps image centered,
// ... but making it smaller causes the scrollpane to collapse
//c.fill = GridBagConstraints.BOTH;
return c;
}
public static void addComponentsToPane(Container container) {
container.setLayout(new GridBagLayout());
// Add top bar
container.add(new JLabel("This would be a top bar with information"), new GridBagConstraints());
// Prepare main image panel
JPanel imagePanel = new JPanel() {
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
// Image replaced by a shape for demonstration purpose
g2d.drawOval(0, 0, IMG_WIDTH, IMG_HEIGHT);
}
public Dimension getMinimumSize() {
return new Dimension(IMG_WIDTH, IMG_HEIGHT);
}
public Dimension getPreferredSize() {
return new Dimension(IMG_WIDTH, IMG_HEIGHT);
}
public Dimension getMaximumSize() {
return new Dimension(IMG_WIDTH, IMG_HEIGHT);
}
};
JScrollPane scrollableImagePanel = new JScrollPane(imagePanel);
container.add(scrollableImagePanel, getScrollPaneConstraints());
}
private static void limitAppSize(JFrame frame) {
frame.pack();
Dimension preferred = frame.getSize();
GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
Rectangle bounds = env.getMaximumWindowBounds();
preferred.width = Math.min(preferred.width, bounds.width);
preferred.height = Math.min(preferred.height, bounds.height);
frame.setSize(preferred);
}
private static void createAndShowGUI() {
JFrame frame = new JFrame("ScrollTest3");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
addComponentsToPane(frame.getContentPane());
limitAppSize(frame);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> createAndShowGUI());
}
}
Как вы можете видеть в закомментированной строке, это можно «исправить», указав GridBagConstraints .BOTH для поля "заполнить", но тогда изображения меньшего размера (попробуйте с 50x50) больше не центрируются: - (
Есть ли способ указать это:
- если изображение меньше, чем область отображения, оно должно быть центрировано
- если изображение больше, чем область отображения, область прокрутки должна заполнять всю область отображения
?