2013-04-01 248 views
1

我以前寫這顯示gif動畫

JLabel label=new JLable(URL); 
frame.getContentPane().add(label); 

,並與gif動畫形象工程

然而,當我想用​​一個imageProxy加載GIF格式的互聯網 它不起作用。

我imageProxy是這個

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我需要setImageObsever 我試過了,也不行。和imageIcon正常工作,沒有代理打印null getImageObserver

我也嘗試讀取源代碼,但我並不真正瞭解。

請幫助我,謝謝。

回答

1

問題的根源可能是由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,甚至沒有調用超級的實現,實際上負責調用repaint()JLabel刷新動畫圖標的新幀。此外,返回false意味着我們不再對更新感興趣。

您可以擴展JLabel以克服此限制。這是一個非常簡單的擴展JLabel,它覆蓋了imageUpdate()。本實施imageUpdate實際的代碼是從Component.imageUpdate()拍攝,只是isIncincRate是簡單的常數:

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; 
    } 
} 

您可以插入imageUpdate()增加顯示「加載圖像」串的功能,同時圖像仍在加載。

我想知道爲ImageIcon實施代理的真正原因是什麼。如果您需要同步圖片加載,則可以使用ImageIO API。