Ok, I've been trying to get my head around using the zlib compression. These are the routines I've come up with, which are intened to turn arrays of bytes, ints and strings into compressed arrays (of bytes), and then back again. It seems to work here, but if someone who understands this properly could take a look, I'd be grateful.
Strict
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
' BYTES
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
Function CompressBytes:Byte[](Bytes:Byte[],CompressLevel=9)
Local length = Len(Bytes) * 2
Local Compressed:Byte[length]
Compressed[0] = Len(Bytes) & $FF
Compressed[1] = (Len(Bytes) Shr 8) & $FF
Compressed[2] = (Len(Bytes) Shr 16) & $FF
Local DataPointer:Byte Ptr
Local CompPointer:Byte Ptr
DataPointer = Bytes
CompPointer = Compressed
CompPointer :+ 3
compress2(CompPointer,length, DataPointer,Len(Bytes), CompressLevel)
Return Compressed[..(length-1+3)]
End Function
Function DecompressBytes:Byte[](Compressed:Byte[])
Local Size = Compressed[0] + (Compressed[1] Shl 8) + (Compressed[2] Shl 16)
Local length = Size+1
Local Uncompressed:Byte[length]
Local CompPointer:Byte Ptr
Local DataPointer:Byte Ptr
CompPointer = Compressed
CompPointer :+ 3
DataPointer = Uncompressed
uncompress(DataPointer,length, CompPointer,Len(Compressed))
Return Uncompressed[..(length-1)]
End Function
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
' INTS
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
Function CompressInts:Byte[](Ints:Int[],CompressLevel=9)
Local length = Len(Ints) * 6
Local Compressed:Byte[length]
Compressed[0] = Len(Ints) & $FF
Compressed[1] = (Len(Ints) Shr 8) & $FF
Compressed[2] = (Len(Ints) Shr 16) & $FF
Local DataPointer:Byte Ptr
Local CompPointer:Byte Ptr
DataPointer = Ints
CompPointer = Compressed
CompPointer :+ 3
compress2(CompPointer,length, DataPointer,Len(Ints) * 4, CompressLevel)
Return Compressed[..(length-1+3)]
End Function
Function DecompressInts:Int[](Compressed:Byte[])
Local Size = Compressed[0] + (Compressed[1] Shl 8) + (Compressed[2] Shl 16)
Local length = Size * 4
Local Uncompressed:Int[Size]
Local CompPointer:Byte Ptr
Local DataPointer:Byte Ptr
CompPointer = Compressed
CompPointer :+ 3
DataPointer = Uncompressed
uncompress(DataPointer,length, CompPointer,Len(Compressed))
Return Uncompressed
End Function
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
' STRINGS
'------------------------------------------------------------------------------
'------------------------------------------------------------------------------
Function CompressStrings:Byte[](Strings:String[],CompressLevel=9)
Local TotalSize = 2
TotalSize :+ Len(Strings) * 2
Local i:Int
For i = 0 To Len(Strings)-1
TotalSize :+ Len(Strings[i])
Next
Local StringsBank:TBank = CreateBank(TotalSize)
Local StringBankStream:TBankStream = CreateBankStream(StringsBank)
WriteShort StringBankStream, Len(Strings)
For i = 0 To Len(Strings)-1
WriteShort StringBankStream, Len(Strings[i])
WriteString StringBankStream, Strings[i]
Next
SeekStream StringBankStream,0
Local Byted:Byte[] = LoadStream(StringBankStream)
CloseStream(StringBankStream)
Return CompressBytes(Byted)
End Function
Function DecompressStrings:String[](Compressed:Byte[])
Local Byted:Byte[] = DecompressBytes(Compressed)
Local StrCount = Byted[0] + (Byted[1] Shl 8)
Local Strings:String[StrCount]
Local p = 2
Local i:Int, j:Int, Length:Int
For i = 0 To (StrCount-1)
Length = Byted[p] + (Byted[p+1] Shl 8)
p :+ 2
Strings[i] = ""
For j = 0 To (Length-1)
Strings[i] :+ Chr$(Byted[p+j])
Next
p :+ Length
Next
Return Strings
End Function
|