• 追加された行はこの色です。
  • 削除された行はこの色です。
TITLE:Animated Gifからフレーム画像を抽出する
#navi(../)
#tags(ImageIO, ImageReader, BufferedImage, Animation)
RIGHT:Posted by &author(aterai); at 2013-03-18
*Animated Gifからフレーム画像を抽出する [#g9299c8d]
``AnimatedGif``から各フレームの画像を抽出します。主に[https://forums.oracle.com/forums/thread.jspa?messageID=5386516 OTN Discussion Forums : Reading gif animation frame rates and such?]の回答を参考に作成しています。
---
category: swing
folder: ExtractFramesFromAnimatedGif
title: Animated Gifからフレーム画像を抽出する
tags: [ImageIO, ImageReader, BufferedImage, Animation, AnimatedGif]
author: aterai
pubdate: 2013-03-18T02:26:09+09:00
description: Animated GIFから各フレームの画像を抽出します。
image: https://lh4.googleusercontent.com/-_xu1jNmYJe0/UUX3d_PzwKI/AAAAAAAABoA/cyS5ABVZdkM/s800/ExtractFramesFromAnimatedGif.png
---
* 概要 [#summary]
`Animated GIF`から各フレームの画像を抽出します。主に[https://community.oracle.com/thread/1271862 Swing - Reading gif animation frame rates and such?]の回答を参考に作成しています。

-&jnlp;
-&jar;
-&zip;
#download(https://lh4.googleusercontent.com/-_xu1jNmYJe0/UUX3d_PzwKI/AAAAAAAABoA/cyS5ABVZdkM/s800/ExtractFramesFromAnimatedGif.png)

//#screenshot
#ref(https://lh4.googleusercontent.com/-_xu1jNmYJe0/UUX3d_PzwKI/AAAAAAAABoA/cyS5ABVZdkM/s800/ExtractFramesFromAnimatedGif.png)
* サンプルコード [#sourcecode]
#code(link){{
private static List<BufferedImage> loadFromStream(ImageInputStream imageStream) throws IOException {
  Iterable<ImageReader> it = () -> ImageIO.getImageReaders(imageStream);
  ImageReader reader = StreamSupport.stream(it.spliterator(), false)
      .filter(MainPanel::checkGifFormat)
      .findFirst()
      .orElseThrow(() -> new IOException("Can not read image format!"));
  reader.setInput(imageStream, false, false);
  List<BufferedImage> list = new ArrayList<>();
  for (int i = 0; i < reader.getNumImages(true); i++) {
    IIOImage frame = reader.readAll(i, null);
    list.add((BufferedImage) frame.getRenderedImage());
  }
  reader.dispose();
  return list;
}

**サンプルコード [#q1a56a3f]
#code(link){{
ImageReader reader = null;
Iterator<ImageReader> readers = ImageIO.getImageReaders(imageStream);
while(readers.hasNext()) {
  reader = readers.next();
private static boolean checkGifFormat(ImageReader reader) {
  String metaFormat = reader.getOriginatingProvider().getNativeImageMetadataFormatName();
  if("gif".equalsIgnoreCase(reader.getFormatName()) &&
            !"javax_imageio_gif_image_1.0".equals(metaFormat)) {
    continue;
  }else{
    break;
  String name;
  try {
    name = reader.getFormatName();
  } catch (IOException ex) {
    name = "";
  }
  return "gif".equalsIgnoreCase(name) && "javax_imageio_gif_image_1.0".equals(metaFormat);
}
if(reader == null) {
  throw new IOException("Can not read image format!");
}
boolean isGif = reader.getFormatName().equalsIgnoreCase("gif");
reader.setInput(imageStream, false, !isGif);
ArrayList<BufferedImage> list = new ArrayList<BufferedImage>();
for(int i=0;i<reader.getNumImages(true);i++) {
  IIOImage frame = reader.readAll(i, null);
  list.add((BufferedImage)frame.getRenderedImage());
}
reader.dispose();
}}

**解説 [#z2a7a3c4]
上記のサンプルでは、``ImageReader``に``AnimatedGif``ファイルを読み込ませて、``IIOImage#getRenderedImage()``で各フレームの``BufferedImage``を取得しています。
* 解説 [#explanation]
上記のサンプルでは、`ImageReader`に`Animated GIF`ファイルを読み込んで`IIOImage#getRenderedImage()`メソッドで各フレームの`BufferedImage`を取得しています。

- 注:
-- 背景色を無視している
-- ``try-with-resources``を使っているので、``JDK 1.7.0``以上が必要
- 背景色や差分フレームは無視している
- `try-with-resources`を使っているので`JDK 1.7.0`以上が必要

**参考リンク [#gf7bd402]
- [https://forums.oracle.com/forums/thread.jspa?messageID=5386516 OTN Discussion Forums : Reading gif animation frame rates and such?]
* 参考リンク [#reference]
- [https://community.oracle.com/thread/1271862 Swing - Reading gif animation frame rates and such?]
- [[JPEGファイルのコメントを取り出す>Swing/IIOMetadata]]
- [[JLabelに表示したAnimated Gifのアニメーションを停止する>Swing/DisableAnimatedGif]]
- [[Animated GIFでのコマ描画時処理>Swing/AnimatedGif]]

**コメント [#hade8703]
* コメント [#comment]
#comment
#comment