I'm having trouble getting my custom panel to show up using JLayeredPanel. I'm currently trying to create a black rectangle on the first layer, and on the second layer, I have a custom JPanel which is a slideshow of images. The slideshow will not display at all, it only works when I add it to the frame. Any thoughts?
Code:
import java.awt.Color;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.Image;
import java.awt.Toolkit;
import java.util.ArrayList;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLayeredPane;
import javax.swing.JPanel;
public class GUI extends JFrame {
private Container pane;
private JPanel emptySlideShow;
private JLayeredPane layeredPane;
public GUI(){
this.setVisible(true);
Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
this.setBounds(0,0,screenSize.width, screenSize.height);
// //Set up the content pane
// pane = this.getContentPane(); //get the content pane to place components
// pane.setLayout(null); //use absolute positioning (using Insets)
// pane.setBackground(new Color(236, 236, 236)); //color the background
//
// //Set up the main menu bar
this.emptySlideShow = new JPanel();
this.emptySlideShow.setBounds(0,0,(int)Toolkit.getDefaultToolkit().getScreenSize().getWidth(),250);
this.emptySlideShow.setBackground(new Color(0,0,0));
layeredPane = new JLayeredPane();
layeredPane.setLayout(null);
layeredPane.add(this.emptySlideShow,new Integer(0));
ArrayList<Image> slides = new ArrayList<Image>();
Image image1 = new ImageIcon("pictures/slide1.png").getImage();
slides.add(image1);
Image image2 = new ImageIcon("pictures/slide2.png").getImage();
slides.add(image2);
ArrayList<String> transitions = new ArrayList<String>();
transitions.add("PanLR");
transitions.add("FadeOut");
this.add(new SlideShow(slides,transitions));
layeredPane.add(new SlideShow(slides,transitions),new Integer(1));
this.add(layeredPane);
}
}
A guess since we don't have all of the pertinent code -- but you need to specify a component's size and position when adding it to the JLayeredPane, and so perhaps you're not setting the SlideShow's size before adding it (it's position will by default be 0, 0).
Question though: Why are you trying to add a SlideShow JPanel to the GUI twice? Once to the JLayeredPane, and the other to the JFrame itself?
Simple. You are adding the components (including JLayeredPane) to the frame AFTER you invoke
this.setVisible(true);
Move this line to the end of the constructor and you should be fine or if you really want to keep this line at the top, you should call revalidate() to update the JFrame and components.
Related
I placed two components inside a JLayeredPane but I can't make them visible. Here is a fairly MCV code. How do I see my JTextField and JLabel inside the layeredPane?
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Font;
import javax.swing.BorderFactory;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JLayeredPane;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.border.EtchedBorder;
public class GUI extends JFrame {
JFrame mainframe = new JFrame();
JPanel centrejPanel = new JPanel();
JTextField keyText;
JLabel jLabel;
public GUI() {
mainframe.setLayout(new BorderLayout());
mainframe.setSize(1200, 700);
mainframe.getContentPane().add(centrejPanel, BorderLayout.CENTER);
keyText = new JTextField("hello");
keyText.setOpaque(false);
keyText.setCaretColor(Color.BLACK);
keyText.setBorder(BorderFactory.createEtchedBorder(EtchedBorder.LOWERED));
jLabel = new JLabel("hello");
jLabel.setFont(new Font("Palatino", Font.BOLD, 18));
jLabel.setVerticalAlignment(JLabel.TOP);
jLabel.setForeground(Color.GRAY);
JLayeredPane layeredPane = new JLayeredPane();
layeredPane.add(keyText, 1);
layeredPane.add(jLabel, 0);
centrejPanel.getRootPane().add(layeredPane);
mainframe.setVisible(true);
}
}
public class Main {
public static void main(String[] args) {
GUI gui = new GUI();
}
}
//mainframe.setLayout(new BorderLayout());
Not needed. The default layout manager of the content pane of the frame is a BorderLayout.
//mainframe.getContentPane().add(centrejPanel, BorderLayout.CENTER);
Don't add an empty panel to the content pane of the frame. Just add the LayeredPane directly to the content pane.
keyText.setBounds(0, 50, 100, 20);
...
jLabel.setBounds(0, 150, 100, 20);
A JLayeredPane uses a null layout so it is your responsibility to set the size and location of each component added to the layered pane.
//centrejPanel.getRootPane().add(layeredPane);
Don't add the layered pane to the root pane. Don't even know if this will work but in any case the content pane will just cover the layered pane.
Read the section from the Swing tutorial on Using Top Level Containers to see how all the frame layers are structured.
mainframe.add(layeredPane);
Just add the layered pane directly to the content pane of the frame. Read the Swing tutorial on How to Use LayeredPane for more information and working examples.
Always start with examples from the tutorial when learning a new concept or component.
If I paint directly on the frame, it shows up fine but the ship will not show up on top of the panel...
package MoonBlast;
import java.awt.BorderLayout;
import java.awt.Dimension;
import javax.swing.JFrame;
public class Frame extends JFrame{
PlaySpace p;
Ship s;
public Frame(String title){
this.setTitle(title);
this.setSize(800, 800);
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
p = new PlaySpace();
s = new Ship();
p.add(s);
this.add(p, BorderLayout.CENTER);
this.setVisible(true);
}
}
package MoonBlast;
import java.awt.Color;
import java.awt.Dimension;
import javax.swing.JPanel;
public class PlaySpace extends JPanel {
public PlaySpace(){
super();
this.setPreferredSize(new Dimension(800, 800));
this.setBackground(Color.BLACK);
}
}
package MoonBlast;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Polygon;
import javax.swing.JComponent;
public class Ship extends JComponent{
#Override
public void paintComponent(Graphics g){
super.paintComponent(g);
Polygon p = new Polygon();
p.addPoint(350, 750);
p.addPoint(450, 750);
p.addPoint(400, 700);
g.setColor(Color.YELLOW);
g.fillPolygon(p);
}
}
The only class I left out was the 1 line viewer class. I have tried everything I could think of and a few more people have looked at it too. Thanks in advance.
You need to override the getPreferredSize() method of your Ship class to return the size of the component. Every Swing component is responsible for knowing its preferred size since it is the component that is doing the custom painting.
but the ship will not show up on top of the panel...
Your PlaySpace class using a FlowLayout by default which respects the preferred size of any component added to it. By default the preferred size of the Ship is (0, 0) so there is nothing to paint.
If I paint directly on the frame, it shows up fine
The default layout manager of the content pane of the frame is a BorderLayout. When you add a component to the CENTER of a BorderLayout, the layout ignores the preferred size of the component and just makes the component take up all the available space in the frame.
Read the section from the Swing tutorial on Layout Managers for more information and working examples of each layout manager.
I made a quick research to solve this problem but until now I found nothing regarding to this. I have one image into one TabbedPane object but when I try to align this image on the center of the label inside the TabbedPane it "Doesn't" work. The center alignment in this case works only for horizontal view but I want to be in the center of both vertical and horizontal. Check out the sample below:
import java.awt.BorderLayout;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JPanel;
import javax.swing.JTabbedPane;
import com.sh.st.gui.MainScreen;
public class test {
JTabbedPane tabbedPane = new JTabbedPane();
JFrame mainFrame = new JFrame();
public static void main (String[] args){
test t = new test();
}
public test(){
JPanel entrance = new JPanel();
JLabel lbImage1;
JMenuBar bar;
JMenu file, registerQuery;
ImageIcon Logo= new ImageIcon("rsc/img/imagem.jpg");
lbImage1= new JLabel(Logo, JLabel.CENTER);
entrance.add(lbImage1);
tabbedPane.addTab("Entrance", null, entrance);
mainFrame.getContentPane().add( tabbedPane, BorderLayout.CENTER);
bar= new JMenuBar();
file= new JMenu("File");
registerQuery= new JMenu("Request");
mainFrame.setVisible(true);
}
}
I guess its not so hard to do what I want but until now as I said, I found nothing, anyone could help please? thanks in advance
The JLabel alignment will only center horizontally due to the potitioning characteristics of its parent container. In this case it is the default layout for JPanel which is FlowLayout. This layout manager does not facilitate easy vertical alignment.
Provided that the JLabel lbImage1 will be the only component on the JPanel entrance, then GridLayout can be used to center the JLabel both horizontally and vertically:
entrance.setLayout(new GridLayout());
I am trying to re-position the button so that it is in the bottom right corner of the frame, but everything I try such as setLocation and setBounds, don't seem to do anything. Also, how would I change the button to an image? So that it is still a button, but an image is displayed.
package TrainCounselor;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Toolkit;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class Start extends JPanel {
public Start() {
// Game Properties
setOpaque(false);
setLayout(new FlowLayout());
}
public void paint(Graphics g) {
Image a = Toolkit
.getDefaultToolkit()
.getImage(
"C:/Users/Mel/workspace/camptycoon/javagame/src/javagame/background1.png");
g.drawImage(a, 0, 0, this);
super.paint(g);
}
public static void main(String[] args) {
JFrame myFrame = new JFrame("Put Image");
JButton startButton = new JButton("Start");
startButton.setLayout(null);
startButton.setLocation(50, 50);
Start c = new Start();
c.add(startButton);
myFrame.add(c);
myFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
myFrame.setTitle("Counselor Training");
myFrame.setSize(755, 600);
myFrame.setResizable(false);
myFrame.setVisible(true);
}
}
I am trying to re-position the button so that it is in the bottom right corner of the frame
Use the appropriate Layout Managers.
I would start by using a JPanel with a FlowLayout that is right aligned. Then you add this panel to the "SOUTH" of the BoderLayout which is used by the JFrame.
See A Visual Guide to Layout Managers for more information.
Note when you add the Start class to the frame you are adding it to the "CENTER", not the south. Also, custom painting is done by override the paintComponent() method, not the paint() method and don't forget to invoke super.paintComponent() before you draw the image, not after.
Also, how would I change the button to an image? So that it is still a button, but an image is displayed.
Read the section from the Swing tutorial on How to Use Buttons.
I'm just wondering why this 100x100 px .gif image isn't showing up on the screen. The image is in the same directory, so the program should have no problem finding it. Does anybody know how to solve this problem?
import java.awt.*;
import java.awt.image.ImageObserver;
import java.io.File;
import javax.imageio.*;
import javax.swing.*;
public class Window extends JFrame{
//the pictures
ImageIcon guy = new ImageIcon("tester.gif");
JLabel pn = new JLabel(guy);
JPanel panel = new JPanel();
Window(){
super("Photuris Lucicrescens");
//Important
setSize(700,600);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
add(panel);
setVisible(true);
//Decoration
Image customIcon = Toolkit.getDefaultToolkit().getImage("iconImage.gif");
setIconImage(customIcon);
//Adding the image
add(pn);
}
}
The problem is that you add two components to the JFrame. When you add a Component to a JFrame, it actually adds it to its content pane. By default, the content pane uses the BorderLayout as its LayoutManager. If you don't set a constraint, the component is considered to be in the center. Therefore, here you have two components that are in the center and receives the same bounds from the LayoutManager, resulting in only one component to be shown, the other being hidden. This is why you see the JPanel and not the JLabel.
If you want to see the JLabel, then don't add that panel to the frame.
Other remarks:
setVisible() should be invoked after you have created your component hierarchy.
I try it on my computer and image is showing up on icon. If you want show the image on background try this :
import java.awt.Image;
import java.awt.Toolkit;
import javax.swing.*;
public class Caine extends JFrame{
//the pictures
ImageIcon guy = new ImageIcon("tester.gif");
JLabel pn = new JLabel(guy);
JPanel panel = new JPanel();
Caine(){
super("Photuris Lucicrescens");
//Important
setSize(700,600);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
add(panel);
setVisible(true);
JLabel im = new JLabel(new ImageIcon("iconImage.gif"));
setIconImage(customIcon);
panel.add(im);
add(pn);
}
}