Image in Bank laden?

Übersicht BlitzBasic Beginners-Corner

Gehe zu Seite 1, 2  Weiter

Neue Antwort erstellen

 

Mathe

Betreff: Image in Bank laden?

BeitragMi, Aug 12, 2009 10:57
Antworten mit Zitat
Benutzer-Profile anzeigen
Hallo,

ich wollt mal fragen ob es möglich ist eine Imagedatei in eine Bank zuladen und dieses Bild, dann mit LoadImage(Bank) zuladen?

Eine Imagedatei in eine Bank zu laden wär ja kein Problem, aber wie kann ich dann die Imagedatei laden?

Code: [AUSKLAPPEN]
Local bank = CreateBank(FileSize("test.jpg"))
Local Image = ReadFile("test.jpg")
Repeat
   PokeByte (bank,x,ReadByte(Image))
   x=x+1
Until Eof(Image) = 1


Für was ich das brauche? Ich will eine kleines Videothekprogramm erstellen, mit Beschreibung zu einzelnen Filmen. Da will ich auch ein paar Bilder einfügen können, diese Bilder werden verschlüsselt in eine Datei geschrieben die vielleicht mal so ausschauen soll (Bin immer noch am überlegen wie ich es am besten machen soll.)
Ein Verschlüsselung hab ich mir schon ausgedacht, diese bringt es eigentlich überhaupt nicht, wollt halt nur mal testen ob es so funktioniert.
Code: [AUSKLAPPEN]
{Add NewFilm\
FilmName: "Filmname"
FilmLaenge:"95"
FilmBeschreibung:"....."
....
{Image\
hier die verschlüsselte Imagedatei.
}Image\
}Add NewFilm\

{Add NewFilm\
FilmName: "Film2"
FilmLaenge:"105"
FilmBeschreibung:"...."
...
{Image\
hier die verschlüsselte Imagedatei.
}Image\
}Add NewFilm\


Ich hoffe, dass ich mich verständlich ausgedrückt habe.

mfg.
Matthias
Windoof nein DANKE => ArchLinux Wink

ozzi789

BeitragMi, Aug 12, 2009 11:06
Antworten mit Zitat
Benutzer-Profile anzeigen
Hi Mathe

Afaik geht das nicht, ich habe er vorher probiert, das Ergebniss ist eine MAV.

Zur Lösung deines Problems:
Anstatt das Bild in eine Bank zu laden, schreibst du es in eine Datei, diese entschlüsselst du lädst sie, kopierst sie und löscht danach die entschlüsselte Datei.

Oder du schreibst dir ein eigenes Bildformat, und einen eigenen Loadimage Befehl.
Du schreibst die Farbwerte in eine Datei und danach wendest du Writepixelfast an.


mfg ozzi
0x2B || ! 0x2B
C# | C++13 | Java 7 | PHP 5

hazumu-kun

BeitragMi, Aug 12, 2009 11:22
Antworten mit Zitat
Benutzer-Profile anzeigen
Wieso denn so kompliziert?
Hol dir die ZLibAPI.dll und verschlüssel das bild und dann fügst du eine Referenz auf das Bild in deiner Videothek Datei ein und packst zum Schluss alles in ein Zip Archiv das du dann noch zur Tarnung umbenennen kannst.
Dann hast du nebenbei noch ne hübsche Kompression.
Warum kann es keine omnipotente Macht geben?
Weil diese omnipotente Macht in der Lage sein müsste, einen so schweren Stein zu schaffen, dass sie ihn nicht heben kann
-> nicht omnipotent
 

Mathe

BeitragMi, Aug 12, 2009 11:55
Antworten mit Zitat
Benutzer-Profile anzeigen
@ozzi789
ich hab mir schon gedacht, dass das nicht so einfach gehen wird.
So würde dann meine Functions ausschauen:
BlitzBasic: [AUSKLAPPEN]
Function Konvert_Image_to_MVTI(ImagePfad$)
Local ImageEndung$ = Right(ImagePfad,4)
Local Image = LoadImage(ImagePfad)
Local SaveMVTI = WriteFile(RequestFile("MVTI-Datei Speichern","",1,"")+".mvti")
DrawImage(Image,0,0)
Local IW = ImageWidth(Image)
Local IH = ImageHeight(Image)
WriteInt SaveMVTI,IW
WriteInt SaveMVTI,IH
For x = 0 To IW
For y = 0 To IH
RGBWert = ReadPixel (x,y)
WriteInt SaveMVTI,RGBWert
Next
Next
FreeImage Image
CloseFile SaveMVTI
Cls
End Function

Type MVTIImage
Field Bank
Field BankID
End Type

Function MVTI_LoadImage(MVTIImage$)
Local BankPos%
Local ImageSize% = FileSize(MVTIImage)
Local Image% = ReadFile(MVTIImage)
mi.MVTIImage = New MVTIImage
mi\Bank = CreateBank(ImageSize)
mi\BankID = Handle(mi.MVTIImage)
PokeInt (mi\Bank,BankPos,ReadInt(Image)) : BankPos=BankPos+4
PokeInt (mi\Bank,BankPos,ReadInt(Image)) : BankPos=BankPos+4
Repeat
PokeInt (mi\Bank,BankPos,ReadInt(Image))
BankPos = BankPos+4
Until Eof(Image) = 1
CloseFile(Image)
Return mi\BankID
End Function

Function MVTI_DrawImage(MVTIID,xx%=0,yy%=0)
Local BankPos
mi.MVTIImage = Object.MVTIImage(MVTIID)
Local IW = PeekInt(mi\Bank,BankPos) : BankPos=BankPos+4
Local IH = PeekInt(mi\Bank,BankPos) : BankPos=BankPos+4
LockBuffer BackBuffer()
For x = 0 To IW
For y = 0 To IH
WritePixel (x+xx,y+yy,PeekInt(mi\Bank,BankPos))
BankPos=BankPos+4
Next
Next
UnlockBuffer BackBuffer()
End Function

Function MVTI_FreeImage(MVTIID)
mi.MVTIImage = Object.MVTIImage(MVTIID)
FreeBank mi\Bank
Delete mi.MVTIImage
End Function

Function MVTI_ImageWidth(MVTIID)
mi.MVTIImage = Object.MVTIImage(MVTIID)
Local Width = PeekInt(mi\Bank,0)
Return Width
End Function

Function MVTI_ImageHeight(MVTIID)
mi.MVTIImage = Object.MVTIImage(MVTIID)
Local Height = PeekInt(mi\Bank,4)
Return Height
End Function


@viken_emesh
hmmm... so könnt ich es auch machen, aber ich glaub, dass bis ich das wieder rausbekomme wie das mit der ZLibAPI.dll funktioniert mit meiner Function schneller geht.
Windoof nein DANKE => ArchLinux Wink

ozzi789

BeitragMi, Aug 12, 2009 13:28
Antworten mit Zitat
Benutzer-Profile anzeigen
Mathe sieht schon gut aus
nur war das jetzt ne frage? Very Happy

mfg ozzi
0x2B || ! 0x2B
C# | C++13 | Java 7 | PHP 5
 

Mathe

BeitragMi, Aug 12, 2009 13:43
Antworten mit Zitat
Benutzer-Profile anzeigen
Ähm nicht wirklich mir ist, aber schon wieder was eingefallen.

So wenn ich jetzt mit meinen Konverter eine Datei erstellen, dann ist leider bei Bilder mit einer Auflösung 1920x1440 fast 11MB groß, wie kann ich diese Function noch optimieren, dass diese Datei nicht so groß wird.

Ich hät mir jetzt gedacht ich machs so:
Ich lese von einem Pixel die Farbe aus, schreibe diese dann in ein Typeregister plus X- & Y-Koordinaten. Wenn jetzt wieder eine Farbe ausgelesen wird, die den gleichen Farbanteil hat, wird für diese keine neues Typeregister angelegt sondern, die X- & Y-Koordinaten werden zu einen Typeregister hinzugefügt die, den gleichen Farbanteil habt.

Die MVTI-Datei würde dann so ausschauen:
Code: [AUSKLAPPEN]
{-1024525\
5,6,7,8,X-Koords,Y-Koords
}
{-1203493\
und hier das gleiche
}


Jetzt wollt ich mal fragen ob sich dieses Verfahren lohnen würde?

mfg.
Matthias
Windoof nein DANKE => ArchLinux Wink

ozzi789

BeitragMi, Aug 12, 2009 14:03
Antworten mit Zitat
Benutzer-Profile anzeigen
Lohnen tut sich alles solange die Datei kleiner wird Wink
Also was sich lohnt ist:

-am anfang reinschreiben wie gross die Datei in Pixeln ist, sodass du nicht immer die koordinaten sondern einfach nur farbwerte einträgst

-gleiche muster zusammenfast (also ein weisses rechteck mit 20 pixel höhe/länge wird zu einem byte mit dem wert 20 o.ä)

-du speicherst nur die unterschiede zum nächsten pixel
bsp:

O O_____Dieser Pixel ist 255,210,191
/___ Dieser Pixel ist 255,200,190

Dann würde das so aussehen
Pixel 1 = 255,210,191
Pixel 2 = 0,10,1 ;Differenz zu Pixel 1




Weis leider nicht allzu viel über Komprimierung aber im Netz hat es viel gutes
http://de.wikipedia.org/wiki/P..._Kodierung
http://de.wikipedia.org/wiki/LZ77

Besonders der ist für Quickbasic aber denn kann man mehr oder weniger einfach übertragen in BB (von EPS)
http://www.east-power-soft.de/...c_tuts_zip
0x2B || ! 0x2B
C# | C++13 | Java 7 | PHP 5

Xeres

Moderator

BeitragMi, Aug 12, 2009 14:11
Antworten mit Zitat
Benutzer-Profile anzeigen
Überdenke das mal logisch... du gibst jedem Farbwert zusätzlich 2 Koordinaten. Eigentlich kann das nur zur Speicherverdopplung führen. In der Realität musst du noch zusätzlich etwas dazu addieren, damit du weißt, wo die Koordinaten aufhören und wo ein Farbwert beginnt.
Win10 Prof.(x64)/Ubuntu 16.04|CPU 4x3Ghz (Intel i5-4590S)|RAM 8 GB|GeForce GTX 960
Wie man Fragen richtig stellt || "Es geht nicht" || Video-Tutorial: Sinus & Cosinus
T
HERE IS NO FAIR. THERE IS NO JUSTICE. THERE IS JUST ME. (Death, Discworld)
 

Mathe

BeitragMi, Aug 12, 2009 14:42
Antworten mit Zitat
Benutzer-Profile anzeigen
@ozzi789
Okey danke.

@Xeres
hmmm... ich hab zu wenig überlegt eigentlich ist ja logisch.
Windoof nein DANKE => ArchLinux Wink

faeX

BeitragMi, Aug 12, 2009 16:19
Antworten mit Zitat
Benutzer-Profile anzeigen
Du könntest natürlich auch ein Schema aus deinen Farben machen... z.B. 4 Bits pro Farbe (ARGB) macht nur 2 Bytes statt 4. Wenn du noch besser optimieren willst, kommst du nicht drum rum einzelne Bits zu speichern, und dafür müssten Bytes gesplittet werden... Meiner Meinung nach viel einfacher wäre folgendes:

- Du speicherst den Typ des Bildes in die Bank (*.jpg, o.ä....)
- Du speicherst die Anzahl der Bytes eines Bildes in deine Bank
- Dahinter kopierst du jedes Byte des Bildes und schreibst es in die Bank

Wenn du das Bild wieder öffnen willst:

- Lese den Typ aus der Bank aus
- Erstelle dir eine Datei mit der Endung (z.b. "Temp.jpg")
- Kopiere alle Bytes der Bank in die Datei
- Öffne das Bild mit LoadImage

Fertig Wink

EDIT 2. Klammer vor den Befehl gesetzt, damit er verlinkt wird.
 

Mathe

BeitragDo, Aug 13, 2009 9:44
Antworten mit Zitat
Benutzer-Profile anzeigen
faeX hat Folgendes geschrieben:
- Du speicherst den Typ des Bildes in die Bank (*.jpg, o.ä....)
- Du speicherst die Anzahl der Bytes eines Bildes in deine Bank
- Dahinter kopierst du jedes Byte des Bildes und schreibst es in die Bank

Wenn du das Bild wieder öffnen willst:

- Lese den Typ aus der Bank aus
- Erstelle dir eine Datei mit der Endung (z.b. "Temp.jpg")
- Kopiere alle Bytes der Bank in die Datei
- Öffne das Bild mit LoadImage


So was hab ich mir am Anfang auch gedacht. Ich find es halt ein wenig umständlich, aber ich glaube mir bleibt eh keine andere Möglichkeit.
Die einfachste Komprimierung die mir einfallen würde wäre, keinen Alphawert zu speichern. Das würde 1/4 vom Speicherbedarf ausmachen, aber die Bilddatei wären immer noch viel zu groß.

ozzi789 hat Folgendes geschrieben:
-gleiche muster zusammenfast (also ein weisses rechteck mit 20 pixel höhe/länge wird zu einem byte mit dem wert 20 o.ä)


Gestern hab ich mir hierzu noch einige Stunden lang den Kopf verbrochen. Mir ist bis jetzt immer noch keine passable Möglichkeit eingefallen wie ich das bewerkstelligen könnte.

mfg.
Matthias
Windoof nein DANKE => ArchLinux Wink

Chrise

BeitragDo, Aug 13, 2009 12:52
Antworten mit Zitat
Benutzer-Profile anzeigen
Vll sowas in der Art:
(Ist jetzt nur meine Überlegung kann auch sein dass es sowas von überhaupt nichts bringt)
Normalerweise speicherst du ja (indirekt den Ort) und alle dazugehörigen Farbwerte (+Alphawert)
Du könntest ja auch einen Pixel nehmen, den Farbwert lesen. Den Farbwert diesmal speichern und dann alle dazugehörigen Pixel in der selben Farbe speichern.
Also der Unterschied wäre dann von:
x,y,r,g,b,a
x,y,r,g,b,a
x,y,r,g,b,a
x,y,r,g,b,a
x,y,r,g,b,a
zu:
r,g,b,a:
x,y
x,y
x,y
x,y
...


Hoffe das kam so rüber wie ich mir das dachte Wink
Llama 1 Llama 2 Llama 3
Vielen Dank an Pummelie, der mir auf seinem Server einen Platz für LlamaNet bietet.

mpmxyz

BeitragDo, Aug 13, 2009 13:20
Antworten mit Zitat
Benutzer-Profile anzeigen
@Chrise
Deine Methode ist aber dennoch Unsinn, da man normalerweise die Position der Pixel nicht mitspeichert.
Und da du bei größeren Bildern 2 Shorts für jede Pixelposition brauchst, kannst du auch gleich alle Farbwerte für jeden Pixel mit 32 Bit angeben.

Die einzige Möglichkeit, die Bilder platzsparend zu speichern, ist wohl leider eine richtige Komprimierung.
Hier gab es irgendwo im Codearchiv eine Huffmancodierung.

Du könntest ja die Bytes, die dabei herauskommen, einfach in eine Zeile schreiben.
Du musst nur alle 13er (Chr(13)) und 10er (Chr(10)) durch irgendwelche 2 Bytes lange Konstruktionen, wie "&3" und "&1" ersetzen.
Zusätzlich brauchst du dann einen Ersatz für "&", da das ein Sonderzeichen kennzeichnet.
"&" könntest du z.B. mit "&&" darstellen.
So könntest du dein Bild komprimiert in einer Datei speichern.

mfG
mpmxyz

ozzi789

BeitragDo, Aug 13, 2009 14:07
Antworten mit Zitat
Benutzer-Profile anzeigen
Mathe hat Folgendes geschrieben:
ozzi789 hat Folgendes geschrieben:
-gleiche muster zusammenfast (also ein weisses rechteck mit 20 pixel höhe/länge wird zu einem byte mit dem wert 20 o.ä)


Gestern hab ich mir hierzu noch einige Stunden lang den Kopf verbrochen. Mir ist bis jetzt immer noch keine passable Möglichkeit eingefallen wie ich das bewerkstelligen könnte.

mfg.
Matthias


Pseudocode, falls nicht verständlich ist frag nur Wink


Code: [AUSKLAPPEN]
For x= 1 To 800
For y= 1 To 600
old=current
current=ReadPixel(x,y)

If old=current
;DA schreiben wir zmb ## und denn Farbwert der bei beiden Pixeln gleich ist
EndIf

If rgbold>rgb-10 And rgbold<rgb+10 ;hier haben wir den rgb wert berechnet, wenn die nicht mehr als 10 abweichen
;Sagen wir die 2 seien gleich!
EndIf ;Dies hat aber zur Folge das wir nicht mehr verlustlos Komprimieren!

Next
Next

DerHase

BeitragDo, Aug 13, 2009 14:57
Antworten mit Zitat
Benutzer-Profile anzeigen
Mach es Dir doch einfach und verzichte auf die Bank und sowas und benutz Al90s geniales Tool Wink
Play Satyr!
 

Mathe

BeitragSa, Aug 15, 2009 8:38
Antworten mit Zitat
Benutzer-Profile anzeigen
so wollt mich noch mal für eure Antworten bedanken.

@DerHase
mir ist es eigentlich darum gegangen was eigenes zusammen zu bekommen und nicht wieder von irgend jemanden das Programm zu benützen.

@Huffman Codierung?
Kann mir jemand da mal ganz kurz den Sinn dieser Codierung näher bringen?
Ich versteh z.B. bei Bildern nicht ganz wie ich sie hier ohne Verlust komprimieren kann.

Ich zähle von einer Bilddatei (800*600) wie oft jeder RGB-Wert vorkommt. Sagen wir mal in diesen Bild kommen 48.000 verschiedene Farbwerte vor. Das heißt das der längste Huffmancode wäre 48.000 Zeichen lang, aber für nur ein so ein Zeichen benötigt man schon 48000 KB und bei einem Bild dieser Auflösung hat man auch mehr Pixel nicht nur eins. Um genau zu hat dieses Bild 480.000 Pixel.

Ich hab so das gefühlt, dass ich dieses Verfahren voll falsch verstanden habe, den wenn ich mir das jetzt so überlege wär mein Speicherbedarf geringer, wenn ich einfach nur jeden RGB-Wert in eine Datei speichern würde.

Kann mich jemand mal aufklären?

mfg.
Matthias
Windoof nein DANKE => ArchLinux Wink

mpmxyz

BeitragSa, Aug 15, 2009 9:38
Antworten mit Zitat
Benutzer-Profile anzeigen
Für die Huffmancodierung zählt man erst einmal alle Byte-Werte der zu komprimierenden Daten.
Dann bekommen die häufigsten Werte ganz kurze Codes, z.B. welche mit 3 Bit Länge, und die selteneren Werte größere Codes, wie z.B. welche mit 16 Bit Länge.

Die Byte-Werte werden durch ihre entsprechenden Codes ersetzt und dadurch, dass die häufigeren Zeichen viel kleiner als normal sind wird die Datenmenge kleiner.
(Es gibt keine Lücken ohne Inhalt zwischen den neuen Bytes!)
Zu dieser Datenmenge muss aber noch angegeben werden, welcher Code welchem Wert entspricht.
Das wären aber maximal 255 Bytes. Das sollte bei den Bildern nicht so viel ausmachen, da sie wahrscheinlich trotzdem viel kleiner geworden sind.

Das war jetzt sehr grob, aber ich kenne diese Codierung nicht so genau.
Vielleicht kann es jemand anderes genauer erläutern.

mfG
mpmxyz

P.S.: *.zip-Dateien und *.png-Bilder nutzen übrigens auch eine solche Codierung.
Moin Moin!
Projekte: DBPC CodeCruncher Mandelbrot-Renderer
 

Mathe

BeitragSa, Aug 15, 2009 10:06
Antworten mit Zitat
Benutzer-Profile anzeigen
@mpmxyz
hmmm... das war mir eigentlich klar, aber ich hab bis jetzt gemeint wenn ich ein Int-Wert in eine Bank schreibe und hier dann vier Byte auslese ein scheiß raus kommt. Jetzt hab ich das mal ausprobiert und jetzt ist mir auch klar warum man da doch was sparen kann xD.
Ganz am Anfang wollt ich eigentlich die Wahrscheinlichkeit der einzelnen RGB-Werte in eine Datei schreiben und hab da gar nicht mehr an die Bytes gedacht. So jetzt weis ich auch wo mein Denkfehler war.

mfg.
Matthias
Windoof nein DANKE => ArchLinux Wink

Noobody

BeitragSa, Aug 15, 2009 10:30
Antworten mit Zitat
Benutzer-Profile anzeigen
In diesem Fall würde ich die Huffmanncodierung nur begrenzt empfehlen. Ein gewöhnliches Bild für deine Videothek wird wenig grössere gleichfarbige Flächen enthalten, sondern hat für gewöhnlich eine gleichstarke Verteilung aller Farben. Die Huffmancodierung ist aber dort am besten, wo man viele gleiche Werte hat, weswegen sie hier die Dateigrösse nur wenig verringern wird.

Du könntest dich stattdessen an der LZW-Kompression versuchen, welche beispielsweise in GIF verwendet wird. Das tolle an LZW ist nun, dass die Ausgabe viele gleiche Codes enthält, sprich, du kannst auf die Ausgabe der Kompression nochmal die Huffman-Kompression draufhauen und kannst so die Dateigrösse beachtlich verringern.
Man is the best computer we can put aboard a spacecraft ... and the only one that can be mass produced with unskilled labor. -- Wernher von Braun

Nicdel

BeitragSa, Aug 15, 2009 10:44
Antworten mit Zitat
Benutzer-Profile anzeigen
Bei der Huffmanncodierung ist außerdem zu beachten, dass die Dateien wegen ihrer Packmethode manchmal als Virus angesehen werden.
Desktop: Intel Pentium 4 2650 Mhz, 2 GB RAM, ATI Radeon HD 3850 512 MB, Windows XP
Notebook: Intel Core i7 720 QM 1.6 Ghz, 4 GB DDR3 RAM, nVidia 230M GT, Windows 7

Gehe zu Seite 1, 2  Weiter

Neue Antwort erstellen


Übersicht BlitzBasic Beginners-Corner

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group