How to draw on subPanels created by .form? - java

I would like to draw on sub-panels, which are created by the .form. There is one "mainPanel", which contains three subPanels named panel1(top), panel2(bottom-left) and panel3(bottom-right).
Now I would like to draw something on the subPanel "panel1", but it does not work. When I run the program, it only shows the three subPanels there, but without my drawings of the "paintComponent()" method.
I pasted my code here, could anyone help me to check what is the problem? Thanks a lot.
public class PanelDrawTest extends JFrame {
private JPanel mainPanel;
private JPanel panel1;
private JPanel panel2;
private JPanel panel3;
public PanelDrawTest(){
getContentPane().add(mainPanel);
setPanel1(new MyPanel1());
}
public JPanel getMainPanel() {
return mainPanel;
}
public JPanel getPanel1() {
return panel1;
}
public void setPanel1(JPanel panel1) {
this.panel1 = panel1;
}
private class MyPanel1 extends JPanel {
public MyPanel1(){
}
#Override
public void paintComponent(Graphics g){
g.drawString("This is Panel 1",20,20);
g.drawRect(0,200,100,200);
}
}
public static void main(String args[]){
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
createAndShowGUI();
}
});
}
private static void createAndShowGUI() {
PanelDrawTest frame = new PanelDrawTest();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setBounds(50, 50, 1200, 700);
frame.setPreferredSize(new Dimension(1200,800));
frame.pack();
frame.setVisible(true);
}
}

Note: The code posted throws a NullPointerException because mainPanel was never initialized.
The constructor is not adding your custom panel to the layout and this is why it cannot be seen.
Try this and you'll see your drawing:
public PanelDrawTest() {
mainPanel = new JPanel();
getContentPane().add(mainPanel,BorderLayout.NORTH);
panel1 = new MyPanel1();
getContentPane().add(panel1,BorderLayout.CENTER);
}

Your version wasn't runnable for me, but this works:
public class PanelDrawTest extends JFrame {
private JPanel mainPanel = new JPanel(); // I added a constructor to avoid NullPointerexception
private JPanel panel1;
private JPanel panel2;
private JPanel panel3;
public PanelDrawTest(){
getContentPane().add(mainPanel);
setPanel1(new MyPanel1());
add(panel1); // and I added the panel
}
public JPanel getMainPanel() {
return mainPanel;
}
public JPanel getPanel1() {
return panel1;
}
public void setPanel1(JPanel panel1) {
this.panel1 = panel1;
}
private class MyPanel1 extends JPanel {
public MyPanel1(){
}
#Override
public void paintComponent(Graphics g){
g.drawString("This is Panel 1",20,20);
g.drawRect(0,200,100,200);
}
}
public static void main(String args[]){
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
createAndShowGUI();
}
});
}
private static void createAndShowGUI() {
PanelDrawTest frame = new PanelDrawTest();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setBounds(50, 50, 1200, 700);
frame.setPreferredSize(new Dimension(1200,800));
frame.pack();
frame.setVisible(true);
}
}

Related

Is there a way to extract which JPanel is clicked?

I'm trying to print which JPanel in JPanel array has been clicked using mouseEvent. How do I do that?
It gives me an error:
Local variable i defined in an enclosing scope must be final or effectively final
for(int i=0; i<count[0]; i++) {
p1[i] = new JPanel();
l1[lcount] = new JLabel("Panel "+(i+1));
p1[i].add(l1[lcount]);
panel_2.add(p1[i]);
lcount++;
p1[i].addMouseListener(new MouseAdapter() {
#Override
public void mouseClicked(MouseEvent e) {
System.out.println(i);
}
});
}
I want to extract the value of i and display it in another JLabel.
You can use the e.getSource() from you mouseEvent(). Just cast it to JPanel.
Here is an example.
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class MouseEventSource {
JFrame frame = new JFrame();
public static void main(String[] args) {
new MouseEventSource().start();
}
public void start() {
JPanel p1 = createPanel("Panel 1", Color.BLUE);
JPanel p2 = createPanel("Panel 2", Color.RED);
MyMouseListener ml = new MyMouseListener();
p1.addMouseListener(ml);
p2.addMouseListener(ml);
frame.setLayout(new FlowLayout());
frame.add(p1);
frame.add(p2);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
}
public JPanel createPanel(String name, Color color) {
JPanel panel = new JPanel() {
public String toString() {
return name;
}
};
panel.setBackground(color);
panel.setPreferredSize(new Dimension(250, 250));
return panel;
}
private class MyMouseListener extends MouseAdapter {
public void mouseClicked(MouseEvent e) {
// not really necessary to print toString()
JPanel panel = (JPanel) e.getSource();
System.out.println(panel);
}
}
}

Adding JPanel to JFrame didn't work

How to add JPanel to JFrame in other class?? I've tried with this code, but when I compile it, it didn't show any component in MyFrame.java (the label "Hello World"). What's wrong with my code?
(Button in MainFrame.java called the MyFrame.java)
Here's the code:
MyPanel.java (contains button and label)
public class MyPanel extends javax.swing.JPanel {
public MyPanel() {
initComponents();
myLabel.setText("Hello World");
}
}
MyFrame.java
public class MyFrame extends javax.swing.JFrame {
MyPanel myPanel = new MyPanel();
public MyFrame() {
initComponents();
this.add(myPanel);
}
}
MainFrame.java
public class MainFrame extends javax.swing.JFrame {
public MainFrame() {
initComponents();
}
private void btnCallFrameActionPerformed(java.awt.event.ActionEvent evt) {
new MyFrame().setVisible(true);
}
public static void main(String args[]) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
new MainFrame().setVisible(true);
}
});
}
}
I don't know what you have done in initComponents method. So I have changed your code a little bit.
public class MyPanel extends javax.swing.JPanel {
public MyPanel() {
initComponents();
//I don't know what you did in initComponents(); so I ve changed the layout to be sure that you didn't use null layout.
this.setLayout(new BorderLayout());
JLabel myLabel = new JLabel();
myLabel.setText("Hello World");
//adding the label in MyPanel
this.add(myLabel);
}
}
public class MyFrame extends javax.swing.JFrame {
MyPanel myPanel = new MyPanel();
public MyFrame() {
initComponents();
// added because of the former reason
this.setLayout(new BorderLayout());
this.add(myPanel);
}
}
I hope you are sure that you can call the btnCallFrameActionPerformed method with some button.

What is the proper way to swap out an existing JPanel in a JFrame with another?

I'm building a program that requires swapping out the current, visible JPanel with another. Unfortunately there seems to be multiple to go about this and all of my attempts have ended in failure. I can successfully get the first JPanel to appear in my JFrame, but swapping JPanels results in a blank JFrame.
My Main JFrame:
public class ShellFrame {
static CardLayout cl = new CardLayout(); //handles panel switching
static JFrame frame; //init swing on EDT
static MainMenu mm;
static Panel2 p2;
static Panel3 p3;
public static void main(String[] args) {
initFrame();
}
public static void initFrame() {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
frame = new JFrame();
frame.setDefaultCloseOperation(3);
frame.setLayout(cl);
mm = new MainMenu();
pp = new PlacementPanel();
//first panel added to frame will always show first
frame.add(mm, "MainMenu");
frame.pack(); //sizes frame to fit the panel being shown
frame.setVisible(true);
}
});
}
public static void switchPanel(String name) {
cl.show(frame.getContentPane(), name);
frame.pack();
}
public static void updatePanel2(/* args */) {
frame.removeAll();
p2 = new Panel2(/* args */);
frame.add(pp, "PlacementPanel");
frame.pack();
frame.validate();
frame.repaint();
}
I'm trying to use updatePanel2 to swap out the existing panel with a new Panel2 but It doesn't seem to be working. Panel2 works fine on it's own but trying to use it in conjunction with my program simply yields a blank window. Any help would be greatly appreciated!
that requires swapping out the current, visible JPanel with another
Have a look at CardLayout for a complete example of how to do it properly.
I have a Swing app which 'swaps' Panels when the user press the 'SPACE' key, showing a live plot of a running simulation. What i did goes like this:
public class MainPanel extends JPanel implements Runnable {
// Called when the JPanel is added to the JFrame
public void addNotify() {
super.addNotify();
animator = new ScheduledThreadPoolExecutor(1);
animator.scheduleAtFixedRate(this, 0, 1000L/60L, TimeUnit.MILLISECONDS);
}
public void paintComponent(Graphics g) {
super.paintComponent(g);
if (spacePressed)
plot.render(g);
else
simulation.render(g);
}
public void run() {
simulation.update();
repaint();
}
}
public class PlotView {
public void render(Graphics g) {
//draw the plot here
}
}
public class SimulationView {
public void render(Graphics g) {
//draw simulation here
}
}
This works very well for my 'show live plot' problem. And there's also the CardLayout approach, which you may turn into a new separate question if you having trouble. Good luck!
You should do .setVisible(false); to the panel which you want to be replaced.
Here is a working example, it switches the panels when you press "ENTER";
If you copy this in an IDE, automatically get the imports (shift+o in Eclipse);
public class MyFrame extends JFrame implements KeyListener {
private JButton button = new JButton("Change Panels");
private JPanel panelOnFrame = new JPanel();
private JPanel panel1 = new JPanel();
public MyFrame() {
// adding labels to panels, to distinguish them
panelOnFrame.add(new JLabel("panel on frame"));
panel1.add(new JLabel("panel 1"));
setSize(new Dimension(250,250));
setDefaultCloseOperation(EXIT_ON_CLOSE);
add(button);
add(panelOnFrame);
setVisible(true);
addKeyListener(this);
addKeyListener(this);
setFocusable(true);
}
public static void main(String[] args) {
MyFrame frame = new MyFrame();
}
#Override
public void keyPressed(KeyEvent k) {
if(k.getKeyCode() == KeyEvent.VK_ENTER){
//+-------------here is the replacement:
panelOnFrame.setVisible(false);
this.add(panel1);
}
}
#Override
public void keyReleased(KeyEvent arg0) {
}
#Override
public void keyTyped(KeyEvent arg0) {
}
}

Java GUI: button controls not Visible

I am having problem displaying my Main Menu on the screen. I don't see where the problem is. All it is displaying is a blank JFrame window. It is not showing my panel with the buttons.
Main Class:
public class Main {
public static void main(String[] args) {
GUIView gui = new GUIView();
}
}
GUIView Class:
import javax.swing.*;
import java.awt.*;
public class GUIView {
protected JFrame frame;
public GUIView() {
frame = new JFrame("Test");
frame.setVisible(true);
frame.setSize(500,500);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
MainMenu Class:
import javax.swing.*;
import java.awt.*;
public class MainMenu extends GUIView {
private JButton b1, b2, b3;
private JPanel panel;
public MainMenu() {
GridBagLayout gridbag = new GridBagLayout();
b1 = new JButton();
b2 = new JButton();
b3 = new JButton();
//Button Settings;
b1.setText("Administrator");
b2.setText("Program Leader");
b3.setText("Lecturer");
//Panel Settings
panel = new JPanel();
panel.setLayout(gridbag);
panel.add(b1);
panel.add(b2);
panel.add(b3);
panel.setVisible(true);
super.frame.add(panel);
}
}
You never create an instance of MainMenu. To fix, you could do:
public static void main(String[] args) {
GUIView gui = new MainMenu();
}
Try it this way............
public class Test1 extends JFrame {
int count;
public Test1(){
this.setSize(400,400);
MyCompo m = new MyCompo();
this.add(BorderLayout.CENTER,m);
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
class MyCompo extends JPanel{
public MyCompo() {
this.setSize(300,300);
setComponents();
//setHandlers();
}
public void paintComponent(Graphics g) {
//setComponents();
}
public void setComponents() {
this.setLayout(new GridLayout(5,4));
this.add(new Button("1"));
this.add(new Button("2"));
this.add(new Button("3"));
this.add(new Button("4"));
this.add(new Button("5"));
this.add(new Button("6"));
this.add(new Button("7"));
this.add(new Button("8"));
}
}
public static void main(String[] args){
EventQueue.invokeLater(new Runnable() {
public void run() {
Test1 t = new Test1();
t.setVisible(true);
}
});
}
}

Image on Custom JComponent is not Visible?

When I run my code it doesn't show up.
Basically I have a custom Jcomponent which I add to my JFrame or View and then create a View that makes the frame in my main method.
I already added to JFrame here is my code for the JComponent:
public class CardDisplay extends JComponent {
private Card card;
private Image cardImage;
public CardDisplay()
{
cardImage = Toolkit.getDefaultToolkit().createImage(("Phase10//res//Blue2.png"));
}
#Override
public void paint(Graphics g)
{
g.drawImage(cardImage, 125 ,200, this);
}
public class View {
public View(){
}
public void makeFrame()
{
JFrame frame = new JFrame("Phase 10");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
JPanel handPanel = new JPanel();
CardDisplay cd = new CardDisplay();
handPanel.setLayout(new FlowLayout());
frame.add(handPanel, BorderLayout.SOUTH);
handPanel.add(cd);
frame.pack();
frame.setSize(600,500);
frame.setResizable(false);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args){
View view = new View();
Game game = new Game();
view.makeFrame();
//game.run();
}
Here is the working version. The problem was mainly related to the preferred size of the component. Please note the implementation of method getPreferredSize().
If you would like to see what are the component boundaries I'd recommend using MigLayout layout manager in debug mode (the site has all necessary documentation).
public class CardDisplay extends JComponent {
private BufferedImage cardImage;
public CardDisplay() {
try {
cardImage = ImageIO.read(new File("Phase10//res//Blue2.png"));
} catch (final IOException e) {
e.printStackTrace();
}
}
#Override
public void paintComponent(final Graphics g) {
super.paintComponent(g);
g.drawImage(cardImage, 0, 0, null);
}
#Override
public Dimension getPreferredSize() {
if (cardImage == null) {
return new Dimension(100, 100);
} else {
return new Dimension(cardImage.getWidth(null), cardImage.getHeight(null));
}
}
public static class View {
public View() {}
public void makeFrame() {
final JFrame frame = new JFrame("Phase 10");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
final JPanel handPanel = new JPanel();
final CardDisplay cd = new CardDisplay();
handPanel.setLayout(new FlowLayout());
frame.add(handPanel, BorderLayout.SOUTH);
handPanel.add(cd);
frame.pack();
frame.setResizable(false);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
}
public static void main(final String[] args) {
final View view = new View();
view.makeFrame();
}
}
For JComponents, you use paintComponent instead of paint. Paint is actually used to draw components while paintComponent is used to draw images.

Categories