Problem With cardlayout

I'm trying to get a card layout to work to display my multiple panels so that I can use it in a project I am working on. I have a JFrame and on that JFrame is a JPanel that will load the cards. I can get all of the cards that are within the same class to load fine. However I have quite a few panels that are very different and I don't want to stick it all into one class. Right now I can get the card (panel) from another class to load fine, but when I click its button to load another card that is where the program dies. I put a print statement in the function just to make sure the program is getting there and it is, but it just isn't loading the new panel.

Here is my code for the frame where I can get everything to load fine:

/*

package layout;

import javax.swing.*;

import java.awt.*;

public class CardLayoutFrameTest extends javax.swing.JFrame {

/** Creates new form CardLayoutFrameTest */

public CardLayoutFrameTest(){

initComponents();

initOtherClassComponents();

}

/** This method is called from within the constructor to

* initialize the form.

* WARNING: Do NOT modify this code. The content of this method is

* always regenerated by the Form Editor.

*/

// <editor-fold defaultstate="collapsed" desc=" Generated Code ">

privatevoid initComponents(){

LoaderPanel =new javax.swing.JPanel();

Card1Panel =new javax.swing.JPanel();

Card2Button =new javax.swing.JButton();

Card2Panel =new javax.swing.JPanel();

Card1Button =new javax.swing.JButton();

Card4Panel =new javax.swing.JPanel();

Change2Card1Button =new javax.swing.JButton();

Change2Card2Button =new javax.swing.JButton();

setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);

LoaderPanel.setLayout(new java.awt.CardLayout());

LoaderPanel.setBackground(new java.awt.Color(255, 255, 204));

LoaderPanel.setMaximumSize(new java.awt.Dimension(400, 225));

LoaderPanel.setMinimumSize(new java.awt.Dimension(400, 225));

LoaderPanel.setPreferredSize(new java.awt.Dimension(400, 225));

Card1Panel.setBackground(new java.awt.Color(153, 0, 0));

Card2Button.setText("Go to Card2");

Card2Button.addActionListener(new java.awt.event.ActionListener(){

publicvoid actionPerformed(java.awt.event.ActionEvent evt){

Card2ButtonActionPerformed(evt);

}

});

org.jdesktop.layout.GroupLayout Card1PanelLayout =new org.jdesktop.layout.GroupLayout(Card1Panel);

Card1Panel.setLayout(Card1PanelLayout);

Card1PanelLayout.setHorizontalGroup(

Card1PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(Card1PanelLayout.createSequentialGroup()

.add(187, 187, 187)

.add(Card2Button)

.addContainerGap(168, Short.MAX_VALUE))

);

Card1PanelLayout.setVerticalGroup(

Card1PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(org.jdesktop.layout.GroupLayout.TRAILING, Card1PanelLayout.createSequentialGroup()

.addContainerGap(167, Short.MAX_VALUE)

.add(Card2Button)

.add(128, 128, 128))

);

LoaderPanel.add(Card1Panel,"card1");

Card2Panel.setBackground(new java.awt.Color(0, 204, 204));

Card1Button.setText("Go to Card4");

Card1Button.addActionListener(new java.awt.event.ActionListener(){

publicvoid actionPerformed(java.awt.event.ActionEvent evt){

Card1ButtonActionPerformed(evt);

}

});

org.jdesktop.layout.GroupLayout Card2PanelLayout =new org.jdesktop.layout.GroupLayout(Card2Panel);

Card2Panel.setLayout(Card2PanelLayout);

Card2PanelLayout.setHorizontalGroup(

Card2PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(Card2PanelLayout.createSequentialGroup()

.add(30, 30, 30)

.add(Card1Button)

.addContainerGap(325, Short.MAX_VALUE))

);

Card2PanelLayout.setVerticalGroup(

Card2PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(Card2PanelLayout.createSequentialGroup()

.add(30, 30, 30)

.add(Card1Button)

.addContainerGap(265, Short.MAX_VALUE))

);

LoaderPanel.add(Card2Panel,"card2");

Card4Panel.setBackground(new java.awt.Color(255, 153, 0));

Change2Card1Button.setText("Card3 in Other Class");

Change2Card1Button.addActionListener(new java.awt.event.ActionListener(){

publicvoid actionPerformed(java.awt.event.ActionEvent evt){

Change2Card1ButtonActionPerformed(evt);

}

});

Change2Card2Button.setText("Card1");

Change2Card2Button.addActionListener(new java.awt.event.ActionListener(){

publicvoid actionPerformed(java.awt.event.ActionEvent evt){

Change2Card2ButtonActionPerformed(evt);

}

});

org.jdesktop.layout.GroupLayout Card4PanelLayout =new org.jdesktop.layout.GroupLayout(Card4Panel);

Card4Panel.setLayout(Card4PanelLayout);

Card4PanelLayout.setHorizontalGroup(

Card4PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(Card4PanelLayout.createSequentialGroup()

.add(74, 74, 74)

.add(Change2Card1Button)

.add(68, 68, 68)

.add(Change2Card2Button)

.addContainerGap(42, Short.MAX_VALUE))

);

Card4PanelLayout.linkSize(new java.awt.Component[]{Change2Card1Button, Change2Card2Button}, org.jdesktop.layout.GroupLayout.HORIZONTAL);

Card4PanelLayout.setVerticalGroup(

Card4PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(Card4PanelLayout.createSequentialGroup()

.add(62, 62, 62)

.add(Card4PanelLayout.createParallelGroup(org.jdesktop.layout.GroupLayout.BASELINE)

.add(Change2Card1Button)

.add(Change2Card2Button))

.addContainerGap(233, Short.MAX_VALUE))

);

Card4PanelLayout.linkSize(new java.awt.Component[]{Change2Card1Button, Change2Card2Button}, org.jdesktop.layout.GroupLayout.VERTICAL);

LoaderPanel.add(Card4Panel,"2buttoncard");

org.jdesktop.layout.GroupLayout layout =new org.jdesktop.layout.GroupLayout(getContentPane());

getContentPane().setLayout(layout);

layout.setHorizontalGroup(

layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(layout.createSequentialGroup()

.add(58, 58, 58)

.add(LoaderPanel, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 446, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)

.addContainerGap(61, Short.MAX_VALUE))

);

layout.setVerticalGroup(

layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(layout.createSequentialGroup()

.add(34, 34, 34)

.add(LoaderPanel, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 318, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)

.addContainerGap(42, Short.MAX_VALUE))

);

java.awt.Dimension screenSize = java.awt.Toolkit.getDefaultToolkit().getScreenSize();

setBounds((screenSize.width-573)/2, (screenSize.height-428)/2, 573, 428);

}// </editor-fold>

privatevoid Change2Card2ButtonActionPerformed(java.awt.event.ActionEvent evt){

//Go to Card1

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel,"card1");

}

privatevoid Change2Card1ButtonActionPerformed(java.awt.event.ActionEvent evt){

//Go to Card3 in another class

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel,"anotherclass");

}

privatevoid initOtherClassComponents()

{

LoaderPanel.add(myDifClassCard,"anotherclass");

}

privatevoid Card1ButtonActionPerformed(java.awt.event.ActionEvent evt){

//Go to Card4

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel,"2buttoncard");

//CardLoad();

}

privatevoid Card2ButtonActionPerformed(java.awt.event.ActionEvent evt){

//Go to Card2

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel,"card2");

}

publicvoid CardLoad()

{

//Load Card4 from another class

System.out.println("Program Flow Passed");

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel,"2buttoncard");

}

/**

* @param args the command line arguments

*/

publicstaticvoid main(String args[]){

java.awt.EventQueue.invokeLater(new Runnable(){

publicvoid run(){

new CardLayoutFrameTest().setVisible(true);

}

});

}

// Variables declaration - do not modify

private javax.swing.JButton Card1Button;

private javax.swing.JPanel Card1Panel;

private javax.swing.JButton Card2Button;

private javax.swing.JPanel Card2Panel;

private javax.swing.JPanel Card4Panel;

private javax.swing.JButton Change2Card1Button;

private javax.swing.JButton Change2Card2Button;

private javax.swing.JPanel LoaderPanel;

// End of variables declaration

DifClassCard myDifClassCard =new DifClassCard();

}//End CardLayoutFrameTest

Here is my code for the other class that I can get to load, but can't get anything to load when I push its button:

package layout;

import javax.swing.*;

import java.awt.*;

publicclass DifClassCardextends javax.swing.JPanel{

/** Creates new form DifClassCard */

public DifClassCard(){

initComponents();

}

/** This method is called from within the constructor to

* initialize the form.

* WARNING: Do NOT modify this code. The content of this method is

* always regenerated by the Form Editor.

*/

// <editor-fold defaultstate="collapsed" desc=" Generated Code ">

privatevoid initComponents(){

DescriptionLabel =new javax.swing.JLabel();

OtherClassButton =new javax.swing.JButton();

setBackground(new java.awt.Color(153, 255, 153));

setMaximumSize(new java.awt.Dimension(400, 225));

setMinimumSize(new java.awt.Dimension(400, 225));

setPreferredSize(new java.awt.Dimension(400, 225));

DescriptionLabel.setText("Card from another class");

OtherClassButton.setText("Go to Card1 in another class");

OtherClassButton.addActionListener(new java.awt.event.ActionListener(){

publicvoid actionPerformed(java.awt.event.ActionEvent evt){

OtherClassButtonActionPerformed(evt);

}

});

org.jdesktop.layout.GroupLayout layout =new org.jdesktop.layout.GroupLayout(this);

this.setLayout(layout);

layout.setHorizontalGroup(

layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(layout.createSequentialGroup()

.add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(layout.createSequentialGroup()

.add(130, 130, 130)

.add(DescriptionLabel))

.add(layout.createSequentialGroup()

.add(104, 104, 104)

.add(OtherClassButton)))

.addContainerGap(127, Short.MAX_VALUE))

);

layout.setVerticalGroup(

layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)

.add(layout.createSequentialGroup()

.add(47, 47, 47)

.add(DescriptionLabel)

.add(30, 30, 30)

.add(OtherClassButton)

.addContainerGap(111, Short.MAX_VALUE))

);

}// </editor-fold>

privatevoid OtherClassButtonActionPerformed(java.awt.event.ActionEvent evt){

//Go to a card in another class

//Go to Card1

CardLayoutFrameTest myMainCard =new CardLayoutFrameTest();

myMainCard.CardLoad();

}

// Variables declaration - do not modify

private javax.swing.JLabel DescriptionLabel;

private javax.swing.JButton OtherClassButton;

// End of variables declaration

}//End DifClassCard

Hopefully that isn't too confusing, thanks for any suggestions in advance.

[17680 byte] By [Bleara] at [2007-11-27 8:11:23]
# 1

A couple of general observations.

a) most of use don't use IDE's to build GUI's (its easier to control when you do it manually), therefore we don't have access to GroupLayout (unless we are using JDK6). So posting code generated from an IDE limits the number of people that can actually test the code

b) Learn to use the Standard Java naming conventions. Your code is hard to read because you don't follow the conventions. In particular variable names don't start with a capital letter.

> CardLayoutFrameTest myMainCard = new CardLayoutFrameTest();

> myMainCard.CardLoad();

I don't believe you should be creating a second instance of the frame. You should be passing in the reference of the from to this class when you create it.

camickra at 2007-7-12 19:55:21 > top of Java-index,Desktop,Core GUI APIs...
# 2

I reworked the program a little so I wouldn't be creating two instances of anything. I have added a third class to initialize everything and to start the program. The problem I am getting now is that when I click the button to jump to a card back on the frame I am getting a nullexceptionpointer error even though the variable was previously initialized to the main frame. Sometime in between when it was initialized and when it is actually used its value gets changed to null.

Here is my new class:

package layout;

import layout.CardLayoutFrameTest;

import layout.DifClassCard;

public class ProgramStart {

DifClassCard myDifClassCard;

CardLayoutFrameTest myMainCardLayout;

/** Creates a new instance of ProgramStart */

public ProgramStart() {

//Initialize the different class card

myDifClassCard = new DifClassCard();

myMainCardLayout = new CardLayoutFrameTest(myDifClassCard);

//Now that main has been initialized we can pass it to DifClassCard

myDifClassCard = new DifClassCard(myMainCardLayout);

javax.swing.SwingUtilities.invokeLater(new Runnable() {

public void run() {

myMainCardLayout.setVisible(true);

}

});

}

public static void main(String[] args) {

new ProgramStart();

}

}//End ProgramStart

Changes made to DifClassCard. I have cut out the code to set up the panel as it hasn't changed and is above:

package layout;

import javax.swing.*;

import java.awt.*;

public class DifClassCard extends javax.swing.JPanel {

//Constructor to initialize components

public DifClassCard() {

initComponents();

}

//Constructor pass in the frame

public DifClassCard(CardLayoutFrameTest mainFrame) {

myMainFrame = mainFrame;

}

private void OtherClassButtonActionPerformed(java.awt.event.ActionEvent evt) {

//Go to a card in another class

//Go to Card1

myMainFrame.CardLoad();

}

// Variables declaration - do not modify

private javax.swing.JLabel DescriptionLabel;

private javax.swing.JButton OtherClassButton;

// End of variables declaration

private CardLayoutFrameTest myMainFrame;

}//End DifClassCard

Here is my main frame code with the code to set up the frame cut out as it hasn't changed

package layout;

import javax.swing.*;

import java.awt.*;

public class CardLayoutFrameTest extends javax.swing.JFrame {

/** Creates new form CardLayoutFrameTest */

public CardLayoutFrameTest(DifClassCard classCard) {

myDifClassCard = classCard;

initComponents();

initOtherClassComponents();

}

private void Change2Card2ButtonActionPerformed(java.awt.event.ActionEvent evt) {

//Go to Card1

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel, "card1");

}

private void Change2Card1ButtonActionPerformed(java.awt.event.ActionEvent evt) {

//Go to Card3 in another class

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel, "anotherclass");

}

private void initOtherClassComponents()

{

LoaderPanel.add(myDifClassCard, "anotherclass");

}

private void Card1ButtonActionPerformed(java.awt.event.ActionEvent evt) {

//Go to Card4

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel, "2buttoncard");

//CardLoad();

}

private void Card2ButtonActionPerformed(java.awt.event.ActionEvent evt) {

//Go to Card2

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel, "card2");

}

public void CardLoad()

{

System.out.println("Program Flow Passed");

//LoaderPanel = new javax.swing.JPanel();

//LoaderPanel.setLayout(new java.awt.CardLayout());

CardLayout cl = (CardLayout)(LoaderPanel.getLayout());

cl.show(LoaderPanel, "2buttoncard");

}

// Variables declaration - do not modify

private javax.swing.JButton Card1Button;

private javax.swing.JPanel Card1Panel;

private javax.swing.JButton Card2Button;

private javax.swing.JPanel Card2Panel;

private javax.swing.JPanel Card4Panel;

private javax.swing.JButton Change2Card1Button;

private javax.swing.JButton Change2Card2Button;

private javax.swing.JPanel LoaderPanel;

// End of variables declaration

private DifClassCard myDifClassCard;

}//End CardLayoutFrameTest

The problem is occuring when myMainFrame.CardLoad(); is being called after the button on DifClassCard is being pressed. I ran through it with a debugger and myMainFrame at one point was initialized.

Thanks in advance for any advice/suggestions.

Bleara at 2007-7-12 19:55:21 > top of Java-index,Desktop,Core GUI APIs...
# 3

> myDifClassCard = new DifClassCard();

> myMainCardLayout = new CardLayoutFrameTest(myDifClassCard);

> myDifClassCard = new DifClassCard(myMainCardLayout);

a) When you create the DifClassCard the reference to the main frame is null

b) you then create a CardLayoutFrameTest with a reference to the DifCardClass that points to a null frame.

c) you create a second DifClassCard. This does not affect the existing CardLayoutFrameTest class. It still points to the first DifClassCard which has a null pointer.

I really don't understand your design. Usually you build your frame first. Then in the main frame code you build the child panels. If the child panels need a reference to the frame then you can use SwingUtilities.windowForComponent(..) method.

camickra at 2007-7-12 19:55:21 > top of Java-index,Desktop,Core GUI APIs...
# 4

When I walk through the program with the debugger that isn't happening.

myDifClassCard = new DifClassCard(); initializes a panel of DifClassCard and does not return null.

Then I send myMainCardLayout = new CardLayoutFrameTest(myDifClassCard); with the panel that was just created so that the frame knows which panel to grab when it later does its processing. This leaves myMainCardLayout as being initialized. In the debugger it is not showing as null.

Then when I use myDifClassCard = new DifClassCard(myMainCardLayout); it assigns the value of myMainCardLayout to a frame variable in the class. I can see the variable hold a value but then somewhere it loses the value before getting to call CardLoad();

Bleara at 2007-7-12 19:55:21 > top of Java-index,Desktop,Core GUI APIs...
# 5

"Usually you build your frame first. Then in the main frame code you build the child panels. "

I don't want to build all of the child panels in the main frame code. For the application I will build I have around 20 different panels that the user can possibly get to. I want each of these panels to be its own class but be loaded onto the main frame.

Bleara at 2007-7-12 19:55:21 > top of Java-index,Desktop,Core GUI APIs...