想要一个具有透明背景的图像的JLabel

时间:2014-01-20 12:31:28

标签: java image swing icons

我在JTable的自定义渲染器中使用此图标作为JLabel。选择表格中的行时,图标背景显示为白色。

我使用paint.net创建了一个绿色三角形,并将其背景设置为白色,其alpha值为255.这是我在此代码中使用的图像,用于为JLabel创建IconImage;出于外部原因,我为图标使用不同的宽度。这是一个示例程序,展示了已完成的工作:

package spacecheck.images;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.util.ArrayList;

import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;

/**
 * represents an icon used in the directory tree; handles 'expanded' and
 * 'unexpanded' directories as well as indentation representing different
 * levels.
 * @author rcook
 *
 */
public class TreeIconExample
{
  public static int UNEXPANDED = 1;
  public static int EXPANDED = 2;

  @SuppressWarnings({"unused"})
  private void say (String msg) { System.out.println(msg); }

  private static ImageIcon expandedIcon = null;
  private static ImageIcon unexpandedIcon = null;
  private static int       iconHeight = 0;
  private static int       iconWidth  = 0;

  private static ArrayList<ImageIcon> cachedExpandedIcons = new ArrayList<ImageIcon>();
  private static ArrayList<ImageIcon> cachedUnexpandedIcons = new ArrayList<ImageIcon>();

  static
  {
    expandedIcon = new ImageIcon(TreeIconExample.class.getResource("images/Expanded.GIF"));
    unexpandedIcon = new ImageIcon(TreeIconExample.class.getResource("images/Unexpanded.GIF"));
    iconHeight = unexpandedIcon.getIconHeight();
    iconWidth =  unexpandedIcon.getIconWidth();
  }

  public TreeIconExample()  {  }

  public static void main(String ... arguments)
  {
    JFrame frame = new JFrame("icon test");
    frame.setBackground(Color.blue);
    JLabel label = new JLabel("background test");
    label.setBackground(Color.magenta);
    TreeIconExample treeIcon = new TreeIconExample();
    ImageIcon icon = treeIcon.getIcon(2, false);
    label.setIcon(icon);
    frame.add(label);
    frame.pack();
    frame.setVisible(true);
  }

  /**
   * return the icon for an expanded or unexpanded level
   * @param int level of folder relative to other levels displayed;
   * starts at 0 and increases with depth
   * @param boolean indicates whether this level is expanded or not.
   * @return ImageIcon appropriate for expansion flag and level.
   */
  public ImageIcon getIcon(int level, boolean expanded)
  {
    ImageIcon result = null;

    // generate this icon and store it in the cache before returning it.
    ImageIcon baseIcon = unexpandedIcon;
    if (expanded) { baseIcon = expandedIcon; }
    int iconH = iconHeight;
    int iconW = iconWidth*(level+1);

    BufferedImage bufferedImage = new BufferedImage(iconW,iconH,BufferedImage.TYPE_INT_ARGB);
    Graphics g = bufferedImage.getGraphics();

    g.fillRect(0, 0, iconW, iconH);
    g.drawImage(baseIcon.getImage(), iconWidth*level, 0, null);
    result = new ImageIcon(bufferedImage);

    return result;
  }
}

这是我的结果:

enter image description here

我想要做的是消除图标的白色部分;我希望它是透明的,所以JLabel的背景显示出来。我不知道为什么洋红色和蓝色都不会出现在这个节目中;如果有人关心告诉我,我会很感激。但是图像上的透明背景是我想要弄清楚的主要内容。

4 个答案:

答案 0 :(得分:5)

  

图像上的透明背景是主要的东西

它不透明的原因是明确地使用不透明的默认颜色填充它: - )

Graphics g = bufferedImage.getGraphics();
say("" + g.getColor());
g.fillRect(0, 0, iconW, iconH);

输出:

java.awt.Color[r=255,g=255,b=255]

所以要么不填充,要么使用完全/部分透明的颜色。

  

我不知道为什么洋红色和蓝色都不会出现在这个节目中;如果有人关心告诉我,我会很感激

  • (已在前面的帖子中回答)洋红色未显示,因为默认情况下标签为!opaque:表示其背景未填充其背景颜色
  • 蓝色未显示,因为您将其设置为其contentPane所覆盖的帧:默认情况下,后者是一个普通的JPanel,其不透明度默认为true,即它以其背景填充其区域

要查看蓝色,请将其设置为contentPane的背景颜色或更改其不透明度:

frame.getContentPane().setBackground(Color.blue);
// or
frame.setBackground(Color.YELLOW);
((JComponent) frame.getContentPane()).setOpaque(false);

答案 1 :(得分:1)

我认为您应该为缓冲图像的Graphics2D使用渲染提示:

Graphics2D g = bufferedImage.createGraphics();
g.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
        RenderingHints.VALUE_ANTIALIAS_ON);

另外,为什么你有fillRect?我想这不会透明。

编辑:尝试运行代码后,只删除fillRect就足以修复白色矩形问题:

enter image description here

注意:我使用的图像是在gimp中创建的GIF。

答案 2 :(得分:1)

将您的标签设置为不透明

label.setOpaque(真)。如果它不起作用。使用没有背景的PNG文件。

如果仍然无效。 您可以尝试不同的方法(比如制作一个自定义标签类来覆盖paintComponent并绘制一个三角形)。

答案 3 :(得分:0)

当你使用Graphics时,我认为你在寻找的是:

Graphics g = bufferedImage.getGraphics();
Graphics2D g2d = (Graphics2D) graphics;
g2d.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.3f));

您可以选择不透明度级别,将值0.3f更改为0到1之间。