当一个JPanel中添加了2个或多个组件时,组件就会消失



我创建了一个类SliderPanel,允许用户使用JSlider旋转图片并返回代表滑块上所选值的int。这个对象继承自JPanel,所以当我向主JPanel(creationPanel(添加两个或多个SliderPanels时,图片似乎会从GUI中消失。有没有解决这个问题的办法,我已经尝试过更改为绝对布局、嵌套面板和调整大小。

这是SliderPanel:的代码

public class SliderPanel extends JPanel
{
private JSlider slider;
private JLabel[] labelsArray;
private static final GridBagConstraints gbc = new GridBagConstraints();
private int selectedValue = 5;
private boolean isImgVisible;

/**
* Constructor which creates the JPanel and manages the changing of the 
* JSlider.
* 
* @param headerTitle The title of the Panel.
* @param window The Window object to retrieve the images from.
*/
public SliderPanel(String headerTitle, Window window)
{
setSize(new Dimension(300, 300));

labelsArray = window.getImages();

setLayout(new GridBagLayout());

// Create a header for the label slider and add it to the panel.
JLabel headerLabel = new JLabel("<HTML><U>" + headerTitle + 
"</U></HTML>");
gbc.gridx = 0;
gbc.gridy = 0;
gbc.anchor = GridBagConstraints.CENTER;
add(headerLabel, gbc);

Hashtable labels = new Hashtable();
for (int i = 0; i < 12; i++)
labels.put(i, new JLabel(String.valueOf(i)));

JPanel sliderAndImgPanel = new JPanel(new GridBagLayout());
JPanel imgPanel = new JPanel();
sliderAndImgPanel.setSize(new Dimension(200, 200));

slider = new JSlider(0, 10, 5);
slider.setLabelTable(labels);
slider.setPaintLabels(true);
slider.setPaintTicks(true);
slider.addChangeListener((ChangeEvent e) -> {
selectedValue = ((JSlider) e.getSource()).getValue();
System.out.println(selectedValue);

if (isImgVisible)
{
System.out.println("in");
sliderAndImgPanel.remove(imgPanel);
imgPanel.removeAll();
}

validate();
repaint();

JLabel pic = labelsArray[selectedValue];
pic.setPreferredSize(new Dimension(150, 150));
imgPanel.add(pic);
gbc.gridx = 0;
gbc.gridy = 0;
gbc.anchor = GridBagConstraints.CENTER;
sliderAndImgPanel.add(imgPanel, gbc);
isImgVisible = true;
validate();
window.validate();
});

JLabel pic = labelsArray[5];
pic.setPreferredSize(new Dimension(150, 150));
imgPanel.add(pic);
gbc.gridx = 0;
gbc.gridy = 0;
gbc.anchor = GridBagConstraints.CENTER;
sliderAndImgPanel.add(imgPanel, gbc);
sliderAndImgPanel.validate();

gbc.gridx = 0;
gbc.gridy = 1;
gbc.anchor = GridBagConstraints.CENTER;
sliderAndImgPanel.add(slider, gbc);

gbc.gridx = 0;
gbc.gridy = 1;
gbc.anchor = GridBagConstraints.CENTER;
add(sliderAndImgPanel, gbc);
}

/**
* This method returns the value selected on the JSlider.
* 
* @return The selected value. [0, 10] 
*/
public int getSelectedValue()
{
return selectedValue;
}
}

这里是Window类,面板被添加到JFrame:

import java.awt.GridLayout;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
public class Window extends JFrame
{
private static JLabel[] imagesArray;

public static void main(String[] args)
{
new Window();
}

public Window()
{
super("Testing");

setLayout(new GridLayout(2,1,5,5));
setSize(1000, 700);
setVisible(true);

imagesArray = loadImages();

add(new SliderPanel("test 1", this));
add(new SliderPanel("test 2", this));

}

//  Accessor method.
public static JLabel[] getImages()
{
return imagesArray;
}

// Loads images from project directory.
private static JLabel[] loadImages()
{
JLabel[] array = new JLabel[11];
// Load each image into the array.
for (int i = 0; i < 11; i++)
{
try
{
BufferedImage newImg = ImageIO.read(new File(i + ".png"));
array[i] = new JLabel(new ImageIcon(newImg));
} catch (IOException ex)
{
System.out.println("Exception: " + i);
}
}
return array;
}
}

提前感谢!

PS:以下是我上传的图片链接:

https://i.imgur.com/BvIehj5.png, 
https://i.imgur.com/f527RdK.png,
https://i.imgur.com/98mgTHr.png,
https://i.imgur.com/Jsqm08U.png,
https://i.imgur.com/0pHTDgE.png,
https://i.imgur.com/TvtEiFm.png,
https://i.imgur.com/VeEDFfn.png,
https://i.imgur.com/3rp59Oz.png,
https://i.imgur.com/AjVf9pU.png,
https://i.imgur.com/sqEO7GL.png,
https://i.imgur.com/dXlush6.png
private static JLabel[] imagesArray;

您正在为JLabel组件创建一个静态数组。

稍后,在我看来,您试图将数组中的JLabel添加到面板中:

JLabel pic = labelsArray[selectedValue];
pic.setPreferredSize(new Dimension(150, 150));
imgPanel.add(pic);

问题是Swing组件只能有一个父级。

因此,通过将JLabel添加到第二个面板,可以将其从第一个面板中移除。

不要保留一个静态的JLabel数组。

相反,保持ImageIcon的静态数组。一个图标CAN可由多个部件共享。

然后,当您想将标签添加到面板时,您可以使用ImageIcon创建一个新的JLabel。

最新更新