I need help making a program that has 2 button. A message appears “I was clicked n time!” whenever the button is clicked. Each button should have a separate click count.
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JFrame;
public class ButtonViewer
{
private static final int FRAME_WIDTH = 400;
private static final int FRAME_HEIGHT = 360;
public static void main(String[] args)
{
int counter1 = 0;
int counter2 = 0;
JFrame frame = new JFrame();
JButton button = new JButton("Click me!");
frame.add(button);
JFrame frame2 = new JFrame();
JButton button2 = new JButton("Click me too!");
frame2.add(button2);
ActionListener listener = new ClickListener();
button.addActionListener(listener);
button2.addActionListener(listener);
counter1++;
counter2++;
frame.setSize(FRAME_WIDTH, FRAME_HEIGHT);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
frame2.setSize(FRAME_WIDTH, FRAME_HEIGHT);
frame2.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame2.setVisible(true);
}
}
To start your going to need to actually add a ClickListener, by actually writing another method below like:
private class listener1 implements ActionListener{
public void actionPerformed(ActionEvent e){
counter1++;
}
}
you have 2 of these classes in this case... one per button.
The second listener would just increment the other counter, when the button is pressed.
A simple solution would be to implement the ActionListener inline. Just do:
button2.addActionListener( new ActionListener(){
...
});
When implementing the actionperfomed method in there, you can easily change the text of button2.
You don't have a call back for the action listener, therefore when you click on the button, the listen knows something is happening but don't have any instruction on what to do. Like #KingWilliam mention, this looks like homework, so looking into action listener call back should be enough to get your gears moving.
the listener is an interface, so in the implementation class, you need to make sure that the actionPerformed() method is implemented. you just need to detect the resource of the 'click' event, if it is coming from button increase the button's counter, and to the same to the button2,.
intialize two variables for the count, say count1,count2. For Button 1 register anonymous class as an event listener like this:
button1.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent ae){
count1++;
new CustomMessage(count1);
}
});
where CustomMessage should be like:
class CustomMessage extends javax.swing.JDialog{
public CustomMessage( int counter){
//...
}
}
make sure to incorporate 'counter' in your message.
Follow similarly for button2. Hope this works for you!
Best of Luck.
Related
I am a fairly new user with programming in Java with about a week and a bit experience, as of before I have been using python for about 3 years but thought to give java a try.
I have been trying to develop my skills by creating small projects and applications and am now creating a small GUI counter.
I have achieved creating the GUI with 2 buttons and a label and have tested the maths behind the application but I am struggling to work out how the ActionListener works as it feels a lot different to python when making a button have a action.
This is My Code;
package gui;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Frame;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.*;
public class GUI{
//This creates a frame or panel to contain things
public static void main(String[] args) {
//Maths To The Counter
int Counter = 0;
System.out.println(Counter);
Counter =+ 1;
System.out.println(Counter);
//Creating The Frame
JFrame frame = new JFrame();
JPanel panel = new JPanel();
panel.setBackground(Color.WHITE);
frame.getContentPane().add(panel);
//Creating The Label
JLabel label3 = new JLabel("Counter: ");
panel.add(label3);
//Button Which should have a funtion to add and display the number
JButton button = new JButton("Click Here.");
panel.add(button);
//Button to reset the counter
JButton buttonReset = new JButton("Reset Counter.");
panel.add(buttonReset);
//Set Size Of Window
frame.setSize(new Dimension(500, 400));
//Set Starting Position to centre
frame.setLocationRelativeTo(null);
//Setting a default close action
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//Set Title
frame.setTitle("Counter");
//Disable Resize
frame.setResizable(false);
//Setting if its visible
frame.setVisible(true);
//Fits frame to fit everything
frame.pack();
}
}
enter code here
I know that in python a action is in a function so that has been my logic to this problem however I have seen that I need to use the actionlistener instead and I am struggling to get my head around it.
If Someone could show me how this type of action should be implemented it would be great help, I have watch some youtube videos and done a bit of research but im still struggling to understand in my situation how to do it.
For any confussion im sorry, overall my question is how do I add a action to a button in my program that can implement my maths at the start.
As well any feedback on the structure of my code would be welcomed as I am just starting in java and I do know poor structure can lead to mistakes.
This code should work:
Basically, in the main method I am creating an instance of the class and calling a method to create the gui.
I also created an instance variable as the counter, otherwise you won't be able to update the variable in your action listener.
public class Gui {
private int counter;
// This creates a frame or panel to contain things
public static void main(String[] args) {
Gui gui = new Gui();
gui.create();
}
private void create() {
// Creating The Frame
JFrame frame = new JFrame();
JPanel panel = new JPanel();
panel.setBackground(Color.WHITE);
frame.getContentPane().add(panel);
// Creating The Label
JLabel label3 = new JLabel("Counter: ");
panel.add(label3);
// Button Which should have a funtion to add and display the number
JButton button = new JButton("Click Here.");
panel.add(button);
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
System.out.println(counter++);
}
});
// Button to reset the counter
JButton buttonReset = new JButton("Reset Counter.");
panel.add(buttonReset);
buttonReset.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
counter = 0;
}
});
// Set Size Of Window
frame.setSize(new Dimension(500, 400));
// Set Starting Position to centre
frame.setLocationRelativeTo(null);
// Setting a default close action
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// Set Title
frame.setTitle("Counter");
// Disable Resize
frame.setResizable(false);
// Setting if its visible
frame.setVisible(true);
// Fits frame to fit everything
}
}
With Lambda expressions, you can simplify your action listeners as follows:
button.addActionListener(a -> System.out.println(counter++));
buttonReset.addActionListener(a -> counter = 0);
If you want to write more than 1 statement, then you can just put your code in curly brackets:
button.addActionListener(a -> {
System.out.println(counter++);
System.out.println("doing more stuff...");
});
JButton has a function called addActionListener. You can pass on an action listener by doing this:
button.addActionListener(() -> {
// Do some logic here
});
Here, I use a lambda expression as an action listener. Within the lambda expression you can place whatever logic you want to have.
Also note that you can add multiple different action listeners to the same button. In a nutshell, the way the JButton interacts with the ActionListeners is based on the observer-pattern.
Imagine this: When the JButton is pressed, it will notify all of it's observers saying "Hey, I have been pressed". Each observer can then independently decide what to do. In case of the JButton, all observers are ActionListeners. If you add multiple ActionListeners then the JButton will notify all of them, and as a result all of their actionPerformed(ActionEvent e) functions are executed. In the example above, I used a lambda expression which then by java is interpreted as an ActionListener.
Other ways to achieve the exact same functionality are:
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
// Do some logic here
}
});
In the example above, you use an anonymous class as an actionlistener.
public class MyClass {
public MyClass() {
JButton button = new JButton("press me");
button.addActionListener(new MyActionListener());
}
private class MyActionListener implements ActionListener {
#Override
public void actionPerformed(ActionEvent e) {
// Do some logic here
}
}
}
In the example above, an inner class is used.
In a nutshell, there is a ton of ways you can make your button have functionality. Above are just a few examples of how to do so.
Does this clarify it a bit more, or do you have some remaining questions?
What is the best way to define the action a button will perform in the code? I want to be able to have one button do one action and the next button do a different action. Is this possible?
You can add action listener like this.
jBtnSelection.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
selectionButtonPressed();
}
} );
You can do this way.
JButton button = new JButton("Button Click");
button.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
//do your implementation
}
});
JButton subclasses AbstractButton, which has a method, addActionListener. By calling this method and passing it the action listener you wish to add, the action listener is added and will be called once an action is fired, either programatically, or by way of user interaction. Other listners can be added such as mouse listeners.
One way is to have your class implement ActionListener. Then implement the actionPerformed() method. Here is an example:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Driver extends JFrame implements ActionListener {
private static final long serialVersionUID = 3549094714969732803L;
private JButton button = new JButton("Click");
public Driver(){
JPanel p = new JPanel(new GridLayout(3,4));
p.add(button);
button.addActionListener(this);
add(p);
}
public static void main(String[] args){
Driver frame = new Driver();
frame.setSize(500,200);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
}
#Override
public void actionPerformed(ActionEvent e) {
System.out.println("You clicked me!");
}
}
anyone know or have an idea as to why my button disappears after i resize the applet?
this is my code:
import java.awt.event.*;
import javax.swing.*;
import acm.program.*;
public class button extends ConsoleProgram {
public void init(){
hiButton = new JButton("hi");
add(hiButton, SOUTH);
addActionListeners();
}
public void actionPerformed(ActionEvent e){
if(hiButton == e.getSource()){
println("hello") ;
}
}
private JButton hiButton;
}
I'm not sure if it is a good Idea to redefine the init-method. When I have a look at http://jtf.acm.org/javadoc/student/acm/program/ConsoleProgram.html I would expect that you have implement only the run-method. Overriding init without calling super.init() Looks strange to me.
Maybe I would be better to derive from JApplet directly for your first steps in Applet programming.
Assuming that
your ConsoleProgram extends (directly or indirectly) JApplet
You declared SOUTH as a static final variable that has the value BorderLayout.SOUTH (otherwise your code doesn't compile)
The code should work, no need to repaint (unless you would like to do some application-specific optimization). I just copied and pasted your code (by expliciting the two assumptions above), I see the applet and the button doesn't disappear on resize.
Anyway there are few "not good" things in the code:
First of all, a naming convention issue: the class name should be "Button" with the first letter capitalized (on top of that, it's a poor name for an Applet)
Second, action listeners should be attached before adding the component;
Third, as Oracle doc suggests here, the code that builds the GUI should be a job that runs on the event dispatcher thread. You can do that by wrapping the build gui code in a Runnable using a SwingUtilities.invokeAndWait(Runnable()
Have you tried calling super.init() at the start of your init() method?
Try explicitly using a layout for your Console and then use relative positioning.
To re-size a button in Applet:
public class Button extends JApplet implements ActionListener {
private JButton button;
public void init() {
Container container = getContentPane();
container.setLayout(null);
container.setBackground(Color.white);
button = new JButton("Press Me");
button.setSize(getWidth()/2,20);
button.setLocation(getWidth()/2-button.getSize().width/2, getHeight()/2-button.getSize().height/2);
container.add(button);
button.addActionListener(this);
}
public void actionPerformed(ActionEvent e) {
int width = (button.getSize().width == getWidth()/2) ? getWidth()/4 : getWidth()/2;
int height = button.getSize().height;
button.setSize(width,height);
button.setLocation(getWidth()/2-width/2, getHeight()/2-height/2);
}
}
To re-size a button in JFrame:
public class Button extends JFrame implements ActionListener {
private JButton button;
public Button(String title) {
Container container = getContentPane();
container.setLayout(null);
container.setBackground(Color.white);
setTitle(title);
setSize(400,400);
button = new JButton("Press Me");
button.setSize(getWidth()/2,20);
button.setLocation(getWidth()/2-button.getSize().width/2,
getHeight()/2-button.getSize().height/2);
container.add(button);
button.addActionListener(this);
}
public void actionPerformed(ActionEvent e) {
int width = (button.getSize().width == getWidth()/2) ? getWidth()/4 : getWidth()/2;
int height = button.getSize().height;
button.setSize(width,height);
button.setLocation(getWidth()/2-width/2, getHeight()/2-height/2);
}
public static void main(String[] args) {
Button button = new Button("Test");
button.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
button.setVisible(true);
}
}
Have you declared the repaint method...???
You are using swing. It needs to have declared a repaint.
Please define a custom repaint mwthod
I've got an array that creates buttons from A-Z, but I want to use it in a
Method where it returns the button pressed.
this is my original code for the buttons:
String b[]={"A","B","C","D","E","F","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","X","Y","Z"};
for(i = 0; i < buttons.length; i++)
{
buttons[i] = new JButton(b[i]);
buttons[i].setSize(80, 80);
buttons[i].setActionCommand(b[i]);
buttons[i].addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
String choice = e.getActionCommand();
JOptionPane.showMessageDialog(null, "You have clicked: "+choice);
}
});
panel.add(buttons[i]);
}
I wasn't sure exactly what you question was, so I have a few answers:
If you want to pull the button creation into a method - see the getButton method in the example
If you want to access the actual button when it's clicked, you can do that by using the ActionEvent.getSource() method (not shown) or by marking the button as final during declaration (shown in example). From there you can do anything you want with the button.
If you question is "How can I create a method which takes in a array of letters and returns to me the last clicked button", you should modify you question to explicitly say that. I didn't answer that here because unless you have a very special situation, it's probably not a good approach to the problem you're working on. You could explain why you need to do that, and we can suggest a better alternative.
Example:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class TempProject extends Box{
/** Label to update with currently pressed keys */
JLabel output = new JLabel();
public TempProject(){
super(BoxLayout.Y_AXIS);
for(char i = 'A'; i <= 'Z'; i++){
String buttonText = new Character(i).toString();
JButton button = getButton(buttonText);
add(button);
}
}
public JButton getButton(final String text){
final JButton button = new JButton(text);
button.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
JOptionPane.showMessageDialog(null, "You have clicked: "+text);
//If you want to do something with the button:
button.setText("Clicked"); // (can access button because it's marked as final)
}
});
return button;
}
public static void main(String args[])
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
JFrame frame = new JFrame();
frame.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
frame.setContentPane(new TempProject());
frame.pack();
frame.setVisible(true);
new TempProject();
}
});
}
}
ActionListener can return (every Listeners in Swing) Object that representing JButton
from this JButton you can to determine, getActionCommand() or getText()
I'm not sure what exactly you want, but what about storing the keys in a queue (e.g. a Deque<String>) and any method that needs to poll the buttons that have been pressed queries that queue. This way you would also get the order of button presses.
Alternatively, you could register other action listeners on each button (or a central one that dispatches the events) that receive the events in the moment they are fired. I'd probably prefer this approach, but it depends on your exact requirements.
try change in Action listener to this
JOptionPane.showMessageDialog(null, "You have clicked: "+((JButton)e.getSource()).getText());
1. First when you will be creating the button, please set the text on them from A to Z.
2. Now when your GUI is all ready, and you click the button, extract the text on the button, and then display the message that you have clicked this button.
Eg:
I am showing you, how you gonna extract the name of the button pressed, i am using the getText() method
butt.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e)
{
JOptionPane.showMessageDialog(null, "You have clicked: "+butt.getText());
}
});
In our code we have a 10 by 10 button array.
We made the 10 by 10 array using a nested for loop, and we have no issue creating the buttons.
Also, we have it so that when a button a is clicked it displays "Button Clicked". But how can we identify which button was clicked?
We're using actionListeners and actionPerformed methods.
You can call the getSource() method on the event.
Or you can use Action classes in your buttons and create a new instance of each when you build the buttons.
Put all the buttons in a list (easily accomplished in the inner loop), make the list available to the ActionListener (eg. as a property of the outer class; I do not know how your numerous team arranged the listeners, so I cannot provide any details). Then call:
int buttonIndex = listWithButtons.indexOf(event.getSource())
If one of you wants to know the exact coordinates of the button, they can be calculated by the formulas:
int row = buttonIndex / 10;
int col = buttonIndex % 10;
I'm assuming this is a JButton. You can use setActionCommand("command" + row + "-" + column). Then in the listener just say getActionCommand() to see which button was clicked.
Two simples solutions, but probably not the best ones :
The button class implementing its own listener.
You can also just test each button to see if it equals the action.getSource() object.
Or simply cast (ButtonClass) to the getSource() to be able to use the retrieved button.
You can use getActionCommand just like this:
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class TestButtons extends JPanel {
private static final long serialVersionUID = 1L;
public TestButtons() {
JButton btn1 = new JButton("Btn1");
btn1.addActionListener(new ButtonListener());
add(btn1);
JButton btn2 = new JButton("Btn2");
btn2.addActionListener(new ButtonListener());
add(btn2);
}
public static void main(String[] args) {
JFrame frame = new JFrame();
frame.getContentPane().add(new TestButtons());
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(200, 200);
frame.setVisible(true);
}
}
class ButtonListener implements ActionListener {
ButtonListener() {
}
public void actionPerformed(ActionEvent e) {
System.out.println(e.getActionCommand()+ " has been clicked");
}
}
We ended up using a nested for loop inside of actionPerformed that ran through the 2d array and called the action methods from there. It probably isn't the best solution, and it's probably best to use a different technique, but it seems to work just fine.
Though there are some really nice ideas in here, thank you guys!