PDA

View Full Version : Beginners Java




LOST1000
Oct 24, 2010, 04:02 PM
I am a Beginners Java class and am having a lot of trouble on this assignment. Any and all help is greatly appreciated.

We are to write a program that displays a window derived from a JFrame. The JFrame should have Border layout and a JPanel in the center of the JFrame. There should be two fixed buttons on the JPanel measuring at 200px by 150 px. When a button is pressed, its color should change. The colors should cycle through five different colors, with the fifth button press cycling back to the original color.

We also need a menu of colors used for button one, which, when chosen, will change button two's color. Clicking button two will change it back to the original color.


This is what I have so far:
http://pastebin.com/vMqh4ZX2


Again, I am really, really confused, so any and ALL help is appreciated. Thank you!



lee1210
Oct 24, 2010, 04:34 PM
I'm reading from my phone so I can't compile and run that (and to be honest, don't know that much about Java UIs, more of a server guy), but good on you for posting the code.

What problems are you having? Does the code compile? If so does it crash? If not what behavior do you get and what do you expect? What resources (book, prof, TA, classmates) do you have and what have you utilized so far?

-Lee

LOST1000
Oct 24, 2010, 04:52 PM
First of all, thanks so much for taking a look at it.

I've got the program running and compiling alright, however, I'm not sure how to get the buttons to cycle through the colors.

I've got the "public void actionPerformed(ActionEvent e)" method and array of colors set as comments right now since I can't seem to understand what the problem is. When I run it as is, I'm getting the two buttons (fixed at the right size and positioning with the title), but that's about it.

plinden
Oct 24, 2010, 05:14 PM
I'm not a Java GUI programmer either (like lee1210 I'm on the server side) but it look like you are trying to associate an action with the JFrame, while it's the button that's being pressed, so you need to hook up the JFrame and the JButtons. If you want your actionPerformed method to be called when a button is pressed, you need to make your JFrame object an ActionListener (implement ActionListener) and add it as a listener to the buttons.

Take a look at this - http://download.oracle.com/javase/tutorial/uiswing/components/button.html#abstractbutton

Edit: Oh and one more thing. Use the Java coding conventions - http://www.oracle.com/technetwork/java/codeconventions-135099.html#367. All classes should start with an upper case letter, so rename your file and class to ButtonProblem.

chown33
Oct 24, 2010, 05:32 PM
For reference, this is the code I see right now:
import javax.swing.JFrame;
import javax.swing.JButton;
import java.awt.BorderLayout;
import java.awt.Color;
import javax.swing.JPanel;

import javax.swing.border.Border;
import javax.swing.border.LineBorder;

public class buttonProblem extends JFrame
{
public buttonProblem()
{

//Could not get this to work
/*
private static boolean USE_CROSS_PLATFORM_UI = false;

int buttonLabelIndex = 0;

String button1Labels[] = { "COLOR", "COLOR", "COLOR", "COLOR", "COLOR"};
Color button1Colors[] = { Color.BLUE, Color.GREEN, Color.ORANGE, Color.PINK, Color.YELLOW};
JButton button1;

String button2Labels[] = { "COLOR", "COLOR", "COLOR", "COLOR", "COLOR"};
Color button2Colors[] = { Color.BLUE, Color.GREEN, Color.ORANGE, Color.PINK, Color.YELLOW};
JButton button2;
*/

setTitle("buttonProblem");

setLayout(null);

//Set up JPanel
JPanel panel = new JPanel();
panel.setLayout(new BorderLayout());

//Set up Border
Border thickBorder = new LineBorder(Color.WHITE, 150);

//Create button1
JButton button1 = new JButton("Button 1");
panel.add(button1, BorderLayout.CENTER);

//set button size
button1.setBounds(100, 125, 200, 150);

//set button color
button1.setOpaque(true);

//create button2
JButton button2 = new JButton("Button 2");
panel.add(button2, BorderLayout.CENTER);

//set button size
button2.setBounds(300, 125, 200, 150);

//set button color
button2.setOpaque(true);

add(button1);
add(button2);

//set default window size
setSize(600, 450);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
setVisible(true);

//Could not get this to work
/*
public void actionPerformed(ActionEvent e)
{
buttonLabelIndex = ++buttonLabelIndex < button1Labels.length?buttonLabelIndex:0;
buttonLabelIndex = ++buttonLabelIndex < button2Labels.length?buttonLabelIndex:0;

button1.setText(button1Labels[buttonLabelIndex]);
button2.setText(button1Labels[buttonLabelIndex]);

if(USE_CROSS_PLATFORM_UI)
{
button1.setBackground(button1Colors[buttonLabelIndex]);
button2.setBackground(button2Colors[buttonLabelIndex]);
}
else
{
button1.setForeground(button2Colors[buttonLabelIndex]);
button2.setForeground(button1Colors[buttonLabelIndex]);
}
}
*/

}

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

}

The commented out sections don't work because they need to be outside the body of the constructor method buttonProblem().

Here is the proper basic structure:
import javax.swing.JFrame;
import javax.swing.JButton;
import java.awt.BorderLayout;
import java.awt.Color;
import javax.swing.JPanel;

import javax.swing.border.Border;
import javax.swing.border.LineBorder;

public class buttonProblem extends JFrame
{
//Could not get this to work
/*
private static boolean USE_CROSS_PLATFORM_UI = false;

int buttonLabelIndex = 0;

String button1Labels[] = { "COLOR", "COLOR", "COLOR", "COLOR", "COLOR"};
Color button1Colors[] = { Color.BLUE, Color.GREEN, Color.ORANGE, Color.PINK, Color.YELLOW};
JButton button1;

String button2Labels[] = { "COLOR", "COLOR", "COLOR", "COLOR", "COLOR"};
Color button2Colors[] = { Color.BLUE, Color.GREEN, Color.ORANGE, Color.PINK, Color.YELLOW};
JButton button2;
*/

public buttonProblem()
{

setTitle("buttonProblem");

setLayout(null);

//Set up JPanel
JPanel panel = new JPanel();
panel.setLayout(new BorderLayout());

//Set up Border
Border thickBorder = new LineBorder(Color.WHITE, 150);

//Create button1
JButton button1 = new JButton("Button 1");
panel.add(button1, BorderLayout.CENTER);

//set button size
button1.setBounds(100, 125, 200, 150);

//set button color
button1.setOpaque(true);

//create button2
JButton button2 = new JButton("Button 2");
panel.add(button2, BorderLayout.CENTER);

//set button size
button2.setBounds(300, 125, 200, 150);

//set button color
button2.setOpaque(true);

add(button1);
add(button2);

//set default window size
setSize(600, 450);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
setVisible(true);

}

//Could not get this to work
/*
public void actionPerformed(ActionEvent e)
{
buttonLabelIndex = ++buttonLabelIndex < button1Labels.length?buttonLabelIndex:0;
buttonLabelIndex = ++buttonLabelIndex < button2Labels.length?buttonLabelIndex:0;

button1.setText(button1Labels[buttonLabelIndex]);
button2.setText(button1Labels[buttonLabelIndex]);

if(USE_CROSS_PLATFORM_UI)
{
button1.setBackground(button1Colors[buttonLabelIndex]);
button2.setBackground(button2Colors[buttonLabelIndex]);
}
else
{
button1.setForeground(button2Colors[buttonLabelIndex]);
button2.setForeground(button1Colors[buttonLabelIndex]);
}
}
*/


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

}

Now you can uncomment the parts that don't work, and add an implements ActionListener to the definition of the class, then setup the listener relationship.

Java is a block-structured language. That means major structural divisions are defined by blocks of code enclosed in { }. You can't just throw code around wherever it looks nice. You have to put the { and } in the correct places. The indentation and placement of newlines is completely irrelevant to the major structure. Only the placement of { and } defines blocks.


One last thing. This is horrifying:
buttonLabelIndex = ++buttonLabelIndex < button1Labels.length?buttonLabelIndex:0;

You should use the modulo operator, designated by %:
buttonLabelIndex = (buttonLabelIndex + 1) % button1Labels.length;

I leave it to you to look this up in a language reference, so you understand what it's doing.

Ordinarily I wouldn't post a specific answer for a homework problem, but it's so horrible it makes my eyes water, and I think you can find the modulo operator in any decent book. For what it's worth, modulo is related to division, if that's not too big a clue.

Ritchie13
Oct 24, 2010, 05:37 PM
I think part of the problem may be to do with the default look and feel on the Mac. I had a similar problem when I did some Java stuff where the buttons would change colour fine on Windows and Linux but not on OS X.

plinden
Oct 24, 2010, 05:43 PM
I think part of the problem may be to do with the default look and feel on the Mac. I had a similar problem when I did some Java stuff where the buttons would change colour fine on Windows and Linux but not on OS X.

Nope. It's because his JFrame is not an ActionListener listening to the JButton actions.

chown33 - I would have just pointed the OP to http://download.oracle.com/javase/tutorial/uiswing/examples/components/ButtonDemoProject/src/components/ButtonDemo.java

Plenty to him help there while not actually doing the work for him. The Java tutorials are a great resource.

LOST1000
Oct 24, 2010, 05:54 PM
chown33, thanks for the help, and sorry for those watery eyes.

I made those corrections; however, my program is still not allowing the buttons to change colors. Here is what I have, not sure why it is still not using those lines of code.

http://pastebin.com/vMqh4ZX2

If Ritchie13 is correct, does this mean that it is possibly compiling on an OS other than Mac?

chown33
Oct 24, 2010, 07:22 PM
There may be more than one problem.

First, not every Look & Feel will allow pushbuttons to change background color. In fact, the Mac's Aqua L&F does not do this. This was noted in another post, but I'll confirm it's true so you can think about what to do about it.

Second, given the above, how would you go about confirming that actionPerformed() is actually being run when a button is clicked? Would a System.out.println() be useful? How about changing the actual text in the arrays, so something visible happens other than a color change? Or how about that USE_CROSS_PLATFORM_UI boolean? What should happen if you change it to true? What does happen?

Now, if nothing happens even after you've added some code to solve the second issue, what else might be missing? Is an action being connected to the buttons? If not, why not? Have you looked at the button example linked by plinden?

plinden
Oct 24, 2010, 09:08 PM
Try to think about what you're doing. You want your JFrame to listen for actions (ie clicks) on the buttons. The JFrame is an object, and the two JButtons are separate objects. How do the JButtons know what other objects to call actionPerformed on? It's not enough that the JFrame creates the two JButton objects. The buttons don't know yet that the JFrame is a listener.

One more thing. You say you need a JPanel, but you haven't done that.

LOST1000
Oct 25, 2010, 10:13 PM
So I'm following what is wrong, but to be honest I'm not sure how to fix these problems. It took me an embarrassingly long time to figure out this much, and I'm kind of overwhelmed (but, of course, thankful) for the input on where my mishaps are.

plinden
Oct 25, 2010, 11:04 PM
Look at the link I posted earlier. I'll do it again:
http://download.oracle.com/javase/tutorial/uiswing/examples/components/ButtonDemoProject/src/components/ButtonDemo.java

Compare it to your code. Can you see:

How the buttons find out about the listener
How the JPanel is used

LOST1000
Oct 25, 2010, 11:35 PM
Okay, so breaking that down really helped, and I think I'm getting closer. Not sure what it is I'm doing wrong now.

http://pastebin.com/H4bhApUa

Again, not sure why you're taking the time to do this, but thanks.

plinden
Oct 25, 2010, 11:50 PM
I didn't really intend for you to copy chunks of the demo code wholesale. I mean, do you know what setMnemonic does? Do you understand what the main method is doing with Runnable?

Go back to what you had before and just compare the two files. All the answers you need are there, but only use what you understand.

LOST1000
Oct 26, 2010, 01:05 AM
My program is due in an hour. I'm still working on it, but it doesn't look like I'll be able to make much more progress at my slow pace. But, again, thanks for the help, I really do appreciate it.