• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Jeanne Boyarsky
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Rob Spoor
  • Devaka Cooray
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Carey Brown
  • Frits Walraven
  • Tim Moores
Bartenders:
  • Mikalai Zaikin

Buttons not displaying till I mouseover them?

 
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi folks,

I'm new to the forums and to Java. I just finished reading through Head First Java, which was pretty good at giving me a base, as I look into more advanced/in-depth books. I set out to make a Tic-tac-toe (Cross and Noughts) game to test my learning so far. While things have gone pretty well so far, I am absolutely stumped by my current issue. When I compile and run the code, the Grid of buttons that I generate do not appear. However, if I mouse over the window, they seem to then get refreshed/repainted. I cannot for the life of me figure out why this is happening. From Googling the issue, it seems this is either an issue with the layout manager or related to a thread conflict with the GUI? (http://java.sun.com/products/jfc/tsc/articles/threads/threads1.html)

I would really appreciate if someone could help explain why this is happening and what I should do to fix the issue. Also, any other suggestions for my code/best practices would be most appreciated. I'm listing out the code for the game class and the button class.



 
Bartender
Posts: 1104
10
Netbeans IDE Java Ubuntu
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Ryan,
Welcome to the Ranch!

Straightaway, when I simply use JButton instead of your CNButton, the buttons are displaying for me.

You are using 2 variables x and y in your class - JButton extends JComponent which extends Container which extends Component - this Component class already has 2 fields declared - x & y - and they are 'int' too. By declaring your own fields with the same name of the super class, you are simply hiding the super class fields. So, whatever purpose the super-class were used goes for a toss.

why do you extend JButton and create a class? what is the purpose of it?
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Ranga,

thanks for your reply. I wasn't aware that I was conflicting with x,y fields from the Component class. However, I renamed x & y instance variables in the CNButton class to xv, yv , but I am still having the same issue, so it would appear that my issue is perhaps unrelated?

With regards to why I am extending JButton to CNButton, I was hoping to create instance variables with the x,y co-ordinate and value for each button object, so I thought that extending JButton would be the right approach? In retrospect, I can get away with using JButtons and having separate array instance variables in the main game class that record the x-y co-ordinates and values for each button.

Since posting this, I've managed to finish up the program and I can successfully play a game for an NxN board. However, I still have this issue with only a single button being displayed when I run the program, and having to hover over the window to make all the other buttons appear on mouseOver. I'm very puzzled by this, although, admittedly, my knowledge in the area of Swing and GUIs is fairly limited at the moment.
 
Bartender
Posts: 5167
11
Netbeans IDE Opera Java
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
1. All Swing components should be constructed on the EDT (also applies to chancing their internal state).
2. Learn to use Layouts and stop worrying about coordinates.
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Darryl Burke wrote:1. All Swing components should be constructed on the EDT (also applies to chancing their internal state).
2. Learn to use Layouts and stop worrying about coordinates.


Hi Darryl. Thanks for your reply. Could you help me out a bit further by pointing out what I could do specifically to construct all my Swing components within the EDT? Unfortunately the book (Head First Java) didn't talk about Event Dispatch Threads for GUI applications, and while I can understand why this is creating troubles (due to the single threaded nature of GUI operations in Swing), I am unsure about which part of my code is using the EDT and which part is running in some other thread that is causing conflicts.

I am trying to read through the Swing tutorials on the oracle website, but I'm still confused at the moment. Perhaps I will understand things more clearly once I have read a different reference book and spent some more time on this, but I would really appreciate some specific help/outline for what would fix my current code in the mean time. Thanks a lot!
 
Marshal
Posts: 28193
95
Eclipse IDE Firefox Browser MySQL Database
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Following on from what Ranganathan Kaliyur Mannar said, you are overriding the getX() and getY() methods of JButton. The documentation for the getX method says

Returns the current x coordinate of the component's origin.


And like Darryl Burke said, you shouldn't be doing that. Especially since your buttons are already in that GridLayout which is supposed to be controlling the location of the buttons. So call those methods something else.
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hooray! Thanks so much Paul, Darryl and Ranga! :-)

Paul, that helped clarify what Ranga mentioned. I didn't realize that getX() and getY() were defined methods that I was overriding. I renamed the methods and instance variables x & y and it is working perfectly now. Also, to clear up the confusion, I am indeed using the Grid Layout manager for arranging the buttons. My getX() and getY() methods were intended as a means of getting the grid position of the button on my tic-tac-toe grid, not the actual co-ordinates of the button. In any case, I've decided to refine my code and get rid of these methods and instance variables as they are unnecessary.

While I'mglad to have this resolved, I'm curious as to why overriding the getX() and getY() was causing this issue? As I understand method overriding, since I am calling these methods on the CNButton objects, the overriding getX() and getY() method that I defined in CNButton should be the one to be called. It seems that this is indeed the case because the program was working correctly (apart from the buttons needing to be moused over for display) even when I had the getX() and getY() methods in Class CNButton. Why would changing the name of these methods to prevent method overriding from occuring resolve this issue? Is it some subtlety involving which threads are used to call these methods in the two scenarios?
 
Paul Clapham
Marshal
Posts: 28193
95
Eclipse IDE Firefox Browser MySQL Database
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Something deep down in the Swing code will have been calling getX() to find out where the x-coordinate of your component is located. You overrode that method to return the wrong information. That would lead to problems in displaying your component. Which is what you observed, no?
 
Paul Clapham
Marshal
Posts: 28193
95
Eclipse IDE Firefox Browser MySQL Database
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ryan Sykes wrote:In any case, I've decided to refine my code and get rid of these methods and instance variables as they are unnecessary.



In fact, as far as I can see your action listener doesn't care much about which button was clicked. What I mean to say is, it doesn't care whether it's the button in row 1, column 3 or the button in row 2, column 2 -- it does the same regardless. So you don't need a separate action listener for each button, you can get away with a single action listener which you attach to all of the buttons.
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Paul, forgive me if I sound dense. I just want to make sure I truly understand why this is happening so I can avoid similar mistakes in the future.

If I understand what you wrote correctly, you're saying that even though my code itself is not explicitly calling getX() or getY(), the Swing code is probably calling those methods deep down somewhere when initializing the main JFrame for displaying all the GUI elements and that is what is causing the conflict and issue? That makes sense to me now. I was not considering what Swing methods are being called in the background unbeknownst to me.

That must still imply that the Swing code was calling getX() and getY() on the CNButton object and not a parent object, as the latter case would result in a call to the original JComponent getX() and getY() methods? Does that sound correct? (I'm just trying to make sure I have understood method overriding and inheritance correctly)

Thanks a ton! I'm definitely going to be scouring the Java docs for any naming conflicts when writing any future code.

Edit -

Paul Clapham wrote:

Ryan Sykes wrote:In any case, I've decided to refine my code and get rid of these methods and instance variables as they are unnecessary.



In fact, as far as I can see your action listener doesn't care much about which button was clicked. What I mean to say is, it doesn't care whether it's the button in row 1, column 3 or the button in row 2, column 2 -- it does the same regardless. So you don't need a separate action listener for each button, you can get away with a single action listener which you attach to all of the buttons.



That is an excellent point Paul. Thanks for pointing that out. I will try to change that so I have a single listener for all buttons.
 
Paul Clapham
Marshal
Posts: 28193
95
Eclipse IDE Firefox Browser MySQL Database
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ryan Sykes wrote:That must still imply that the Swing code was calling getX() and getY() on the CNButton object and not a parent object, as the latter case would result in a call to the original JComponent getX() and getY() methods? Does that sound correct? (I'm just trying to make sure I have understood method overriding and inheritance correctly)



Well, yeah. That's how inheritance and polymorphism work. There's no such thing as a "parent object" anyway -- your CNButton is a JButton, there isn't some separate hidden JButton when you create a CNButton. There's only one object, which is a CNButton and is a JButton and is a JComponent and is whatever other classes are in the inheritance chain.
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Perfect. Yes, that was silly of me, and now that I think about it, it all makes sense :-). Thanks a ton for all your help!
 
Darryl Burke
Bartender
Posts: 5167
11
Netbeans IDE Opera Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Ryan Sykes wrote:Hi Darryl. Thanks for your reply. Could you help me out a bit further by pointing out what I could do specifically to construct all my Swing components within the EDT?


You're welcome.

Search this forum for SwingUtilities.invokeLater and you'll find plenty of examples. To further your understanding, go through the tutorial on Concurrency in Swing.
 
Ryan Sykes
Ranch Hand
Posts: 58
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Darryl Burke wrote:

Ryan Sykes wrote:Hi Darryl. Thanks for your reply. Could you help me out a bit further by pointing out what I could do specifically to construct all my Swing components within the EDT?


You're welcome.

Search this forum for SwingUtilities.invokeLater and you'll find plenty of examples. To further your understanding, go through the tutorial on Concurrency in Swing.


Thanks Darryl. I already have that page bookmarked and will try to go through it over the weekend :-).
 
Greenhorn
Posts: 1
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Not meaning to resurrect a dead thread, but I just wanted to post my thanks to Paul, Ranganathan and Ryan. I was doing some googling around to find this annoying bug and this eventually came up. This was EXACTLY my problem. I extended JButton, added int variable x and y members, added getX() and getY() member functions. Once I changed these, the problem vanished I did this because the location of the button in respect to the grid/array was all the information I needed. I decided it was worth creating an account just to post my thanks and I too should read through some of this material.
 
Marshal
Posts: 79178
377
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Welcome to the Ranch
It shows that old posts are still useful.
 
Greenhorn
Posts: 2
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
hi everyone ,
i got the same problem today, I searched in web and i got this question here , but i didn't get answer to my question
actually i am working with netbeans ide and this is my code snippet i added for generating a new button and text filed in my gui

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

javax.swing.JTextField jt;
javax.swing.JButton bs;
jt = new javax.swing.JTextField("text field");

bs = new javax.swing.JButton("new button");
bs.setLocation(100,200);
bs.setSize(150,50);

jt.setLocation(100, 120);
jt.setSize(60,60);
panel.add(jt);
panel.add(bs);
panel.revalidate();
validate();
panel.setVisible(true);
}


but i my new button is not visible until mouse is moved on it.......

according to the previous answers given by someone i tried to check whether i am overridding anything but i am not but why this is happening in my code
please help
thanks in advance
 
Campbell Ritchie
Marshal
Posts: 79178
377
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Welcome to the Ranch

Don't use set size or set position methods except on top‑level containers. Use a layout manager.
Don't use a listener to add or remove components. Add them in the constructor, initGUI method or similar.
You probably don't need validate or revalidate then.
 
harinath kanchu
Greenhorn
Posts: 2
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
THANkS Campbell Ritchie FOR YOUR REPLY,

but according to one of my friends sugussetion I just added one more statement that is "repaint();" at the end of the method and now it is working fine.

I am working with java very recently so i need to improve my conceptual knowledge in java.

anyhow i will consider your sugesstion and will try to improve my code.

this site is helping me well.....
 
Politics is a circus designed to distract you from what is really going on. So is this tiny ad:
a bit of art, as a gift, the permaculture playing cards
https://gardener-gift.com
reply
    Bookmark Topic Watch Topic
  • New Topic