从mjpeg流中保存图像

时间:2012-09-25 13:40:02

标签: java stream jpeg mjpeg


我正试图从MJPEG流中捕获图像(jpeg)。
根据本教程http://www.walking-productions.com/notslop/2010/04/20/motion-jpeg-in-flash-and-java/ 我应该从Content-Length开始保存日期:结束于-myboundary。
但由于某种原因,当我打开一个保存的文件时,我收到此消息无法打开此图片,因为该文件似乎已损坏,已损坏或太大。

public class MJPEGParser{

    public static void main(String[] args){
        new MJPEGParser("http://192.168.0.100/video4.mjpg");
    }

    public MJPEGParser(String mjpeg_url){
        try{

            URL url = new URL(mjpeg_url);
            BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream()));
            String line;
            while((line = in.readLine()) != null){
                System.out.println(line);
                if(line.contains("Content-Length:")){
                    BufferedWriter out = new BufferedWriter(new FileWriter("out.jpeg"));
                    String content = in.readLine();
                    while(!content.contains("--myboundary")){
                        out.write(content);
                        System.out.println(content);
                        content = in.readLine();

                    }
                    out.close();
                    in.close();
                    System.exit(0);
                }
            }

            in.close();

        }catch(Exception e){
            e.printStackTrace();
        }
      }
}

我将非常感谢任何提示。

2 个答案:

答案 0 :(得分:1)

有很多事情可能导致您的代码失败:

  • 并非所有MJPEG流都以您的教程建议的MIME方式进行编码 引用Wikipedia

      

    [...]没有文件定义了一种确切的格式,这种格式被普遍认为是在所有情境中使用的“Motion JPEG”的完整规范。

    例如,可以使用MJPEG作为AVI(即RIFF)文件的视频编解码器。因此,请确保您的输入文件采用教程描述的格式。

  • 文本--myboundary几乎肯定是占位符。在典型的multipart MIME message中,全局MIME标头将提供boundary属性,指示实际用于分隔部件的字符串。你必须将--添加到那里给出的字符串。
  • 当您使用ReaderWriter时,您正在操作字符,而不是字节。根据您的语言环境,这两者之间可能没有1:1的对应关系,从而打破了流程中数据的二进制格式。您应该对字节流进行操作,或者明确地使用某些字符编码,如ISO-8859-1,其中 具有这样的1:1对应关系。

答案 1 :(得分:0)

我最近试图解决这个问题,我的谷歌研究多次将我带到这里。我最终解决了这个问题。关键部分是使用 BufferedInputStreamFileOutputStream 读取和写入 jpeg 字节,同时还将字节缓冲区连接成字符串以读取和识别帧之间的标头:

int inputLine;
String s="";
byte[] buf = new byte[1]; //reading byte by byte 

URL url = new URL("http://127.0.0.1:8080/?action=stream");
BufferedInputStream in = new BufferedInputStream(url.openStream());
OutputStream out = new FileOutputStream("output.jpg");
        
while ((inputLine = in.read(buf)) != -1) {
 
    s= s+ new String(buf, 0, inputLine);

    if (s.contains("boundarydonotcross")){
        System.out.println("Found a new header");
        s="";
    }

如果有人需要,完整的代码在这里:

https://github.com/BabelCoding/MJPEG-to-JPG