I would like to have a jframe with the text on the left(JLabel) and button on the right. I added the text first and would like to try not to set the frame to right to left.
EndFrame code ... uses information from other class and other classes update the JLabel.
public class endFrame extends JFrame
{
public endFrame()
{
setSize(500,75);
setLayout(new FlowLayout());
add(board.winner);
JButton r = new JButton("Reset");
r.addActionListener(board.mouse);
add(r);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
}
}
MadProgrammer showed me that using Container#add(Comonent, int) allows you to move the objects in the correct order that you want.
Related
I have two components ready to add to frame:
class Lamina extends JPanel{
public Lamina(){
setLayout(new BorderLayout(50,50));
JPasswordField user_password = new JPasswordField();
add(user_password, BorderLayout.SOUTH);
}
}
class DOMHeader extends JPanel
{
public DOMHeader()
{
setLayout(new BorderLayout());
JLabel title = new JLabel("Sign in");
add(title, BorderLayout.NORTH);
}
}
This is my class UI:
public class UI {
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
// TODO code application logic here
Frame frame = new Frame();
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setResizable(true);
frame.setTitle("Metin2");
}
}
Frame class:
class Frame extends JFrame {
public Frame() {
Toolkit screen = Toolkit.getDefaultToolkit();
Dimension screenSize = screen.getScreenSize();
int widthScreen = screenSize.width;
int heightScreen = screenSize.height;
setBounds((widthScreen/4/2),(heightScreen/4/2),(widthScreen/2/2), (heightScreen/2/2));
Image icon = screen.getImage("icon.jpeg");
setIconImage(icon);
/* Add to Components to frame*/
add(new DOMHeader());
add(new Lamina());
}
}
In my class Frame I'm adding the components shown earlier, but it "put on top of" a component another component.
According to the API:
public Component add(Component comp,int index)
Adds the specified component to this container at the given position
(index).
I run the main method:
As you can see it only show the Component DOMHeader class: add(new DOMHeader())
And what happened with add(new Lamina())
What number or Constant I should give it ?
This line:
class Frame extends JFrame {
is incorrect for the following reasons:
It's confusing because of AWT Frame class
It extends JFrame but you never change the behavior of the JFrame later, so no need to extend JFrame but create it inside of class
Now, we must head to JFrame class in which says:
The default content pane will have a BorderLayout manager set on it.
Now, if we go to the visual guide for layout managers in the BorderLayout section we can see the following image:
Which shows us that we can only add our components to 5 locations:
PAGE_START (or NORTH)
LINE_START (or WEST)
CENTER
LINE_END (or EAST)
PAGE_END (or SOUTH)
To answer your question:
According to the API:
public Component add(Component comp,int index)
Adds the specified component to this container at the given position (index).
What number or Constant I should give it ?
Well you need to add it as follows:
JFrame frame = new JFrame("Write your title here"); //Follow first advice
frame.add(new DOMHeader(), BorderLayout.NORTH); //These are the constants.
frame.add(new Lamina(), BorderLayout.SOUTH);
You confused yourself by adding the items in their locations in their own JPanels not on the JFrame itself.
Side note: Why are you doing these weird calculations?
setBounds((widthScreen/4/2),(heightScreen/4/2),(widthScreen/2/2), (heightScreen/2/2));
Wouldn't it be clearer if you called: widthScreen / 8?
As per #camickr comment:
There is no need for the DOMHeader and Lamina classes. You don't need to extend JPanel just to add a component to the frame. The "content pane" of a JFrame is a JPanel, so you can just add the label and text field to the frame as shown above.
You can also have your code improved in this way:
JFrame frame = new JFrame("Your title here");
JLabel title = new JLabel("Sign in");
JPasswordField userPassword = new JPasswordField(); //changed variable name to userPassword instead of user_password to follow Java naming conventions
frame.add(title, BorderLayout.NORTH);
frame.add(userPassword, BorderLayout.SOUTH);
frame.setVisible(true); //This line should be the last one or you'll find yourself with strange "bugs" when your application starts until you move it or resize it
No need to create a whole new JPanel for each component.
I have to align a button on my program to the exact middle, the current code I have runs it but displays the button as large as the program, I am wanting a center button that is a specific size, here is what I tried
/**
* Created by Timk9 on 11/04/2016.
*/
import javax.swing.*;
import java.awt.*;
public class Test extends JFrame {
{
JFrame window = new JFrame("Test");
window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
window.setResizable(true);
window.setSize(600, 600);
window.setVisible(true);
window.setLocationRelativeTo(null);
JPanel p = new JPanel(new GridBagLayout());
//Button does not appear until I resize the program?
JButton b1 = new JButton("Click here");
GridBagConstraints c = new GridBagConstraints();
p.add(b1);
window.add(p);
}
public static void main(String[] args) {
new Test();
}
}
JPanel p = new JPanel(new GridBagLayout());
You create a panel with a GridBagLayout which is a good layout manager to use to center the component.
p.add(b1);
But then you add the button to the panel without using any contraints.
The code should be:
p.add(b1, c);
//Button does not appear until I resize the program?
All components should be added to the frame BEFORE the frame is made visible. The setVisible(...) statement should be the last statement of the constructor.
Also could you point out which part is an instance initializer block, I thought I was using a constructor
See the FrameDemo example from the Swing tutorial on How to Make Frames for a better way to structure your code so you follow Swing conventions. Start with the working code and make the changes to add your panel containing the button, instead of using the JLabel. Note you no longer need to use the getContentPane() method, you can just add the panel directly to the frame.
It is the LayoutManager that defines how components are layed out where and how big. GridLayout which you are using e. g. divides the available space in equal grid fields and makes the components completely fill this space which is why your button is as big as your application. See here for more info about LayoutManagers: https://docs.oracle.com/javase/tutorial/uiswing/layout/visual.html
Btw. your code is not compilable: new JButton("he"),JButton.ALIGN_CENTER)
I have created a JScrollPane with a JPanel inside it and I want to add JPanel/JLabel/Other objects after pressing the button. For example after three button presses I want to get something like this:
I tried myJPane.add(testLabel) with testlabel.setBounds()but no result, I don't want to use GridLayout because of the unchangeable sizes. I would like it if the added objects had different sizes - adjusted to the text content.
What should I use for it and how?
Thanks in advance.
Best regards,
Tom.
Here is a JPanel inside a JScrollPane that adds JLabels to it when pressing the button:
public class Example extends JFrame {
public Example() {
JPanel boxPanel = new JPanel();
boxPanel.setLayout(new BoxLayout(boxPanel, BoxLayout.PAGE_AXIS));
JTextField textField = new JTextField(20);
JButton sendButton = new JButton("Send");
sendButton.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
JLabel label = new JLabel(textField.getText());
label.setOpaque(true);
label.setBackground(Color.RED);
boxPanel.add(label);
boxPanel.add(Box.createRigidArea(new Dimension(0,5)));
textField.setText("");
boxPanel.revalidate();
// pack();
}
});
JPanel southPanel = new JPanel();
southPanel.add(textField);
southPanel.add(sendButton);
add(new JScrollPane(boxPanel));
add(southPanel, BorderLayout.PAGE_END);
setDefaultCloseOperation(EXIT_ON_CLOSE);
pack();
setLocationRelativeTo(null);
setVisible(true);
}
public static void main(String[] args) {
new Example();
}
}
The BoxLayout will stack the labels on top of each other.
Notes:
setOpaque(true) must be called on label for it to honor the background color.
Box.createRigidArea is used for creating gaps. Use it as you wish.
The call to revalidate() is imperative in order to display the new components immediately.
Calling pack() (on the JFrame) will resize it each time to fit all the new components. I just put it there for demonstration since the initial frame size is too small to display the initial components added.
I will use a BoxLayout, creating a vertical box, and after each button action, it will add a new JPanel to this box.
Example:
public class YourChat extends JPanel{
private JScrollPane sc;
private Box bv;
public YourChat(){
bv = Box.createVerticalBox();
sc = new JScrollPane(bv);
//your functions (panel creation, addition of listeners, etc)
add(sc);
}
//panel customized to have red backgroud
private class MyPanel extends JPanel(){
private JLabel label=new JLabel();
public MyPanel(String text){
setBackgroundColor(Color.red);
add(label);
}
}
//inside the action listener
public void actionPerformed(ActionEvent e) {
sc.add(new MyPanel(textField.getText()));
textField.setText("");
}
}
For extra information check on:
[https://docs.oracle.com/javase/tutorial/uiswing/layout/box.html]
See also the example
[http://www.java2s.com/Code/Java/Swing-JFC/VerticalandhorizontalBoxLayouts.htm]
Use BoxLayout if you want only add vertically, otherwise you can use FlowLayout for both directions.
I have two JPanel a and b.By default a is set as ContentPane.Jpanel a has a button on it which when clicked changes contentPane to panel b.But I want it to panel 'b' to slideIn or fade-In smoothly instead of sudden change.
Here is the code (in case necessary)
class GUI extends JFrame implements ActionListener
{
JPanel a,b;
JButton button;
GUI()
{
super("Sliding Layout");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setVisible(true);
button=new JButton("Slide");
button.addActionListener(this);
a=new JPanel();
a.setBackground(Color.RED);
a.add(button);
b=new JPanel();
b.setBackground(Color.GREEN);
b.add(new JLabel("New Content Pane"));
setSize(800,400);
setContentPane(a);
}
public void actionPerformed(ActionEvent e)
{
button.setText("Changed");
//what should I do here to change the contentPane to panel 'b' with green color
//with either slide-in-from -right or fade-in effect?
}
}
After searching I found that Universal Tween Engine and Sliding Layout are two possible options.But Sliding Layout is I suppose based on Changing the grid cells but I want to change entire contentPane.So Tween Engine is the option but I tried to understand about an hour but no success.
I have attached the jars to my project.Can anyone of you please provide a code snippet or exact tutorial.
Thanks in advance.
You can use this http://java-sl.com/tip_slider.html approach. It's based on CardLayout extension.
I'm working on large scale program. As you can see I have one main JFrame and about 20 menu items on that. Each menu item must pop up a new window. At the beginning I have created a JLayeredPanel and then I assigned each menu item to one JPanel which is inside JFrame.Then I put 25 panel in JLayeredPanel... Default all the panels are set to invisible like:
panel1.setVisible(false);
panel2.setVisible(false);
so on
When user click on one menu item, its JPanel will be visible and rest are invisible. It looks messy and I have 5000 lines code. I used InternalFrame and TabbedPane but I'm not happy with them. I want to split my code in different JPanel classes and assign them to the main JFrame. I mean when user clicked on each menu item it will call the external JPanel and render it on the JPanel on the main JFrame. I am using design mode in netbeans and it does everything for me but the simpled structure is like this and it is not working:
public class NewJPanel extends JPanel{
//I have added buttons and etc on this panel
......
}
public class frame extends JFrame(){
JPanel panel = new JPanel();
.....
Public frame(){
frame.add(panel);
}
......
//When use click on the any button on the panel
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
//this is not working
NewJPanel fi = new NewJPanel ();
panel1.add(fi);
//or I tested this way separately but it did not work
panel1.remove();
panel1 = new NewJPanel();
add(panel);
invalidate();
}
}
please give me any suggestion how I can control this program in splited classes in professional way.
remove JPanel from JFrame.getContentPane.remove(myPanel)
add a new JPanel with constants, everyhing depends of used LayoutManager and its methods implemented in API
call JFrame.(re)validate() and JFrame.repaint() as last code lines, if everything is done, these notifiers correctly repaint available area
again to use CardLayout, there isn't signoficant performance or memory issue
Please give me any suggestion how I can control this program in splited classes in proressional way.
Ok.
You should put all of your JPanels in a JTabbedPane. The JTabbedPane would be added to the JFrame.
The JFrame, JTabbedPane, and each JPanel would be constructed in a separate class.
You use Swing components, rather than extending them. The only reason you extend a Swing component is if you override one of the component methods.
You should also create model classes for each of the JPanels, as well as a model class for the application.
Read this article to see how to put a Swing GUI together.
make's code better
public class NewJPanel extends JPanel{
//I have added buttons and etc on this panel
......
}
public class frame extends JFrame(){
JPanel panel = new JPanel();
.....
Public frame(){
//frame.add(panel); you dont need call frame because extends JFrame in frame class
add(panel);
......
//When use click on the any button on the panel
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
//this is not working
NewJPanel fi = new NewJPanel();
add(fi);
//or I tested this way separately but it did not work
/*panel1.remove();
panel1 = new NewJPanel();
add(panel);
invalidate();you must define panel1 before use it,like :JPanel panel1 = new JPanel();*/
}
}