Eigenes Videoformat

Diskussion zum Thema Programmierung unter DOS (Intel x86)
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Eigenes Videoformat

Beitrag von zatzen »

Ich mache mal hier einen neuen Thread.

Seit längerem habe ich mir gedacht, man könnte doch eine 256col VGA Universalpalette machen.
je 3 Bit für Rot und Grün, 2 Bit für Blau. Die Ergebnisse von konvertierten Bildern sind nicht überwältigend,
aber dennoch ganz nett.

Um mich mit den neuen Möglichkeiten der RGB Zerlegung näher vertraut zu machen, möchte ich
ein Videoformat basteln. Einige kennen sicherlich das FLI(c) Format... Ähnlich werde ich das machen,
nur die Veränderungen speichern, aber ich denke statt Zeilen- und Pixelweise vorzugehen werde ich
das mal blockweise (8x8, je nachdem) probieren, schliesslich sind Bilder 2-dimensional.

Möglich wäre, dass ein ganzer Block einfach nur in einer Farbe gehalten ist, oder dass dort nur zwei
verschiedene Werte vorkommen etc... Oder auch Querbezüge zwischen den einzelnen "Layern".
Durch die Farbreduktion entstehen auch mitunter große einfarbige Flächen (bzw. auch in den drei verschiedenen
Layern, vor allem bei blau), so dass eine Kompression gut greifen kann. Anderweitige Kompression
ist möglich, wenn in einem Block und Layer der Wert nur um + - 1 schwankt -> 1 Bit.
Denkbar ist auch, verlustbehaftet, eine 1Bit-delta-Bildung, wodurch dann eine gewisse Unschärfe
entsteht. Diese könnte aber, zumindest bei zeilenweisem vorgehen, tolerabel sein, wenn man
bedenkt, dass analoge Fernseher horizontal ebenfalls eine gewisse Unschärfe aufweisen und
trotzdem funktionieren.

Je nachdem wie das alles wird kann man es evtl. auch auf eine Sprite-Engine übertragen.
RGB-Aufteilung kann auch für Spielegrafik Vorteile haben, für Transparenz-Effekte oder
Anti-Aliasing, und alles ohne Tabelle.

Ist wohl alles nicht neu, aber für mich. Vielleicht erfinde ich hier auch unnötigerweise das MPEG-Rad neu,
aber es macht halt Spass.
mov ax, 13h
int 10h

while vorne_frei do vor;
wobo
DOS-Guru
Beiträge: 613
Registriert: So 17. Okt 2010, 14:40

Re: Eigenes Videoformat

Beitrag von wobo »

zatzen hat geschrieben:Ich mache mal hier einen neuen Thread.

Seit längerem habe ich mir gedacht, man könnte doch eine 256col VGA Universalpalette machen.
je 3 Bit für Rot und Grün, 2 Bit für Blau. Die Ergebnisse von konvertierten Bildern sind nicht überwältigend,
aber dennoch ganz nett.
Das ist die Standard - Video - Palette. Die ersten VGA Hardware-Videoplayer (z.B. Cirrus Logic DG5425) haben alle Videos in dieser Palette abgespielt.

Das war übrigens auch die Standardpalette des PGA (professional graphics adapter), den ibm als Edel-Alternative zu EGA 1985 rausbrachte (die PGA - Grafikkarte kostete meines Wissens so um die 10.000 DM und benötigte 3 ISA-Slots und hatte selbst einen 8088 on board...).

zatzen hat geschrieben: Um mich mit den neuen Möglichkeiten der RGB Zerlegung näher vertraut zu machen, möchte ich
ein Videoformat basteln. Einige kennen sicherlich das FLI(c) Format... Ähnlich werde ich das machen,
nur die Veränderungen speichern, aber ich denke statt Zeilen- und Pixelweise vorzugehen werde ich
das mal blockweise (8x8, je nachdem) probieren, schliesslich sind Bilder 2-dimensional.
Ja, bitte mach so ein Videoformat und baue derartige Video-Sequenzen vielleicht sogar in Dein Game ein :-)!

Ich hatte mir vor ein paar Jahren einen FLi-Player (nur 320x200) gebastelt und habe dann auch Überlegungen für ein eigenes Animations-/Videoformat gemacht, weil ich die zeilenweise Betrachtung von Veränderungen ebenfalls ein wenig arg rudimentär empfand. So weit wie Du war ich mit meinen Überlegungen allerdings nicht. Ich habe dann auch recht schnell gemerkt, dass es mir einfach an kreativen Know-How fehlt: Wieso soll ich ein Video-/Animationsformat entwerfen, wenn mir jegliche Kreativität fehlt, auch eigene Animationen oder wenigstens Videos zu erstellen. Das Projekt war einfach ein paar Hausnummern zu groß. Deswegen würde es mich schon sehr freuen, wenn Du so ein Projekt durchziehen könntest: dann könnte ich das ganze mal in Aktion sehen.

Du musst ja auch nicht gleich das ganze in Dein Game integrieren. Ich hätte auch Lust, z.B. Deine Videoprojekte aus Deinem Youtube-Kanal in Dos zu sehen. Wäre also Grund genug, einen ZVC-Player (Zatzen Video Container) als Stand-Alone-Projekt durchzuführen.

Mmmm, bin gerade am Überlegen, ob ich meinen Entschluss, die Programmierei an den Nagel zu hängen, revidieren soll. Gibt es eigentlich eine einfache Möglichkeit, Videos als Einzelbilder auf HD abzulegen?

Edit: Habe gerade einmal ein 1.5-minütiges 320x240-Videos in Einzelbilder zerlegen lassen - ich hätte auch vorher nachrechnen können: 230kb*30 fps *90 sec = 2500 pics zu 512 MB (komprimiert). Jetzt müßte ich die Bilder alle einlesen, dekomprimieren, Farbtiefe auf 8- bit reduzieren, um endlich mein raw material zu haben... ... zuviel data! Linux hat schon Probleme auf meiner ollen Kiste, Verzeichnisse mit den 2500 pics zu laden. Unter Dos ist das jedenfalls nicht zu handeln. Neee, neee - ich zieh mich in meine Consumer-Ecke zurück :-)!

Bin mal gespannt, welche Kompressiosrate sich bei Dir ergibt: Lustig wäre es ja schon, wenn man Videos im eigenen Format auf CD brennen könnte und dann von dort direkt mit einem eigenem Player abspielen könnte. Aber mir ist schleierhaft, wie man die Datenraten hinbekommen soll: Selbst wenn man ein 4xCD-Rom voraussetzt (600kb/s -> ca. 20 Min. Video) und das Video auf 15 fps runterbringt, dürfte die Grenze bei max. 20kb pro Frame liegen. Das wäre eine Kompressionsrate von mehr als 3:1...
elianda
DOS-Übermensch
Beiträge: 1150
Registriert: Mi 31. Jan 2007, 19:04
Wohnort: Halle
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von elianda »

Vielleicht hilft es, sich durchzulesen, wie http://csdb.dk/release/?id=127922 es macht. Das kann man dann fuer low-end PC umsetzen.
Diverse Retro-Computer vorhanden.
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Hallo Wobo,

Ich glaube, die Standard VGA-Palette (die man beim Einschalten von Mode 13 hat) ist nicht ganz so.
Sie enthält ja noch die EGA-Palette, 16 Graustufen, und die letzten paar Farben sind schwarz, zudem
sind (angeblich) manche der Farben doppelt enthalten. Ich habe ja vor, wirklich 256 verschiedene Farbtöne zu machen.
Dabei entstehen teilweise leicht verfärbte Grautöne, aber das macht mir nichts, da soll erstmal jemand mit
nem perfekt kalibrierten Monitor in einer perfekt neutral beleuchteten Umgebung kommen...

Ich hoffe, wenn ich was gutes hinkriege mit dem Video-Format, dass man wenigstens 10 Sekunden oder
so in ca. 500K bekommt, dann kann man eine komplette Videosequenz vorladen. Naja ansonsten Frame
für Frame laden geht ja auch noch. Dass das "Preis-/Leistungsverhältnis" von DivX und Konsorten
nicht erreicht werden kann, ist klar. Aber es geht hier auch um Geschwindigkeit.

Ich weiss noch nicht ganz, ob ich es wirklich blockweise gestalte. Immerhin sind wertereduzierte Grafiken
auch innerhalb der Zeilen RLE komprimierbar. Blockweise ist aber auch eine Betrachtung, die bei ein
wenig Recherche zur Grafik vom ZX Spectrum führt, bei dem grundsätzlich 1-Bit monochrome Grafiken
vorlagen, die dann nur noch 8x8 blockweise 2-farbig eingefärbt wurden. Das wäre eine Möglichkeit
fürs Video, wäre dann aber schnell verlustbehaftet.

Generell würde ich auch für Sprites und Hintergründe diese Universalpalette verwenden, um völlig frei
in der Farbwahl zu sein, mich nicht festlegen zu müssen, auch wenn es auf Kosten der generellen
Qualität geht. Wenn man aber nur gehobene EGA-Standards voraussetzen will ist es aber kein
Defizit.

Naja, an so Convertern kann man ja wirklich ab und an mal kurz programmieren, das ist nicht so
etwas wofür man 10 Jahre jeden Tag dran werkeln muss. ;)

VirtualDub kann Einzelbilder aus Videos rausholen, bspw. als BMP.
Ich werde das so machen, TrueColor Bilder rausholen und dann in mein Format konvertieren.
Ganz nett ist dabei, dass es Freepascal gibt, kann im Prinzip alles was BP kann, hat aber
praktisch (oder theoretisch) keine Speichergrenzen. Und läuft in Windows. Ähem. Aber
nehme ich nur für Converter, es umständlich diese in Real-Mode Grenzen zu machen.

Mein System hat kein Problem mit zig tausend Einzelbildern mit zweistelliger GB Größe insgesamt.
Free Pascal zum Glück auch nicht. Bin auch grad dabei, das AVI Format zu verstehen, damit ich,
für andere Sachen die ich noch so mache, direkt ein AVI mit unkomprimierten Bildern schreiben
kann und nicht Einzeldateien, die in Windows doch ein wenig das System verlangsamen.

Also... Ich rede hier verbotenerweise von Windows. Aber für Datenaufbereitung von groß
nach klein ist es doch sehr von Vorteil wenn man ein Daten-Mega-Potentes System vor sich hat.

Die Kompressionsrate musst du durchschnittlich sehen. Denn die wäre in meinem Fall variabel,
so wie bei FLI. Wenn sich wenig bewegt könnte ein Einzelbild vielleicht auch schonmal mit 1K auskommen.

Ich häng zur Illustration mal ein Bild mit dem Referenzpapagei an, was man so qualitätstechnisch erwarten
kann, wenn das ganze verlustfrei arbeitet.
referenzpapa.png
referenzpapa.png (39.58 KiB) 18409 mal betrachtet
Zuerst alle drei Channels (8 Bit), dann Rot (3 Bit), Grün (3 Bit), Blau (2 Bit)
Man kann gut sehen, dass sich da schon einiges an Fläche bildet, die man
komprimieren könnte. Das ist aufgrund der Stufenreduktion auch bei fast
jedem Bild so, und "schnellere" Wechsel sind oft nur 1-stufig und lassen
sich mit 1 Bit beschreiben.

Als Video muss man nur das updaten, was sich von einem Bild zum anderen
verändert hat. Manchmal ist auf dieser Ebene aber eine komplette komprimierte
Bildinfo genauso kompakt.


Danke elianda.
Scheint etwas umfangreicher zu sein. Guck ich bei Gelegenheit mal rein, vorerst wollte ich die
Sache recht simpel mit RLE und/oder 1-Bit Codierung, Delta, sonstwas angehen.
mov ax, 13h
int 10h

while vorne_frei do vor;
wobo
DOS-Guru
Beiträge: 613
Registriert: So 17. Okt 2010, 14:40

Re: Eigenes Videoformat

Beitrag von wobo »

zatzen hat geschrieben:Hallo Wobo,

Ich glaube, die Standard VGA-Palette (die man beim Einschalten von Mode 13 hat) ist nicht ganz so.
Ja, ich sprach ja auch nicht von der Standard VGA-Palette, sondern von der Standard Video- Palette der VGA. Die ist, wie Du schreibst 8 Intensitäten Grün, 8 Intensitäten Rot, und 4 INtensitäten Blau - eben weil blau anscheinend vom menschlichen Auge nicht so fein aufgelöst wird, wie die anderen Farben.

Ich hatte einmal einen Konvertret geschrieben, um möglichst viele geklaute 256-Farbbilder mit unterschiedlichen Paletten zu einen. Da bin ich letztlich auch bei der Videopalette hängen geblieben und hatte bei den einzelnen Bildern dann immer eine Verwendung von 31-64 Farben - so, wie Du es ja auch beschreibst.
zatzen hat geschrieben: Dabei entstehen teilweise leicht verfärbte Grautöne, aber das macht mir nichts, da soll erstmal jemand mit
nem perfekt kalibrierten Monitor in einer perfekt neutral beleuchteten Umgebung kommen...
Ja, subjektiv fand ich schon viele "scheußliche" Grau-Töne dabei...

zatzen hat geschrieben: Ich hoffe, wenn ich was gutes hinkriege mit dem Video-Format, dass man wenigstens 10 Sekunden oder
so in ca. 500K bekommt, dann kann man eine komplette Videosequenz vorladen. Naja ansonsten Frame
für Frame laden geht ja auch noch. Dass das "Preis-/Leistungsverhältnis" von DivX und Konsorten
nicht erreicht werden kann, ist klar. Aber es geht hier auch um Geschwindigkeit.
Das ist klar - es geht ja nur darum, das Fli-Format ein bisschen auf den konkreten Bedarf zu optimieren.

Es kommt halt auch auf das konkrete Video an (wie Du schon geschrieben hast): Gestern hatte ich ein Video mit einem Klavierspieler bei fester Kamera in Einzelbilder zerlegt: da waren wirklich 3/4 des Bildes ständig nahezu unverändert.

Wenn Du mit variabler Datenrate arbeiten willst: Setzt Du dann eine Obergrenze für die Einzelne Frame oder ist die Obergrenze ein ganzes Bild (64k bei 320x200)?
zatzen hat geschrieben: VirtualDub kann Einzelbilder aus Videos rausholen, bspw. als BMP.
Ich werde das so machen, TrueColor Bilder rausholen und dann in mein Format konvertieren.
Ganz nett ist dabei, dass es Freepascal gibt, kann im Prinzip alles was BP kann, hat aber
praktisch (oder theoretisch) keine Speichergrenzen. Und läuft in Windows. Ähem. Aber
nehme ich nur für Converter, es umständlich diese in Real-Mode Grenzen zu machen.
Das ist das nächste Problem - ich habe von der Programmierung unter Win/Linux absolut Null-Ahnung. Das hat mich jetzt schon mehrfach geärgert. Vielleicht fange ich mal vorsichtig mit VBA an...
freecrac
DOS-Guru
Beiträge: 861
Registriert: Mi 21. Apr 2010, 11:44
Wohnort: Hamburg Horn

Re: Eigenes Videoformat

Beitrag von freecrac »

Ich hatte mir mal eine TV-Karte ausgeliehen und damit einige Aufnahmen gemacht und diese dann als *.avi-Datei gespeichert. Dort habe ich mir dann mit dem Animation-Shop vom Paintshop-pro-Grafikprogramm die einzelnen Bilder herausgeholt und als unkomprimierte *.TGA-Bilder mit 24 Bit true color und 320x240 abgespeichert.

Dann habe ich die Bilder nacheinander in den Speicher geladen und vom ersten Bild alle Farben und Adresssen der Pixel in eine Tabelle gerettet. Bei den folgenden Bildern habe ich nur noch jene Pixel und Adressen, die eine andere Farbe haben als das vorherige Bild, in die Tabelle gerettet. Damit man sehen kann wieviel Byte für jedes Bild in der Tabelle zusammen kommen habe ich die Adresse innerhalb der Tabelle und die Anzahl der Bytes für jedes Bild mir ausgeben lassen.

Danach werden die Bilder aus der Tabellle zum Bildschirm gebracht. Für wenige Sekunden Film kommt so schon eine Menge an Megabytes zusammen. Die Tabelle für wenige Sekunden von einem Footballspiel:

Code: Alles auswählen

    Lade:F01.tga    Start:00390400h    Ende:003A390Fh    Länge:00013510h
    Lade:F02.tga    Start:003A3910h    Ende:003B87BFh    Länge:00014EB0h
    Lade:F03.tga    Start:003B87C0h    Ende:003CD677h    Länge:00014EB8h
    Lade:F04.tga    Start:003CD678h    Ende:003E1947h    Länge:000142D0h
    Lade:F05.tga    Start:003E1948h    Ende:003F4B07h    Länge:000131C0h
    Lade:F06.tga    Start:003F4B08h    Ende:004074CFh    Länge:000129C8h
    Lade:F07.tga    Start:004074D0h    Ende:00419B7Fh    Länge:000126B0h
    Lade:F08.tga    Start:00419B80h    Ende:0042BEB7h    Länge:00012338h
    Lade:F09.tga    Start:0042BEB8h    Ende:0043E6EFh    Länge:00012838h
    Lade:F10.tga    Start:0043E6F0h    Ende:00450707h    Länge:00012018h
    Lade:F11.tga    Start:00450708h    Ende:0046244Fh    Länge:00011D48h
    Lade:F12.tga    Start:00462450h    Ende:0047461Fh    Länge:000121D0h
    Lade:F13.tga    Start:00474620h    Ende:0048645Fh    Länge:00011E40h
    Lade:F14.tga    Start:00486460h    Ende:00498A6Fh    Länge:00012610h
    Lade:F15.tga    Start:00498A70h    Ende:004ABC57h    Länge:000131E8h
    Lade:F16.tga    Start:004ABC58h    Ende:004BF56Fh    Länge:00013918h
    Lade:F17.tga    Start:004BF570h    Ende:004D3097h    Länge:00013B28h
    Lade:F18.tga    Start:004D3098h    Ende:004E6687h    Länge:000135F0h
    Lade:F19.tga    Start:004E6688h    Ende:004FA67Fh    Länge:00013FF8h
    Lade:F20.tga    Start:004FA680h    Ende:0050F80Fh    Länge:00015190h
    Lade:F21.tga    Start:0050F810h    Ende:00524B3Fh    Länge:00015330h
    Lade:F22.tga    Start:00524B40h    Ende:00537C77h    Länge:00013138h
    Lade:F23.tga    Start:00537C78h    Ende:0054B237h    Länge:000135C0h
    Lade:F24.tga    Start:0054B238h    Ende:0055F607h    Länge:000143D0h
    Lade:F25.tga    Start:0055F608h    Ende:00573DB7h    Länge:000147B0h
    Lade:F26.tga    Start:00573DB8h    Ende:005888D7h    Länge:00014B20h
    Lade:F27.tga    Start:005888D8h    Ende:0059D56Fh    Länge:00014C98h
    Lade:F28.tga    Start:0059D570h    Ende:005B169Fh    Länge:00014130h
    Lade:F29.tga    Start:005B16A0h    Ende:005C6167h    Länge:00014AC8h
    Lade:F30.tga    Start:005C6168h    Ende:005DA2E7h    Länge:00014180h
    Lade:F31.tga    Start:005DA2E8h    Ende:005EDFEFh    Länge:00013D08h
    Lade:F32.tga    Start:005EDFF0h    Ende:00601D6Fh    Länge:00013D80h
    Lade:F33.tga    Start:00601D70h    Ende:006158AFh    Länge:00013B40h
    Lade:F34.tga    Start:006158B0h    Ende:0062998Fh    Länge:000140E0h
    Lade:F35.tga    Start:00629990h    Ende:0063C60Fh    Länge:00012C80h
    Lade:F36.tga    Start:0063C610h    Ende:0064EABFh    Länge:000124B0h
    Lade:F37.tga    Start:0064EAC0h    Ende:0066000Fh    Länge:00011550h
    Lade:F38.tga    Start:00660010h    Ende:00670D77h    Länge:00010D68h
    Lade:F39.tga    Start:00670D78h    Ende:006813DFh    Länge:00010668h
    Lade:F40.tga    Start:006813E0h    Ende:0069193Fh    Länge:00010560h
    Lade:F41.tga    Start:00691940h    Ende:006A1BD7h    Länge:00010298h
    Lade:F42.tga    Start:006A1BD8h    Ende:006B2D5Fh    Länge:00011188h
    Lade:F43.tga    Start:006B2D60h    Ende:006C3A9Fh    Länge:00010D40h
    Lade:F44.tga    Start:006C3AA0h    Ende:006D3667h    Länge:0000FBC8h
    Lade:F45.tga    Start:006D3668h    Ende:006E3207h    Länge:0000FBA0h
    Lade:F46.tga    Start:006E3208h    Ende:006F274Fh    Länge:0000F548h
    Lade:F47.tga    Start:006F2750h    Ende:007026DFh    Länge:0000FF90h
    Lade:F48.tga    Start:007026E0h    Ende:00712207h    Länge:0000FB28h
    Lade:F49.tga    Start:00712208h    Ende:007202BFh    Länge:0000E0B8h
    Lade:F50.tga    Start:007202C0h    Ende:0072CFA7h    Länge:0000CCE8h
    Lade:F51.tga    Start:0072CFA8h    Ende:00738ABFh    Länge:0000BB18h
    Lade:F52.tga    Start:00738AC0h    Ende:00743AEFh    Länge:0000B030h
    Lade:F53.tga    Start:00743AF0h    Ende:0074ED1Fh    Länge:0000B230h
    Lade:F54.tga    Start:0074ED20h    Ende:0075AC2Fh    Länge:0000BF10h
    Lade:F55.tga    Start:0075AC30h    Ende:00766D5Fh    Länge:0000C130h
    Lade:F56.tga    Start:00766D60h    Ende:007744BFh    Länge:0000D760h
    Lade:F57.tga    Start:007744C0h    Ende:00783057h    Länge:0000EB98h
    Lade:F58.tga    Start:00783058h    Ende:00792FC7h    Länge:0000FF70h
    Lade:F59.tga    Start:00792FC8h    Ende:007A3DC7h    Länge:00010E00h
    Lade:F60.tga    Start:007A3DC8h    Ende:007B4817h    Länge:00010A50h
    Lade:F61.tga    Start:007B4818h    Ende:007C47AFh    Länge:0000FF98h
    Lade:F62.tga    Start:007C47B0h    Ende:007D32AFh    Länge:0000EB00h
    Lade:F63.tga    Start:007D32B0h    Ende:007E06A7h    Länge:0000D3F8h
    Lade:F64.tga    Start:007E06A8h    Ende:007EE60Fh    Länge:0000DF68h
    Lade:F65.tga    Start:007EE610h    Ende:007FD957h    Länge:0000F348h
    Lade:F66.tga    Start:007FD958h    Ende:0080CEF7h    Länge:0000F5A0h
    Lade:F67.tga    Start:0080CEF8h    Ende:0081BC7Fh    Länge:0000ED88h
    Lade:F68.tga    Start:0081BC80h    Ende:00824B5Fh    Länge:00008EE0h

                       Benötigter Speicher: 9 Mega-Byte
Wenige Sekunden mit Bibo, dem gelben Vogel aus der Sesamstrasse, verschlingen ähnlich viel Speicherplatz.

Dirk
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Hallo wobo, Programmierung in Windows wäre mit Freepascal ja äquivalent zu DOS,
nur mit weniger Einschränkungen, und aber auch, ASM ist da irgendwie anders.

Eine feste maximale Bitrate wollte ich nicht setzen, das würde fürs erste zu kompliziert,
eher nach dem Prinzip, möglichst klein, aber eben so groß wie's dann kommt.
Wenn man es blockweise angeht, wäre vielleicht von Bild zu Bild denkbar, gewisse
Toleranzen einzubauen, so dass z.B. aus den 64 Pixeln eines 8x8 Blocks zwei Stück
geschlabbert werden dürfen. Dadurch erhöht sich die Wahrscheinlichkeit, Blöcke
nicht updaten zu müssen. Verglichen wird dann aber immer mit dem vorherigen
decodierten Bild hin zu dem neuen zu codierenden, und nicht mit dem verlustfreien Vorgänger.


Hallo Dirk!

Ich habe das ja etwas anders vor. Zum einen, wenn ich das richtig verstehe, hast du Pro Pixel
ja 3 Byte. Und dann kommen noch die Adressen dazu, bei 320x240 müsste das je ein Word sein.
Bin mir nicht sicher ob ich das richtig verstehe, aber auf diese Weise ist es kein Wunder, dass
das alles so groß wird. Es ist ja so wie du es beschreibst eine verlustfreie "Kompression" im TrueColor
Format. Wenn du die Bilder als PNG speicherst könnten schon kleinere Wert rauskommen.
Ich blicke da aber nicht ganz durch, mir ist unklar was genau jetzt in so einer Tabelle steht.
8 Bit Farbe? Die Koordinaten bzw. Adresse als Word? Ein Hex-Wert von > 10000 entspricht
ja in etwa der Größe von 320x240.

Was ich mir da ausdenke zieht ja nicht zuletzt den Nutzen daraus, dass die Stufen der einzelnen
Kanäle auf wenige Bits runterskaliert werden. Es wird daher niemanden zufrieden stellen der wirklichen
Fotorealismus möchte, aber um 1990 hätte solche Grafik am PC schon die Leute beeindruckt.

Mein Ziel ist es aber auch, möglichst nicht über 1x CD-ROM Datenrate zu gehen, sondern eher
auch Videos hinzubekommen, die in sinnvoller Länge auch auf eine Diskette passen (würden).
Wenigstens 10-15 Sekunden auf eine. Mit gezielt erstellten Videos sollte das kein Problem sein,
d.h. computer-generierte Videos wo wirklich klinisch abgegrenzt nur wenig Bereiche Bewegung haben.
Anders ist das natürlich bei echten gefilmten Videos.


Ideal wäre natürlich, wenn man wirklich nur die Information speichern könnte, die sich verändert.
Nur gehört zu jeder Veränderung eines Pixels auch eine Adresse, und da muss man sich etwas
einfallen lassen, gerade auch weil in meinem Fall der Wert eines Pixels bei Blau ja nur zwei Bit
beträgt, und die Koordinaten / Adresse mehr.
Wenn man 320x200 in 8x8 Blöcke unterteilt, könnte man für einen Layer 125 (320x200 / (8*8*8) )Byte
anlegen in denen die Bits sagen, welcher Block verändert werden soll und welcher nicht. Und dann
gibt es ja noch Lauflängencodierung. Oder Delta, sowohl von einem Pixel zum Nachbarpixel oder auch
von einem Pixel des vorherigen Bildes zum jetzigen. Da gibt es letztlich viele Möglichkeiten die man
kombinieren oder für jede Situation die beste raussuchen kann, und da werde ich drüber nachdenken.

Nebenbei, 16:9 ist unser Freund, da sparen wir ein Viertel.
mov ax, 13h
int 10h

while vorne_frei do vor;
freecrac
DOS-Guru
Beiträge: 861
Registriert: Mi 21. Apr 2010, 11:44
Wohnort: Hamburg Horn

Re: Eigenes Videoformat

Beitrag von freecrac »

Moin.
zatzen hat geschrieben: Hallo Dirk!

Ich habe das ja etwas anders vor. Zum einen, wenn ich das richtig verstehe, hast du Pro Pixel
ja 3 Byte. Und dann kommen noch die Adressen dazu, bei 320x240 müsste das je ein Word sein.
Für die Farben werden 4 Byte je Pixel verwendet wegen 32 Bit-Videomode und weil so grosse Datenmengen Platz brauchen, deswegen verwende ich den Bigrealmode zusammen mit dem LFB und bekomme damit 4 Byte Adressen.
Pro Pixel werden also 8 Byte in eine Tabelle geschrieben.
Bin mir nicht sicher ob ich das richtig verstehe, aber auf diese Weise ist es kein Wunder, dass
das alles so groß wird.
Stimmt. Aber es gibt wohl keine schnellere Möglichkeit truecolor Bilddaten zum Bildschirm zu bringen,
weil die Adressen und die Farben einfach nur aus der Tabelle geholt werden müssen
und die Farben dann ohne Umwege zu der jeweiligen Adresse gebracht werden können.
Es ist ja so wie du es beschreibst eine verlustfreie "Kompression" im TrueColor
Format.
Eigentlich ist es eher das Gegenteil einer Kompression, weil grösser kann man die Daten nicht mehr auspacken.
Wenn du die Bilder als PNG speicherst könnten schon kleinere Wert rauskommen.
Ich blicke da aber nicht ganz durch, mir ist unklar was genau jetzt in so einer Tabelle steht.
8 Bit Farbe? Die Koordinaten bzw. Adresse als Word? Ein Hex-Wert von > 10000 entspricht
ja in etwa der Größe von 320x240.
Der erster Eintrag in der Tabelle könnte die vier Bytes grosse Adresse des LFB sein, wenn der Pixel links oben eine Farbe enthält. Danach folgt die Farbe mit 4 Bytes. Adresse, Farbe, Adresse, Farbe usw.. Und alles leider nur ohne einen einzigen Ton als Stummfilm ohne musikalische Untermahlung.
Was ich mir da ausdenke zieht ja nicht zuletzt den Nutzen daraus, dass die Stufen der einzelnen
Kanäle auf wenige Bits runterskaliert werden. Es wird daher niemanden zufrieden stellen der wirklichen
Fotorealismus möchte, aber um 1990 hätte solche Grafik am PC schon die Leute beeindruckt.
Meine erste Grafikkarte die ich gekauft habe sollte auf jeden Fall schon true color haben und deswegen habe ich mir eine ET4000 geholt, weil ich mit weniger Farben nicht zufrieden zu stellen war. Auch wollte ich niemals einen 14" CRT-Monitor verwenden und habe mir deswegen gleich einen 15" CRT gekauft und der erlaubte schon eine Auflösung von 1280x1024 zu verwenden.
Mein Ziel ist es aber auch, möglichst nicht über 1x CD-ROM Datenrate zu gehen, sondern eher
auch Videos hinzubekommen, die in sinnvoller Länge auch auf eine Diskette passen (würden).
Wenigstens 10-15 Sekunden auf eine. Mit gezielt erstellten Videos sollte das kein Problem sein,
d.h. computer-generierte Videos wo wirklich klinisch abgegrenzt nur wenig Bereiche Bewegung haben.
Anders ist das natürlich bei echten gefilmten Videos.
Ja ich verstehe.
Ideal wäre natürlich, wenn man wirklich nur die Information speichern könnte, die sich verändert.
Ich vergleiche dafür die Farben mit den Farben des vorherigen Bildes und trage nur die Veränderungen in die Tabellle ein.

Wie man an der Längeangaben der verschiedenen Tabelleneinträge der einzelnen Bilder sehen kann, werden bei den bewegten TV-Bildern mit Kamera-Schwenk die meisten Pixel sich ständig verändern und wohl nur relativ wenige Pixel unverändert bleiben. Der Längenunterschied der jeweiligen Einträge ist ja nicht so gross. Ab Bild 44 wird die Länge der Einträge je Bild etwas geringer nachdem der Kamera-Schwenk vorbei ist.
Nur gehört zu jeder Veränderung eines Pixels auch eine Adresse, und da muss man sich etwas
einfallen lassen, gerade auch weil in meinem Fall der Wert eines Pixels bei Blau ja nur zwei Bit
beträgt, und die Koordinaten / Adresse mehr.

Wenn man 320x200 in 8x8 Blöcke unterteilt, könnte man für einen Layer 125 (320x200 / (8*8*8) )Byte
anlegen in denen die Bits sagen, welcher Block verändert werden soll und welcher nicht. Und dann
gibt es ja noch Lauflängencodierung. Oder Delta, sowohl von einem Pixel zum Nachbarpixel oder auch
von einem Pixel des vorherigen Bildes zum jetzigen. Da gibt es letztlich viele Möglichkeiten die man
kombinieren oder für jede Situation die beste raussuchen kann, und da werde ich drüber nachdenken.

Nebenbei, 16:9 ist unser Freund, da sparen wir ein Viertel.
Ja damit kann man bestimmt die Daten kleiner bekommen.

Dirk
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Ich mache das jetzt mal per 8x8 Blöcke. So funktioniert das ja auch bei "amtlichen" Formaten wie JPEG.

Muss ich mich also "nur" darauf konzentrieren, wie man so einen 8x8 Block am besten komprimiert,
alle Möglichkeiten ausprobieren, und am Ende die kleinste aussuchen.

Mit beeindruckender Grafik um 1990 meinte ich übrigens nur, dass eben solche Videos schon ganz
nett gewesen wären, einfach wegen der Möglichkeit, sie auf damaligen Rechnern darzustellen.
Soetwas hatte ich in dieser Zeit nicht erlebt, das kam irgendwie erst Mitte der 90er mit Windows auf.
Bei weniger gut ausgeleuchtetem Quellmaterial könnte einem der Spass an der Sache schon vergehen -
ist alles nur ein Versuch.
Dithering würde die Qualität stark erhöhen, dabei müsste ich dann aber auch für die Kompression sehr
intelligente Verfahren ausdenken. Denkbar wäre ein Verfahren, quasi ein verstümmeltes RLE, wenn
in einem Block nur zwei Farben vorkommen und maximal je 1 Pixel Abstand, dann kann man einen
Bitstream ansetzen der sagt, jetzt Pixel überspringen oder nicht. Im Falle von Dithering liesse sich
dann, wenn es passt und im günstigsten Fall, ein 8x8 Block in ca. 4 Byte unterbringen.
Natürlich geht auch, wenn in einem Block eine komplett geditherte Fläche vorliegt, das ganze
auf ca. 1 Byte unterzubringen.
mov ax, 13h
int 10h

while vorne_frei do vor;
DOSferatu
DOS-Übermensch
Beiträge: 1220
Registriert: Di 25. Sep 2007, 12:05
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von DOSferatu »

Vielleicht kann ich auch etwas Gedankenschaum dazu beitragen:

Man könnte das Ganze auch auf 256 feste "Pattern" beschränken, die "Standard" sind und nicht "mitübertragen" werden, sondern inhärenter Bestandteil des Players sind. Ein Pattern wäre 8x8 Pixel, mit unterschiedlichen Helligkeiten (so "Verläufen" und so und verschiedenen generischen Formen - kanns noch genauer erklären), also in "Graustufen".
Man rechnet das Bild erstmal "auseinander", d.h. rot/grün/blau getrennt. Für jede Phase einzeln schaut man sich die 8x8 "Graustufen" Pixel an, die sich ergeben - ermittelt die dunkelste und hellste Stufe. Dann "skaliert" man das ganze so, daß man es so hochrechnet, daß die dunkelste Stelle auf 0 und die hellste auf 255 (also max.) geht. Dieses Ergebnis prüft man gegen die 256 möglichen Patterns und nimmt das passendste.
Im Ergebnis braucht man dann für 64 Pixel (was brutto 192 Bytes wären) dann nur noch 9 Bytes:
3 Bytes pro Phase: Pattern-Nr, Min-Wert, Max-Wert.

Man kann das Ganze noch reduzieren, indem man zB. nur 64 Patterns und 32 Min/Max Werte nimmt.
Dann könnt man pro Phase mit einem Word (6/5/5 Bits) aus.

Sortiert man die Patterns, ist das Suchen darin etwas schneller (z.B. mit iterativer Suche) - aber insgesamt würde - wie immer - das Erstellen der Daten (durch das Suchen) etwas aufwendiger als das Abspielen.

Außerdem könnte man auch pro "Quadrat" ein "Delta" Byte einfügen, das angibt, wieviele Quadrate übersprungen werden können, weil sie sich nicht - oder zu wenig - geändert haben. (Dann braucht man noch beim Erstellen des Videos einen Qualität-Parameter, der angibt, ab welcher prozentualen "Unterschiedlichkeit" ein neues Pattern an die Stelle kommt oder das alte noch bestehen bleibt.

Eine gute zusätzliche Methode wäre, vorher den "Noise" aus dem Bild rauszurechnen (quasi so "glätten" - kann's genauer erklären) und dann einen eigenen "niedrigbittigen" "Noise-Layer" drüberzulegen.

Weitere Möglichkeit: (noch mehr sparen), indem man nicht alle 3 Farbphasen (R,G,B) nimmt, sondern von einem Farbkreis ausgeht, der eine beliebige "Reichweite" hat. (Maximal 0 bis 1529, aber natürlich reduziert auf z.B. 8 Bit oder so - z.B. 0 bis 254, und 255 für reines weiß)....

Naja, Ideen über Ideen....

Ich dachte auch schon mal daran, ein eigenes Videoformat zu entwickeln. (Hm... - Fällt das sehr auf?)
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

An die Sache mit Standardmustern hatte ich auch schon gedacht.
Aber noch nicht so vertieft. Wäre es vielleicht denkbar, einfach 65536
Muster zu haben und dann alles per Word zu definieren? Wären 6 Byte
pro Block, also 6 K pro Bild ...
Aber irgendwie... Je nach Quelle kiegt man dann schon bei gleicher
Größe eine bessere Qualität hin, denke ich.

Erstmal nehme ich ein wenig Abstand von dem Videogedanken und
konzentriere mich auf die verlustfreie Datenreduktion von Bildern
im 3-3-2 Bit Format. Wenn man da wirklich was sparen kann würde
sich das nämlich auch lohnen für Sprites und ein Spiel allgemein.
Dass man dann mit 8x8 Pixelblöcken arbeiten muss soll mich erstmal
nicht weiter stören, viele Games benutzen sowieso durch 8 teilbare
Größen, und ich selbst habe das auch schon so gemacht, ohne dass
es technisch erforderlich gewesen wäre.

Ich bin gerade dabei, die verschiedensten "Algorhythmen" zu schreiben,
wie man ein 8x8 Quadrat abspeichern kann. Neben den eigentlichen
Daten brauche ich dann je nachdem noch eine Block-"Header" Definition
und ein Byte das die Daten deklariert, im Falle von z.B. ganzer Block
einfarbig eben die entspr. Farbe, oder aber es braucht gar keine
Info wenn der Block einfach unkomprimiert gespeichert wird. Ist ja
klar.

Dass man sich erstmal nur auf 8x8 Pixel konzentrieren muss macht
die Sache für ein Menschenhirn doch einfacher.


OT: Ich bekomme keine Nachrichten per email auf neue Nachrichten, obwohl
ich das hier angekreuzt habe und meine email im System hinterlassen habe.
mov ax, 13h
int 10h

while vorne_frei do vor;
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Ok, 65536 Muster a 64 Byte oder so würden ja gar nicht in den Speicher passen.

Du hast das ja auch alles differenzierter ausgedrückt.

Ich versuch's wie gesagt erstmal mit blockweiser der Situation angepasster Codierung.


Was die Palette angeht... Darüber habe mir nie so sehr viele Gedanken gemacht und
würde aber jetzt für's erste, wo ich sowieso "retro" mache, mit dieser Kompromiss-
Unversal-Palette arbeiten. Ich glaube notfalls würde mir sogar EGA genügen.
mov ax, 13h
int 10h

while vorne_frei do vor;
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Zwischenmeldung:

Folgendes Bild:
inp00000.png
inp00000.png (12.66 KiB) 18327 mal betrachtet
Unkomprimiert: 64000 Byte

PNG: 12959 Byte

GIF: 16308 Byte

PCX: 32557 Byte


Mein Format: 23278 Byte


Liege ich also immerhin schonmal zwischen PCX und GIF, und ich denke am Ende werde ich GIF erreichen,
vielleicht sogar übertreffen, das dann alles aber ohne unbequeme Huffman Codierung, und vielleicht wird
es schnell genug, meine Art der Kompression in Echtzeit z.B. für Sprites zu verwenden.

Derzeit habe ich nur 7 Methoden und noch keine R-G-B getrennten Modi (bis auf eine).

Methoden sind bisher:
0 - Block komplett mit einer Farbe füllen die durch 4 Bit definiert ist, R, G, B jeweils 1 Bit an oder aus + 1 Bit Hell / Dunkel
1 - Block unkomprimiert einfach kopieren
2 - Block komplett mit einer Farbe füllen die mit einem Byte Index zwischen 0 und 255 definiert ist
3 - 1 Bit - weise speichern mit bis zu 2 Farben Palette
4 - 2 Bit - weise speichern mit bis zu 4 Farben Palette
5 - 3 Bit - weise speichern mit bis zu 8 Farben Palette
6 - 4 Bit - weise speichern mit bis zu 16 Farben Palette
Bei den letzten vier (bzw. bei 3 nicht wirklich) steht im Definitionbyte,
wie viele Farben die Palette tatsächlich hat, bspw. sind für 10 Farben
4 Bit nötig, aber man kann trotzdem 6 Byte in der Palettendefinition sparen.

Bis auf Methode 0 alles noch Byte-bezogen, ohne Zerlegung in RGB.
Lauflänge ist auch noch nicht drin.

Da müsste also noch was gehen... Ich will im "Kommando-Byte" 4 Bit für die Kennzeichnung
der Methode verwenden und weitere 4 Bit für Parameter. So kommt Methode Null komplett
ohne weitere Daten aus, der ganze Block ist mit nur einem Byte definiert.
Vielleicht sollte ich aber erstmal einen Viewer oder Decoder schreiben um sicherzustellen,
dass auch alles richtig funktioniert.
mov ax, 13h
int 10h

while vorne_frei do vor;
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Ein Update:
monkey2.png
monkey2.png (18.08 KiB) 18300 mal betrachtet
Ein GIF belegt damit 20808 Byte,

mein Encoder derzeit 28278 Byte.

Dem Bild habe ich die 3-3-2 Palette aufgeprägt, ich hätte schlimmeres erwartet.
Mit derartiger Farbenvielfalt, wenn auch nicht ganz wie im Original, kann man
doch leben.

Wahrscheinlich werde ich GIF höchstens erreichen und nicht übertreffen, aber mal sehen.
Mit der Zeit fallen mir immer wieder neue Methoden ein, Blöcke zu komprimieren.

Wenn Huffman oder Lempel-Ziv gleichzeitig effektiver und dabei auch noch schnell zu dekodieren wäre,
dann ist dies alles natürlich irgendwie sinnlos. Aber ich denke, für jeden Grafik-Block extra eine Huffman
Routine laufen zu lassen wäre doch komisch.
Bei meiner Weise geht es möglicherweise sogar schneller als unkomprimiert, da durchweg weniger Daten
gelesen werden müssen und das Entpacken größtenteils auf Register-Ebene stattfinden wird.

Ich habe derzeit 11 verschiedene Methoden, alle noch auf komplette Farbindexe bezogen, d.h. noch
nicht R-G-B weise aufgeteilt. Ob letzteres überhaupt etwas bringt, werde ich dann sehen.
Hier das Ende des Logfiles:

Code: Alles auswählen

method #0 used 282x
description: storing complete block in 1 color using 3 bit rbg + 1 bit luminance
average size of compressed blocks incl. header: 1.00 byte(s)

method #1 used 91x
description: copying complete block uncompressed in 8 bit
average size of compressed blocks incl. header: 65.00 byte(s)

method #2 used 5x
description: storing complete block in 1 color using 1 byte palette index
average size of compressed blocks incl. header: 2.00 byte(s)

method #3 used 3x
description: encoding block in 1 bit using up to 2 indexed colors
average size of compressed blocks incl. header: 11.00 byte(s)

method #4 used 57x
description: encoding block in 2 bit using up to 4 indexed colors
average size of compressed blocks incl. header: 20.51 byte(s)

method #5 used 207x
description: encoding block in 3 bit using up to 8 indexed colors
average size of compressed blocks incl. header: 31.43 byte(s)

method #6 used 300x
description: encoding block in 4 bit using up to 16 indexed colors
average size of compressed blocks incl. header: 45.24 byte(s)

method #7 used 0x
description: storing complete block in 2 colors dithered

method #8 used 1x
description: 1 bit rle encoding (packets of 4 bit: 3bit length 1 bit value)
average size of compressed blocks incl. header: 9.00 byte(s)

method #9 used 2x
description: 2 color splitted field: 2 byte colors, 1 byte position
average size of compressed blocks incl. header: 4.00 byte(s)

method #10 used 0x
description: parallel straight lines, one byte each or pal + 2/1 bit

method #11 used 52x
description: setting individual pixels up to 4 colors with 1 color background
average size of compressed blocks incl. header: 14.87 byte(s)


total compressed filesize: 28278 bytes

Effektiver zeigt sich das natürlich an Bildern mit weniger Information, bspw. wenn auf dem
Bildschirm nur ein Logo und ein Schriftzug erscheint, dann habe ich bspw. nur 4K - aber GIF ist
mir derzeit immer um etwa 1/4 voraus.
mov ax, 13h
int 10h

while vorne_frei do vor;
Benutzeravatar
zatzen
DOS-Guru
Beiträge: 518
Registriert: Di 17. Apr 2012, 05:10
Wohnort: bei Köln
Kontaktdaten:

Re: Eigenes Videoformat

Beitrag von zatzen »

Ich habe ein bisschen probiert und bin zu dem Entschluss gekommen, dass ich bis auf weiteres
keine R-G-B Aufteilung mit einbaue. Das ist gar nicht so effektiv, vor allem wäre es aber
sehr umständlich zu entpacken, man müsste alles 3x durchlaufen lassen und dann auch noch
aus dem Zielspeicher lesen, um RGB Bitweise zusammenzusetzen.
Lasse ich mir lieber noch ein paar andere Sachen einfallen. Bspw. Blöcke mit identischem Inhalt
erhalten einfach einen Word-Index in den die Daten zu vorherigen Blockdaten, oder das gleiche
auch für Paletten, da lassen sich bis zu 14 Byte pro Block sparen, muss ich nur für höhere Wahrschein-
lichkeit dass sie gleich sind diese sortieren. Besser wäre wohl noch, die Paletten von den anderen Daten
getrennt abzulegen, z.B. alle hintereinander am Ende. Mal sehen. Bei mehrfach vorkommenden
Paletten wäre so auch 5 oder 6 Bit Codierung evtl. gewinnbringend.
Der Aufwand, die effektivsten Methoden zu finden, wird deutlich größer, aber es würde sich lohnen.
Ich muss da anders herangehen, wohl erstmal für jeden Block die Palette bilden und doppelte bereits
kennzeichnen (wobei kleinere auch schon im Anfang von größeren enthalten sein können), und dann
mit der Kompression beginnen.
mov ax, 13h
int 10h

while vorne_frei do vor;
Antworten