Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/332.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用java swing在ImageIcon代理中显示动画gif_Java_Swing_Jlabel_Imageicon_Animated - Fatal编程技术网

使用java swing在ImageIcon代理中显示动画gif

使用java swing在ImageIcon代理中显示动画gif,java,swing,jlabel,imageicon,animated,Java,Swing,Jlabel,Imageicon,Animated,我以前写过这个 JLabel label=new JLable(URL); frame.getContentPane().add(label); 它可以与动画gif图像一起使用 但是,当我想使用imageProxy从internet加载gif表单时 它不起作用 我的代理是这个 public class ImageProxy implements Icon{ ImageIcon imageIcon; URL imageURL; Thread retrievalThread; boolean re

我以前写过这个

JLabel label=new JLable(URL);
frame.getContentPane().add(label);
它可以与动画gif图像一起使用

但是,当我想使用imageProxy从internet加载gif表单时 它不起作用

我的代理是这个

public class ImageProxy implements Icon{
ImageIcon imageIcon;
URL imageURL;
Thread retrievalThread;
boolean retrieving =false;
public ImageProxy(URL url){
    imageURL = url;
}

public int getIconHeight() {skip}
public int getIconWidth() {skip}

@Override
public void paintIcon(final Component c, Graphics g, int x, int y) {
    System.out.println("paint");
    if(imageIcon !=null){
        imageIcon.paintIcon(c, g, x, y);
    }else{
        g.drawString("Loading image", x+10, y+80);
        if(!retrieving){
            retrieving =true;
            retrievalThread = new Thread(new Runnable(){
                public void run(){
                    try{
                        imageIcon = new ImageIcon(imageURL);
                        c.repaint();
                    }catch(Exception e){
                        e.printStackTrace();
                    }
                }
            });
            retrievalThread.start();
        }
    }
}
}

它可以成功加载图像,但不会自动刷新图像 我必须通过缩放帧来改变图像, 每次我把它放大一张图片

我看了文件, 它说,为了显示gif,我需要设置ImageObsever 我试过了,没用。并且imageIcon正常工作,getImageObserver没有代理打印null

我也试着阅读源代码,但我并没有真正理解


请帮助我,谢谢。

问题的根源可能是
JLabel
实现的
ImageObserver
接口:

public boolean imageUpdate(Image img, int infoflags,
               int x, int y, int w, int h) {
    // Don't use getDisabledIcon, will trigger creation of icon if icon
    // not set.
if (!isShowing() ||
        !SwingUtilities.doesIconReferenceImage(getIcon(), img) &&
        !SwingUtilities.doesIconReferenceImage(disabledIcon, img)) {

    return false;
}
return super.imageUpdate(img, infoflags, x, y, w, h);
}
以下是
SwingUtilities.doesIconReferenceImage
的代码:

static boolean doesIconReferenceImage(Icon icon, Image image) {
Image iconImage = (icon != null && (icon instanceof ImageIcon)) ?
                   ((ImageIcon)icon).getImage() : null;
return (iconImage == image);
}
如您所见,如果图标不是
ImageIcon
的实例,
imageUpdate()
的结果将是
false
,甚至不调用super的实现,super的实现实际上负责调用
JLabel
上的
repaint()
来刷新动画图标的新帧。此外,返回
false
意味着我们对更新不再感兴趣

您可以扩展
JLabel
以克服此限制。下面是一个非常简单的
JLabel
扩展,它覆盖了
imageUpdate()
。此
imageUpdate
实现的实际代码取自
组件。imageUpdate()
,只是
isInc
incRate
为简单起见是常量:

public static class CustomLabel extends JLabel {
    private static final boolean isInc = true;
    private static final int incRate = 100;

    public CustomLabel(Icon image) {
        super(image);
    }

    @Override
    public boolean imageUpdate(Image img, int infoflags, int x, int y,
            int w, int h) {
        int rate = -1;
        if ((infoflags & (FRAMEBITS | ALLBITS)) != 0) {
            rate = 0;
        } else if ((infoflags & SOMEBITS) != 0) {
            if (isInc) {
                rate = incRate;
                if (rate < 0) {
                    rate = 0;
                }
            }
        }
        if (rate >= 0) {
            repaint(rate, 0, 0, getWidth(), getHeight());
        }
        return (infoflags & (ALLBITS | ABORT)) == 0;
    }
}
公共静态类CustomLabel扩展了JLabel{
私有静态最终布尔值isInc=true;
专用静态最终整数增量=100;
公共自定义标签(图标图像){
超级(图像);
}
@凌驾
公共布尔图像更新(图像img、int-infoflags、int-x、int-y、,
整数w,整数h){
整数率=-1;
如果((信息标志和(帧位|所有位))!=0){
比率=0;
}如果((信息标志和某些位)!=0,则为else{
如果(isInc){
比率=增加率;
如果(比率<0){
比率=0;
}
}
}
如果(速率>=0){
重新绘制(速率,0,0,getWidth(),getHeight());
}
返回(infoflags&(ALLBITS | ABORT))==0;
}
}
您可以插入
imageUpdate()
,添加在图像仍在加载时显示“加载图像”字符串的功能


我想知道为
ImageIcon
实现代理的真正原因是什么。如果需要同步图像加载,可以使用
ImageIO
API

问题的根源可能是由
JLabel
实现的
ImageObserver
接口:

public boolean imageUpdate(Image img, int infoflags,
               int x, int y, int w, int h) {
    // Don't use getDisabledIcon, will trigger creation of icon if icon
    // not set.
if (!isShowing() ||
        !SwingUtilities.doesIconReferenceImage(getIcon(), img) &&
        !SwingUtilities.doesIconReferenceImage(disabledIcon, img)) {

    return false;
}
return super.imageUpdate(img, infoflags, x, y, w, h);
}
以下是
SwingUtilities.doesIconReferenceImage
的代码:

static boolean doesIconReferenceImage(Icon icon, Image image) {
Image iconImage = (icon != null && (icon instanceof ImageIcon)) ?
                   ((ImageIcon)icon).getImage() : null;
return (iconImage == image);
}
如您所见,如果图标不是
ImageIcon
的实例,
imageUpdate()
的结果将是
false
,甚至不调用super的实现,super的实现实际上负责调用
JLabel
上的
repaint()
来刷新动画图标的新帧。此外,返回
false
意味着我们对更新不再感兴趣

您可以扩展
JLabel
以克服此限制。下面是一个非常简单的
JLabel
扩展,它覆盖了
imageUpdate()
。此
imageUpdate
实现的实际代码取自
组件。imageUpdate()
,只是
isInc
incRate
为简单起见是常量:

public static class CustomLabel extends JLabel {
    private static final boolean isInc = true;
    private static final int incRate = 100;

    public CustomLabel(Icon image) {
        super(image);
    }

    @Override
    public boolean imageUpdate(Image img, int infoflags, int x, int y,
            int w, int h) {
        int rate = -1;
        if ((infoflags & (FRAMEBITS | ALLBITS)) != 0) {
            rate = 0;
        } else if ((infoflags & SOMEBITS) != 0) {
            if (isInc) {
                rate = incRate;
                if (rate < 0) {
                    rate = 0;
                }
            }
        }
        if (rate >= 0) {
            repaint(rate, 0, 0, getWidth(), getHeight());
        }
        return (infoflags & (ALLBITS | ABORT)) == 0;
    }
}
公共静态类CustomLabel扩展了JLabel{
私有静态最终布尔值isInc=true;
专用静态最终整数增量=100;
公共自定义标签(图标图像){
超级(图像);
}
@凌驾
公共布尔图像更新(图像img、int-infoflags、int-x、int-y、,
整数w,整数h){
整数率=-1;
如果((信息标志和(帧位|所有位))!=0){
比率=0;
}如果((信息标志和某些位)!=0,则为else{
如果(isInc){
比率=增加率;
如果(比率<0){
比率=0;
}
}
}
如果(速率>=0){
重新绘制(速率,0,0,getWidth(),getHeight());
}
返回(infoflags&(ALLBITS | ABORT))==0;
}
}
您可以插入
imageUpdate()
,添加在图像仍在加载时显示“加载图像”字符串的功能

我想知道为
ImageIcon
实现代理的真正原因是什么。如果需要同步图像加载,可以使用
ImageIO
API