Saleh Feek
Saleh Feek

Reputation: 2076

JLabel: After overriding paintComponent(). How to make setText() render the text String?

I wrote a subclass of JLabel, and I override paintComponent(Graphics) method to make a gradient background color.

This is the subclass of JLabel:

import java.awt.Color;
import java.awt.Dimension;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.BorderFactory;
import javax.swing.JLabel;

public class DLabel extends JLabel
{

    Dimension size = new Dimension(70, 80);

    public DLabel()
    {
        this.setPreferredSize(size);
        this.setBorder(BorderFactory.createBevelBorder(TOP, Color.white, Color.black));
    }

    public void paintComponent(Graphics g)
    {
        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g;
        Color color1 = new Color(226, 218, 145);
        Color color2 = color1.brighter();
        int w = getWidth();
        int h = getHeight();
        GradientPaint gp = new GradientPaint(
                0, 0, color1, 0, h, color2);
        g2d.setPaint(gp);
        g2d.fillRect(0, 0, w, h);
    }

}

When I create an instance of this label it is displayed correctly, but when I use setText(String) the text is not rendered anything.

DLabel label = new DLabel();
label.setText("I am"); //No text displayed.

I tried different compilations of these methods after setting the text:

label.setOpaque(true);
label.revalidate();
label.repaint();

But nothing happed

Upvotes: 5

Views: 10157

Answers (3)

Hovercraft Full Of Eels
Hovercraft Full Of Eels

Reputation: 285405

What if you call the super.paintComponent(g) at the end of the method, so that the label draws the text after it draws the gradiant:

public void paintComponent(Graphics g) {
  // super.paintComponent(g);  // *** commented
  Graphics2D g2d = (Graphics2D) g;
  Color color1 = new Color(226, 218, 145);
  Color color2 = color1.brighter();
  int w = getWidth();
  int h = getHeight();
  GradientPaint gp = new GradientPaint(0, 0, color1, 0, h, color2);
  g2d.setPaint(gp);
  g2d.fillRect(0, 0, w, h);
  super.paintComponent(g); // *** added
}

Also, as an unrelated aside, I prefer to change this:

Dimension size = new Dimension(70, 80);

public DLabel()
{
    this.setPreferredSize(size);
    this.setBorder(BorderFactory.createBevelBorder(TOP, Color.white, 
         Color.black));
}

to this:

public static final Dimension PREF_SIZE = new Dimension(70, 80);

public DLabel()
{
    this.setBorder(BorderFactory.createBevelBorder(TOP, Color.white, 
         Color.black));
}

@Override
public Dimension getPreferredSize() {
  Dimension superDim = super.getPreferredSize();
  int width = Math.max(superDim.getWidth(), PREF_SIZE.getWidth());
  int height = Math.max(superDim.getHeight(), PREF_SIZE.getHeight()); 
  return new Dimension(width, height);
}

Upvotes: 8

Alan Yackel
Alan Yackel

Reputation: 498

When you did the paint it painted over the text. Take a look at the SwingX project. It has a JxLabel class that will do exactly what you want.

Upvotes: 4

MadProgrammer
MadProgrammer

Reputation: 347314

JLabel renders its text content within the paintComponent method.

You are, correctly, calling super.paintComponent, but are then promptly painting over it, using fillRect

Try moving the call to super.paintComponent to the end of the method (after the fillRect call) and leave the label as transparent

Upvotes: 4

Related Questions