H.264 frame genauer Schnitt von mkv(h.264) Dateien

  • Hab mir gerade überlegt, es müsste doch gehen folgendes zu machen:
    1. Quelle analysieren um grob die H.264 Level&Profil Einschränkungne usw. zu haben (MediaInfo)
    2. Quelle analysieren und die FrameTypen zu kennen (Avisynth + FFInfo)
    3. Liste mit von-nach cut Bereichen und den benachbarten I-Frames erstellen (mit ner kleine vfw+Avisynth&FFmpegSource basierte GUI)
    4. Splitten der Quell mkv Datei an den benachbarten I-frames und so 'toKeep'- und 'toDelete'-Stücke erstellen (mit ffmpeg oder mkvmerge)
    5. Extrahieren und schneiden des Audioteils der Teile der 'toDelete'-Stücke (mit ffmpeg)
    6. reencode des Teile der 'toDelete' Stücke die behalten werden sollen (Avisynth mit trim + x264)
    7. die in 5&6 erstellten Streams in 'reencoded'-mkvs zusammen muxen (mit mkvmerge)
    8. 'toDelete'- und 'eencoded'-Stücke mit zusammenfügen (mit mkvmerge)
    oder?


    Seht ihr da irgendwo ein wirkliches Problem? (dachte erst Punkt 2 könnte problematisch sein, geht aber easy)


    Cu Selur

  • Das sollte funktionieren. Ich selbst habe schon Sachen vie Hex Editor gecuttet aber immer and IDR Frames.
    Den Teil des GOP's der "mittendrinn" war habe ich neu codiert mit den selben Parametern und via Hex Editor dranngepappt.
    Das war jedoch ein h.264 raw-stream ohne Container oder Audio ...


    DG's altes DGAVCDec eignet sich sehr gut für sowas da der Indexfile noch "lesbar" ist. Hier muß man nur aufpassen das der Herr Graft bei 1 anfängt zu zählen und nicht bei 0. d.h. die Bytepositionen sind um 1 verschoben.

  • Das ist ja im Prinzip das, was auch die kommerziellen h264 Smart Renderer machen.


    Bei einem ordentlichen h264 mit hinreichend IDRs wird das auch einwandfrei funktionieren.


    Bei den üblichen Verdächtigen, für die man derartige Anwendungen häufig benötigt, TV-Streams, gibts so gut wie gar keine IDRs, nur Is und da kanns leicht passieren, dass etwas ausserhalb auf die gelöschten Frames referenziert. ->Decodingfehler


    Zuletzt genanntes passiert auch eigentlich bei jedem Schnitt der Kommerzsoftwares, gewisse Decoder sind halt relativ resistent dagegen, sodass es nicht jeden User stört.


    Eigentlich müsste man vom gelöschten Teil den Teil aufheben, auf den noch andere Frames referenzieren, und zwar theoretisch auf Frame- und Makroblockbasis.
    Nur wohin mit den Daten, geeignete Container gibts wohl noch nicht, und der theoretische Ansatz wurde bisher von niemandem verfolgt.
    Videoredo will kein eigenes Analysetool programmieren, und ne Lizenz für h264visa ist ihnen zu teuer.

  • Zitat

    Eigentlich müsste man vom gelöschten Teil den Teil aufheben, auf den noch andere Frames referenzieren, und zwar theoretisch auf Frame- und Makroblockbasis.


    Was den Unterschied zwischen I und IDR Frames ausmachen dürfte. Über I-Frames darf referenziert werden, über IDR Frames nicht.
    -> Das Problem ist also vermutlich, dass man wirkliche GOPs identifizieren muss, die meisten Tools das aber nicht können,..


    Cu Selur


  • -> Das Problem ist also vermutlich, dass man wirkliche GOPs identifizieren muss, die meisten Tools das aber nicht können,..


    Ich mache sowas ähnliches bei meinen TV Aufnahmen, die ich automatisch samt Werbung mit handbrake nach mkv(h264,aac) konvertiere.


    Falls ich die Sendung dann wirklich aufheben will, schneide ich die Werbung raus.
    Und zum Analysieren verwende ich mkvinfo.



    Ich habe Mosu gefragt und er meinte, dass mkvinfo ein "I Frame" nur bei einem IDR Frame anzeigt.
    Bei I Frames würde es als P Frames markieren. (soweit meine Erinnerung, ist schon ein Jahr her)


    Dann mit mkvmerge splitten, handbrake beherrscht framegenaues kodieren und mit mkvmerge wieder zusammenfügen.
    Klappt ganz gut, nur die Codec Einstellungen sollten sehr genau übereinstimmen.


    Gellas

  • Eigentlich müsste man vom gelöschten Teil den Teil aufheben, auf den noch andere Frames referenzieren, und zwar theoretisch auf Frame- und Makroblockbasis.
    Nur wohin mit den Daten, geeignete Container gibts wohl noch nicht, und der theoretische Ansatz wurde bisher von niemandem verfolgt.
    Videoredo will kein eigenes Analysetool programmieren, und ne Lizenz für h264visa ist ihnen zu teuer.


    Hallo,


    Dieser Ansatzpunkt klingt sogar logisch für einen Nichtprogrammierer wie ich es bin, und das habe ich mir auch schon länger gedacht. Es müsste ein Containerformat geben das es erlaubt, den Abspielzeitpunkt im Anfangsheader oder sonst wo, festzulegen. Wenn dann nämlich die Schnittpunkte festgelegt sind, mussen beim Schnitt die Frames auf die referenziert wird, mit in den Container. Das wären ja immer einige Frames vor jedem Schnittpunkt. Erstaunlich das diese Idee noch niemand aufgegriffen hat.


    Gerd

  • Das Problem an der Idee ist:
    1. einen Container und Splitter&Decoder zu haben, die dies erlauben. (wenn Codingdorder != Displayorder ist wird das ganze noch etwas chaotischer ;), man müsste vermutlich pro GOP und teilweise pro Frame entsprechende Infos speichern,..)
    2. das Inputmaterial so genau zu analysieren, dass man wirklich weiß welche Frames man bräuchte
    3. das man vermutlich fast die kompletten GOPs aufheben muss in denen das letzte und erste Frame des Schnittbereiches sind, je nach dem verwirft mal also vielleicht gar keine Informationen

  • Für alle die es interessiert hier eine kleine Proof-Of-Concept MKV-VideoOnly-Frame-Accurate Cut Implementation die ich in den letzten Tagen geschrieben habe.
    Proof-Of-Concept = zeigt nur das es geht und es sind bewusst (Zeitmangel) einige Sachen weggelassen wurden (Audio-, Untertitel-, Chapter-, vfr-Handling), ging mir im wesentlichen nur darum zu gucken, ob die Idee aus dem ersten Thread klappt oder ob was übersehen wurde. -> ging wie erwartet alles recht easy (wenn auch mit fast 2000 Zeilen Code doch länger als ich erwartet hatte ;))


    Cu Selur


    Ps.: Ob es sich wohl lohnt aus dem Proof-Of-Concept eine stabilere Version mit Audio support zu machen?

  • Noch mal ein paar Gedanken:


    > 2. Quelle analysieren und die FrameTypen zu kennen (Avisynth + FFInfo)
    > 3. Liste mit von-nach cut Bereichen und den benachbarten I-Frames erstellen (mit ner kleine vfw+Avisynth&FFmpegSource basierte GUI)
    > 4. Splitten der Quell mkv Datei an den benachbarten I-frames und so 'toKeep'- und 'toDelete'-Stücke erstellen (mit ffmpeg oder mkvmerge)
    -> 2&3 kann man auch einfach implementieren, wenn man FFMS als Basis nimmt.


    > 6. reencode des Teile der 'toDelete' Stücke die behalten werden sollen (Avisynth mit trim + x264)
    -> wenn man diesen Teil (also ein encode Frame X bis Frame Y eines Files) mit libav (ohne Avisynth) hinbekommt (sollte gehen), hätte man ein Tool was unter Windows, Linux und Mac läuft


    > 7. die in 5&6 erstellten Streams in 'reencoded'-mkvs zusammen muxen (mit mkvmerge)
    -> geht auch mit ffmpeg


    Cu Selur

  • Ich mag mich irren, aber wäre es nicht enorm vorteilhaft fürs Decoding, wenn man die Streamparameter so exakt wie möglich übernehmen könnte?
    Ansonsten: Machen, darauf wartet die Welt schon lang!

  • Zitat

    Hilft h264parse?


    Würde nur Sinn machen, wenn man das Ganze komplette mit GStreamer macht, hab aus Spaß an der Freude letztens mal die ersten zwei Schritte noch mal mit FFMS implementiert, aber mittlerweile die Lust an der ganzen Sache verloren.
    -> falls jemand Lust, Laune und Zeit hat aus dem ganzen ein laufendes Projekt zu machen, kann ich ihm gerne meinen SourceCode des Proof-Of-Concept und des FFMS Anfangs geben, denke aber für mich ist das Ganze hier wohl erst mal zu Ende.


    Abschließend kann ich aber sagen, dass es mich noch mehr verwundert als am Anfang, dass ffmpeg&Co die Funktionalität nicht haben, da es alles keine Magie sondern eher einfach ist. (das genaue Parsen des Material mal rausgelassen, da für die meisten Schnitte eine grobe Analyse wie sie MediaInfo liefert reicht)


    Cu Selur

  • Noch mal draufgeguckt und leicht angepasst:
    1. Quelle analysieren um grob die H.264 Level&Profil Einschränkungne usw. zu haben (MediaInfo)
    2. Quelle analysieren und die FrameTypen zu kennen (Avisynth + FFInfo)
    3. Liste mit von-nach cut Bereichen und den benachbarten I-Frames erstellen (mit ner kleine vfw+Avisynth&FFmpegSource basierte GUI)
    4. Splitten der Quell mkv Datei an den benachbarten I-frames und so 'toKeep'- und 'toDelete'-Stücke erstellen (mkvmerge)
    5. Schneiden des Audioteils ( und aller andern Stream dabei) (mkvmerge)
    6. reencode des Teile der 'toDelete' Stücke die behalten werden sollen (Avisynth mit trim + x264)
    7. die 'toKeep' Teile alle als raw Daten extrahieren damit ein zusammenfügen mit mkvmerge klappt (mkvextract)
    8. alle Teilstücke zusammenfügen (mkvmerge)
    -> hab jetzt sogar schon eine kleine pre-alpha, bei der das Schneiden von mkvStreams (mit H.264 Video und Audio) frame-genau klappt. (Und ja, ich bin immer noch sehr verwundert, dass es keine freie Software gibt die frame-akkurate Schnitte von mkvs erlaubt, mit x264, mkvtoolnix und mediaInfo hat man wenn man die GUI mal außen vor lässt alles was man braucht.)


    Leider ist das ganze für den Preview und das Reencoding noch Avisynth basiert, aber vielleicht krieg ich auch das noch 'gefixed',..


    Cu Selur

  • Zumindest beim Reencoding könnte man AviSynth leicht umgehen, in dem man einfach --seek und --frames von x264 nutzt, aber bis dahin würde ich bei Schritt 6 nicht die "toDelete"-Stücke als Quelle nehmen, sondern die bereits für die Vorschau indexierte Originaldatei. Wenn man den bereits erstellten Index wiederverwendet, könnte man so etwas Zeit sparen. Außerdem könnte so das ein oder andere Open-GOP-Problem vermieden werden.
    Bei Schritt 5 würde ich "+" anstatt "," für die --split-Anweisung nehmen (siehe "parts" mkvmerge doc). So werden alle Audiodaten in eine einzige Datei geschrieben. Macht das Muxen etwas einfacher und verhindert, daß unnötig Daten auf die Platte geschrieben werden.
    Man könnte analog bei Schritt "4" auch noch etwas Zeit/Speicherplatz durch "parts" sparen, in dem man alle "toDelete"-Stücke direkt überspringt.


    Außerdem müßtest Du noch an die Timecodes denken, damit es bei VFR nicht zu Problemen kommt.


    Bei einem ersten Test hatte ich auch Probleme. Wollte zwei Teile aus der Mitte eine Filmes ausschneiden. (Also die beiden Teile sollen erhalten bleiben und der Rest gelöscht werden.) Nun werden 2 Audioschnitte und 4 neue x264-Encodes erstellt, was auf den ersten Blick logisch erscheint. (Jeweils ein Teil der GOP zu Beginn und Ende eines Schnitts werden neu kodiert.) Allerdings wird anscheinend vergessen, die "toKeep"-Teile zu erstellen und ebenfalls zu muxen.


    Achte außerdem darauf, daß die Kommandozeile nicht die maximale Grenze von Windows sprengt. Bei vielen Schnitten und langen Ordner- bzw. Dateinamen müßtest Du auf Optionsdateien ausweichen. (näheres siehe mkvmerge doc)
    Zur GUI äußere ich mich in diesem Stadium mal noch nicht.