Reputation: 121
I am using my class call KButton that extends from JButton bui I add some code that make it more beautiful such as changing the font, set rounded border, change the background using Graphics and Graphics2D. However it is not work when i want to add code to make it change color when move over! my code is here
public class KButton extends JButton implements MouseMotionListener{
private static final long serialVersionUID = 1L;
public KButton(){
setStyle();
}
public KButton(String text){
super(text);
this.setText(text);
setStyle();
addMouseMotionListener(this);
}
public void setStyle(){
setFont(new Font("San Serif",Font.PLAIN,12));
setContentAreaFilled(false);
setBorder(new RoundedBorder(3));
}
@Override
protected void paintComponent(Graphics g){
Graphics2D g2 = (Graphics2D)g.create();
g2.setPaint(new GradientPaint(new Point(0, 0), Color.WHITE, new Point(0, getHeight()), Color.LIGHT_GRAY));
g2.fillRect(0, 0, getWidth(), getHeight());
g2.dispose();
super.paintComponent(g);
}
@Override
public void mouseDragged(MouseEvent arg0) {
// TODO Auto-generated method stub
}
@Override
public void mouseMoved(MouseEvent arg0) {
Graphics g=this.getGraphics();
Graphics2D g2 = (Graphics2D)g.create();
g2.setPaint(new GradientPaint(new Point(0, 0), Color.WHITE, new Point(0, getHeight()), Color.BLUE.brighter()));
g2.fillRect(0, 0, getWidth(), getHeight());
g2.dispose();
super.setText(getText());
setBorder(new RoundedBorder(3));
super.paintComponent(g);
}
}
and it seems not work!
Upvotes: 0
Views: 670
Reputation: 16302
Although @MadProgrammer's advice is true, you can omit all this burden by setting the buttons rollover image:
//In constructor
setRolloverImage(myRolloverImage);
But I'm not sure this is the exact method name, do some research.
Upvotes: 0
Reputation: 7403
Don't do painting in mouseMoved
, just set the properties to paint, and then repaint the component . Also, MouseListener provides mouseEntered and mouseExited events, which work better for this use case. :
public class KButton extends JButton {
private Color bottomBg = Color.LIGHT_GRAY;
public KButton(String text) {
super(text);
addMouseListener(this);
}
@Override
protected void paintComponent(Graphics g){
super.paintComponent(g);
Graphics2D g2 = (Graphics2D)g;
g2.setPaint(new GradientPaint(new Point(0, 0), Color.WHITE, new Point(0, getHeight()), this.bottomBg));
g2.fillRect(0, 0, getWidth(), getHeight());
}
public void mouseEntered(MouseEvent evt) {
this.bottomBg = Color.BLUE.brighter();
this.repaint();
}
public void mouseExited(MouseEvent evt) {
this.bottomBg = Color.LIGHT_GRAY;
this.repaint();
}
// add other MouseListener methods, or use a MouseAdapter
// with just those two methods overridden
}
Upvotes: 0
Reputation: 347334
Don't use getGraphics
. The approriate place to perform custom painting is within the paintComponent
method. getGraphics
is a transient reference to the graphics context last used to the paint the component, when the component is repainted, any changes will be overridden by those in the various paintXxx
methods.
You should, also, never be calling any of the paintXxx
methods yourself (unless you are trying to render the component to an image of course)
Instead, use a state flag to changes the way that paintComponent
works and call repaint
when you want to update the state.
In your case, there are at least two things that destroying your painting efforts in your mouseMoved
method, setText
and the mouse movement itself. Both of which will cause a repaint
to occur.
Personally, I would use MouseListener#mouseEntered
and MouseListener#mouseExited
instead and change the state of the button model (to rolled over for example) and then examine that value in the paintComponent
method to make my painting decisions
Also, beware that super.paintComponent
will attempt to clear the graphics context, preparing for painting and should be called first
Upvotes: 1