2012-02-17 16 views
27

Qualcuno può consigliare una libreria Java che mi consenta di creare un video a livello di programmazione? In particolare, sarebbe effettuare le seguenti operazioni:Libreria Java consigliata per la creazione di un video a livello di programmazione

  • prendere una serie di BufferedImages come fotogrammi
  • permettono uno sfondo WAV/MP3 da aggiungere
  • permettono WAV/MP3 'accessori' da aggiungere al arbitrariamente, a livello di programmazione punti specificati
  • uscita il video in un formato comune (MPEG, ecc)

qualcuno può consigliare qualcosa? Per il mixaggio di immagine/suono, vivrei persino con qualcosa che ha preso una serie di frame e per ogni frame ho dovuto fornire i byte grezzi di dati audio non compressi associati a quel frame.

P.S. Non deve nemmeno essere una "libreria di terze parti" in quanto tale se Java Media Framework ha le chiamate per ottenere quanto sopra, ma dalla mia memoria abbozzata ho la sensazione che non sia così.

+0

Si può provare questo. http://wiki.xuggle.com/MediaTool_Introduction – Ovilia

+0

Ho guardato Xuggle, ma non sembra quasi un rompicoglioni da installare. Non sei sicuro del motivo per cui queste persone hanno un blocco mentale con il solo darti un jar/dll/exe da scaricare ... –

+0

P.S. Una soluzione che ho per ora - in attesa di qualcosa di meglio - è di salvare i frame come ad es. I file PNG chiamano quindi l'utilità ffmpeg della riga di comando sui frame. Suppongo che sia effettivamente ciò che una biblioteca potrebbe fare sotto il cofano comunque. –

risposta

5

Ho utilizzato il codice indicato di seguito per eseguire correttamente gli elementi 1, 2 e 4 nella lista dei requisiti in puro Java. Vale la pena dare un'occhiata e probabilmente potresti capire come includere # 3.

http://www.randelshofer.ch/blog/2010/10/writing-quicktime-movies-in-pure-java/

+0

Questo è sicuramente funzionalmente vicino alle specifiche che ho citato. Per come la vedo io, il principale svantaggio è che esso amalgama efficacemente i singoli fotogrammi piuttosto che usare un codec video, così si finisce con file più grandi. D'altra parte, mi piace l'idea che non ci siano problemi di brevetto. –

4

ho trovato uno strumento chiamato ffmpeg che può convertire i file multimediali da un formato ad un altro. C'è un filtro chiamato libavfilter in ffmpeg che è il sostituto di vhook che permette al video/audio di essere modificato o esaminato tra il decodificatore e l'encoder. Penso che dovrebbe essere possibile inserire frame grezzi e generare video. Ho ricercato su qualsiasi implementazione java di ffmpeg e ho trovato la pagina "Getting Started with FFMPEG-JAVA" che è un wrapper JAVA su FFMPEG che usa JNA.

+0

Grazie - lo controllerò sicuramente ad un certo punto! –

-1

Prova JavaFX.

JavaFX include il supporto per il rendering di immagini in più formati e il supporto per la riproduzione di audio e video su tutte le piattaforme in cui è supportato JavaFX.

Here è un tutorial sulle immagini manipolare

Here è un tutorial sulla creazione di presentazioni, scadenze e scene.

Here è domande frequenti sull'aggiunta di suoni.

La maggior parte di questi sono su JavaFX 1.3. Ora JavaFX 2.0 è fuori.

0

Perché non utilizzare FFMPEG?

Sembra che ci sia un wrapper Java per esso:

http://fmj-sf.net/ffmpeg-java/getting_started.php

Ecco un esempio di come compilare varie fonti dei media in un unico video con FFMPEG:

http://howto-pages.org/ffmpeg/#multiple

E , infine, i documenti:

http://ffmpeg.org/ffmpeg.html

+0

Quindi al momento sto usando FFMPEG, anche se in un modo un po 'goffo perché non ho capito come usare tutte le opzioni. ATM Sto salvando tutti i fotogrammi come immagini in una cartella, quindi eseguendo FFMPEG su di essi. Presumo che ci sia un modo per collegare i frame direttamente uno alla volta a FFMPEG senza doverli salvare, ma non l'abbiamo ancora capito. Pensavo che ci potrebbe essere già una biblioteca che ha fatto questo, per esempio. –

1

È possibile provare una libreria di codec Java pura denominata JCodec.
Ha un codificatore H.264 (AVC) molto semplice e un muxer MP4. Ecco un codice di esempio completo preso dai loro campioni - TranscodeMain.

private static void png2avc(String pattern, String out) throws IOException { 
    FileChannel sink = null; 
    try { 
     sink = new FileOutputStream(new File(out)).getChannel(); 
     H264Encoder encoder = new H264Encoder(); 
     RgbToYuv420 transform = new RgbToYuv420(0, 0); 

     int i; 
     for (i = 0; i < 10000; i++) { 
      File nextImg = new File(String.format(pattern, i)); 
      if (!nextImg.exists()) 
       continue; 
      BufferedImage rgb = ImageIO.read(nextImg); 
      Picture yuv = Picture.create(rgb.getWidth(), rgb.getHeight(), ColorSpace.YUV420); 
      transform.transform(AWTUtil.fromBufferedImage(rgb), yuv); 
      ByteBuffer buf = ByteBuffer.allocate(rgb.getWidth() * rgb.getHeight() * 3); 

      ByteBuffer ff = encoder.encodeFrame(buf, yuv); 
      sink.write(ff); 
     } 
     if (i == 1) { 
      System.out.println("Image sequence not found"); 
      return; 
     } 
    } finally { 
     if (sink != null) 
      sink.close(); 
    } 
} 

Questo campione è più sofisticato e in realtà mostra mux di frame codificati in file MP4:

private static void prores2avc(String in, String out, ProresDecoder decoder, RateControl rc) throws IOException { 
    SeekableByteChannel sink = null; 
    SeekableByteChannel source = null; 
    try { 
     sink = writableFileChannel(out); 
     source = readableFileChannel(in); 

     MP4Demuxer demux = new MP4Demuxer(source); 
     MP4Muxer muxer = new MP4Muxer(sink, Brand.MOV); 

     Transform transform = new Yuv422pToYuv420p(0, 2); 

     H264Encoder encoder = new H264Encoder(rc); 

     MP4DemuxerTrack inTrack = demux.getVideoTrack(); 
     CompressedTrack outTrack = muxer.addTrackForCompressed(TrackType.VIDEO, (int) inTrack.getTimescale()); 

     VideoSampleEntry ine = (VideoSampleEntry) inTrack.getSampleEntries()[0]; 
     Picture target1 = Picture.create(ine.getWidth(), ine.getHeight(), ColorSpace.YUV422_10); 
     Picture target2 = null; 
     ByteBuffer _out = ByteBuffer.allocate(ine.getWidth() * ine.getHeight() * 6); 

     ArrayList<ByteBuffer> spsList = new ArrayList<ByteBuffer>(); 
     ArrayList<ByteBuffer> ppsList = new ArrayList<ByteBuffer>(); 
     Packet inFrame; 
     int totalFrames = (int) inTrack.getFrameCount(); 
     long start = System.currentTimeMillis(); 
     for (int i = 0; (inFrame = inTrack.getFrames(1)) != null && i < 100; i++) { 
      Picture dec = decoder.decodeFrame(inFrame.getData(), target1.getData()); 
      if (target2 == null) { 
       target2 = Picture.create(dec.getWidth(), dec.getHeight(), ColorSpace.YUV420); 
      } 
      transform.transform(dec, target2); 
      _out.clear(); 
      ByteBuffer result = encoder.encodeFrame(_out, target2); 
      if (rc instanceof ConstantRateControl) { 
       int mbWidth = (dec.getWidth() + 15) >> 4; 
       int mbHeight = (dec.getHeight() + 15) >> 4; 
       result.limit(((ConstantRateControl) rc).calcFrameSize(mbWidth * mbHeight)); 
      } 
      spsList.clear(); 
      ppsList.clear(); 
      H264Utils.encodeMOVPacket(result, spsList, ppsList); 
      outTrack.addFrame(new MP4Packet((MP4Packet) inFrame, result)); 
      if (i % 100 == 0) { 
       long elapse = System.currentTimeMillis() - start; 
       System.out.println((i * 100/totalFrames) + "%, " + (i * 1000/elapse) + "fps"); 
      } 
     } 
     outTrack.addSampleEntry(H264Utils.createMOVSampleEntry(spsList, ppsList)); 

     muxer.writeHeader(); 
    } finally { 
     if (sink != null) 
      sink.close(); 
     if (source != null) 
      source.close(); 
    } 
} 
Problemi correlati