unit uTiledata;

interface

uses Classes, SysUtils, GR32, Dialogs, Graphics, Windows;

const   dBACKGROUND = $1;
        dWEAPON = $2;
        dTRANSPARENT = $4;
        dTRANSLUCENT = $8;
        dWALL = $10;
        dDAMAGING = $20;
        dIMPASSABLE = $40;
        dLIQUID = $80;

        dUNKNOWN1 = $100;
        dSURFACE = $200;
        dBRIDGE = $400;
        dGENERIC = $800;
        dWINDOW = $1000;
        dNOSHOOT = $2000;
        dA = $4000;
        dAN = $8000;

        dMONGEN = $10000;
        dFOLIAGE = $20000;
        dPARTIALHUE = $40000;
        dUNKNOWN2 = $80000;
        dMAP = $100000;
        dCONTAINER = $200000;
        dWEARABLE = $400000;
        dLIGHTSOURCE = $800000;

        dANIMATION = $1000000;
        dNODIAGONAL = $2000000;
        dUNKNOWN3 = $4000000;
        dARMOR = $8000000;
        dROOF = $10000000;
        dDOOR = $20000000;
        dSTAIRBACK = $40000000;
        dSTAIRRIGHT = $80000000;

type    TLandTileRecord = packed record
             Flags : longword;
             TexID : word;
             Name : array[0..19] of char;
        end;

        TStaticTileRecord = packed record
                Flags : Longword;
                Weight, Quality : Byte;
                Unknown1 : Word;
                Unknown2 : Byte;
                Quantity : Byte;
                AnimID : Word;
                Unknown3, Hue, Unknown4, Unknown5, Height : Byte;
                Name : array[0..19] of Char;
        end;

        TTiledata = class
        private
        mulStream : TMemoryStream;
        public
        Loaded : Boolean;
        constructor Create;
        destructor Free;
        procedure Load( FilePath : String );
        procedure Save( FilePath : String );
        function GetLandTile( Id : Integer ) : TLandTileRecord;
        function GetLandName( Id : Integer ) : String;
        function GetLandFlag( Id, Flag : Integer ) : Boolean;
        function GetCompleteLandFlag( Id : Integer ) : Integer;
        function GetLandTexId( Id : Integer ) : Integer;
        procedure SetLandTile( Id : Integer; LandTileRecord : TLandTileRecord );
        function GetStaticTile( Id : Integer ) : TStaticTileRecord;
        function GetStaticName( Id : Integer ) : String;
        function GetStaticAnimId( Id : Integer ) : Integer;
        function GetStaticHeight( Id : Integer ) : Integer;
        function GetStaticHue( Id : Integer ) : Integer;
        function GetStaticQuality( Id : Integer ) : Integer;
        function GetStaticQuantity( Id : Integer ) : Integer;
        function GetStaticWeight( Id : Integer ) : Integer;
        function GetStaticUnknown1( Id : Integer ) : Integer;
        function GetStaticUnknown2( Id : Integer ) : Integer;
        function GetStaticUnknown3( Id : Integer ) : Integer;
        function GetStaticUnknown4( Id : Integer ) : Integer;
        function GetStaticUnknown5( Id : Integer ) : Integer;
        function GetStaticFlag( Id, Flag : Integer ) : Boolean;
        procedure SetStaticTile( Id : Integer; StaticTileRecord : TStaticTileRecord );
        function AddFlag( Flag : Integer; Checked : Boolean ) : Integer;
        procedure SaveMapToFile( FilePath : String );
        procedure LoadMapFromFile( FilePath : String );
        procedure SaveStaticToFile( FilePath : String );
        procedure LoadStaticFromFile( FilePath : String );
        function GetStaticTileCount : Word;
        procedure FillStatics;
end;

var     Tiledata : TTiledata;

implementation

uses uUtilities, StrLib, uGaugeForm, uMulpatcher;

constructor TTiledata.Create;
begin
        mulStream := TMemoryStream.Create;
        Loaded := False;
end;

destructor TTiledata.Free;
begin
        mulStream.Free;
end;

procedure TTiledata.Load( FilePath : String );
begin
        mulStream.LoadFromFile( FilePath );
        Loaded := true;
end;

procedure TTiledata.Save( FilePath : String );
begin
        mulStream.SaveToFile( FilePath );
end;

function TTiledata.GetLandTile( Id : Integer ) : TLandTileRecord;
var     Pos : Integer;
begin
        Pos := ( Id div 32 )*4 + 4 + Id*sizeof( TLandTileRecord );
        mulStream.Seek( Pos, soFromBeginning );
        mulStream.Read( Result, sizeof( TLandTileRecord ) );
end;

function TTiledata.GetStaticTile( Id : Integer ) : TStaticTileRecord;
var     Pos : Integer;
begin
        Pos := 512*32*sizeof( TLandTileRecord ) + 512*4 + Id*sizeof( TStaticTileRecord ) + ( Id div 32 )*4 + 4;
        mulStream.Seek( Pos, soFromBeginning );
        mulStream.Read( Result, sizeof( TStaticTileRecord ) );
end;

function TTiledata.GetStaticTileCount : Word;
begin
        Result := ( mulStream.Size - 512*32*sizeof( TLandTileRecord ) - 512*4 ) div ( sizeof( TStaticTileRecord )*32 + 4 );
        Result := Result * 32;
end;

function TTiledata.GetLandName( Id : Integer ) : String;
var     LandTile : TLandTileRecord;
begin
        LandTile := GetLandTile( Id );
        Result := LandTile.Name;
end;

function TTiledata.GetStaticName( Id : Integer ) : String;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Name;
end;

function TTiledata.GetLandTexId( Id : Integer ) : Integer;
var     LandTile : TLandTileRecord;
begin
        LandTile := GetLandTile( Id );
        Result := LandTile.TexID;
end;

function TTiledata.GetStaticAnimId( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.AnimID;
end;

function TTiledata.GetStaticHeight( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Height;
end;

function TTiledata.GetStaticHue( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Hue;
end;

function TTiledata.GetStaticQuality( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Quality;
end;

function TTiledata.GetStaticQuantity( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Quantity;
end;

function TTiledata.GetStaticWeight( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Weight;
end;

function TTiledata.GetStaticUnknown1( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Unknown1;
end;

function TTiledata.GetStaticUnknown2( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Unknown2;
end;

function TTiledata.GetStaticUnknown3( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Unknown3;
end;

function TTiledata.GetStaticUnknown4( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Unknown4;
end;

function TTiledata.GetStaticUnknown5( Id : Integer ) : Integer;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := StaticTile.Unknown5;
end;

function TTiledata.GetLandFlag( Id, Flag : Integer ) : Boolean;
var     LandTile : TLandTileRecord;
begin
        LandTile := GetLandTile( Id );
        Result := ( LandTile.Flags and Flag ) = Flag;
end;

function TTiledata.GetCompleteLandFlag( Id : Integer ) : Integer;
var     LandTile : TLandTileRecord;
begin
        LandTile := GetLandTile( Id );
        Result := LandTile.Flags;
end;

function TTiledata.GetStaticFlag( Id, Flag : Integer ) : Boolean;
var     StaticTile : TStaticTileRecord;
begin
        StaticTile := GetStaticTile( Id );
        Result := ( StaticTile.Flags and Flag ) = Flag;
end;

procedure TTiledata.SetLandTile( Id : Integer; LandTileRecord : TLandTileRecord );
var     Pos : Integer;
begin
        Pos := ( Id div 32 )*4 + 4 + Id*sizeof( TLandTileRecord );
        mulStream.Seek( Pos, soFromBeginning );
        mulStream.Write( LandTileRecord, sizeof( TLandTileRecord ) );
end;

procedure TTiledata.SetStaticTile( Id : Integer; StaticTileRecord : TStaticTileRecord );
var     Pos : Integer;
begin
        Pos := 512*32*sizeof( TLandTileRecord ) + 512*4 + Id*sizeof( TStaticTileRecord ) + ( Id div 32 )*4 + 4;
        mulStream.Seek( Pos, soFromBeginning );
        mulStream.Write( StaticTileRecord, sizeof( TStaticTileRecord ) );
end;

function TTiledata.AddFlag( Flag : Integer; Checked : Boolean ) : Integer;
begin
        if Checked then
                Result := Flag
        else
                Result := 0;
end;

procedure TTiledata.SaveMapToFile( FilePath : String );
var     Datei : Textfile;
        Zeile : String;
        LandTile : TLandTileRecord;
        i : Integer;
begin
        AssignFile( Datei, FilePath );
        Rewrite( Datei );
        Write( Datei, 'ID	Name	TextureID	Unused	Unused	Transparent	Translucent	Block	Damage	Impassible	Wet	unknown1	Unused	Unused	Unused	Unused	Unused	Unused	Unused	Unused' );
        Writeln( Datei, '	Unused	Unused	unknown2	Unused	Unused	Unused	Unused	Unused	Unused	unknown3	Unused	Unused	Unused	Unused	Unused' );

        for i:=0 to $FFFF do begin
                LandTile := GetLandTile( i );
                Zeile := Format( '0x%x', [i] );
                Zeile := Zeile + Chr( VK_TAB ) + LandTile.Name;
                Zeile := Zeile + Chr( VK_TAB ) + Format( '0x%x', [LandTile.TexId] );

                if GetLandFlag( i, $1 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $2 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $4 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $8 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $10 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $20 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $40 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $80 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetLandFlag( i, $100 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $200 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $400 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $800 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $1000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $2000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $4000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $8000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetLandFlag( i, $10000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $20000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $40000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $80000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $100000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $200000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $400000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $800000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetLandFlag( i, $1000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $2000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $4000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $8000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $10000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $20000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $40000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetLandFlag( i, $80000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                Writeln( Datei, Zeile );
        end;
        CloseFile( Datei );
end;

procedure TTiledata.LoadMapFromFile( FilePath : String );
var     i, Id : Integer;
        Datei : Textfile;
        Zeile : String;
        Liste : TStringList;
        LandTile : TLandTileRecord;
begin
        AssignFile( Datei, FilePath );
        Reset( Datei );
        Readln( Datei, Zeile );

        for i:=0 to $FFFF do begin
                if eof( Datei ) then break;
                Readln( Datei, Zeile );

                Liste := TStringList.Create;
                StrLib.Split( Zeile, Chr( VK_TAB ), Liste );

                Id := strtoint( Liste[0] );
                StrPCopy( LandTile.Name, Liste[1] );
                LandTile.TexID := strtoint( Liste[2] );

                LandTile.Flags := 0;
                LandTile.Flags := LandTile.Flags + AddFlag( $1, Liste[3] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $2, Liste[4] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $4, Liste[5] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $8, Liste[6] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $10, Liste[7] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $20, Liste[8] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $40, Liste[9] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $80, Liste[10] = '1' );

                LandTile.Flags := LandTile.Flags + AddFlag( $100, Liste[11] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $200, Liste[12] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $400, Liste[13] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $800, Liste[14] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $1000, Liste[15] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $2000, Liste[16] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $4000, Liste[17] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $8000, Liste[18] = '1' );

                LandTile.Flags := LandTile.Flags + AddFlag( $10000, Liste[19] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $20000, Liste[20] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $40000, Liste[21] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $80000, Liste[22] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $100000, Liste[23] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $200000, Liste[24] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $400000, Liste[25] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $800000, Liste[26] = '1' );

                LandTile.Flags := LandTile.Flags + AddFlag( $1000000, Liste[27] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $2000000, Liste[28] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $4000000, Liste[29] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $8000000, Liste[30] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $10000000, Liste[31] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $20000000, Liste[32] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $40000000, Liste[33] = '1' );
                LandTile.Flags := LandTile.Flags + AddFlag( $80000000, Liste[34] = '1' );

                SetLandTile( Id, LandTile );
                Liste.Free;
        end;
        CloseFile( Datei );
end;

procedure TTiledata.SaveStaticToFile( FilePath : String );
var     Datei : Textfile;
        Zeile : String;
        StaticTile : TStaticTileRecord;
        i : Integer;
begin
        AssignFile( Datei, FilePath );
        Rewrite( Datei );
        Write( Datei, 'ID	Name	Weight/Quantity	Layer/Quality	Gump/AnimID	Height	Hue	Class/Quantity	unknown1	unknown2	unknown3	unknown4	Background	Weapon	Transparent	Translucent	Wall' );
        Write( Datei, '	Damage	Impassible	Wet	Unknow1	Surface	Bridge	Generic	Window	NoShoot	PrefixA	PrefixAn	Internal	Foliage	PartialHue	Unknow2	Map	Container/Height	Wearable	Lightsource' );
        Writeln( Datei, '	Animation	NotDiagonal	Unknow3	Armor	Roof	Door	StairBack	StairRight' );

        for i:=0 to GetStaticTileCount-1 do begin
                StaticTile := GetStaticTile( i );
                Zeile := Format( '0x%x', [i] );
                Zeile := Zeile + Chr( VK_TAB ) + StaticTile.Name;
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Weight );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Quality );
                Zeile := Zeile + Chr( VK_TAB ) + Format( '0x%x', [StaticTile.AnimId] );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Height );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Hue );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Quantity );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Unknown1 );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Unknown2 );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Unknown3 );
                Zeile := Zeile + Chr( VK_TAB ) + inttostr( StaticTile.Unknown4 );

                if GetStaticFlag( i, $1 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $2 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $4 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $8 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $10 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $20 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $40 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $80 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetStaticFlag( i, $100 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $200 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $400 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $800 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $1000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $2000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $4000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $8000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetStaticFlag( i, $10000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $20000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $40000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $80000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $100000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $200000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $400000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $800000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                if GetStaticFlag( i, $1000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $2000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $4000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $8000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $10000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $20000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $40000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';
                if GetStaticFlag( i, $80000000 ) then
                        Zeile := Zeile + Chr( VK_TAB ) + '1'
                else
                        Zeile := Zeile + Chr( VK_TAB ) + '0';

                Writeln( Datei, Zeile );
        end;
        CloseFile( Datei );
end;

procedure TTiledata.LoadStaticFromFile( FilePath : String );
var     i, Id, b : Integer;
        Zeile : String;
        Liste : TStringList;
        Datei : Textfile;
        StaticTile : TStaticTileRecord;
begin
        AssignFile( Datei, FilePath );
        Reset( Datei );
        ReadLn( Datei, Zeile );

        I := 0;

        while not Eof( Datei ) do begin
                try
                Readln( Datei, Zeile );
                Liste := TStringList.Create;
                StrLib.Split( Zeile, Chr( VK_TAB ), Liste );

                if Length( Liste[1] ) > 19 then begin
                        Liste[1] := Copy( Liste[1], 1, 19 );
                end;

                StrPCopy( StaticTile.Name, Liste[1] );
                Id := strtoint( Liste[0] );
                StaticTile.Weight := strtoint( Liste[2] );
                StaticTile.Quality := strtoint( Liste[3] );
                StaticTile.AnimID := strtoint( Liste[4] );
                StaticTile.Height := strtoint( Liste[5] );
                StaticTile.Hue := strtoint( Liste[6] );
                StaticTile.Quantity := strtoint( Liste[7] );
                StaticTile.Unknown1 := strtoint( Liste[8] );
                StaticTile.Unknown2 := strtoint( Liste[9] );
                StaticTile.Unknown3 := strtoint( Liste[10] );
                StaticTile.Unknown4 := strtoint( Liste[11] );


                StaticTile.Flags := 0;
                StaticTile.Flags := StaticTile.Flags + AddFlag( $1, Liste[12] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $2, Liste[13] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $4, Liste[14] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $8, Liste[15] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $10, Liste[16] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $20, Liste[17] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $40, Liste[18] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $80, Liste[19] = '1' );

                StaticTile.Flags := StaticTile.Flags + AddFlag( $100, Liste[20] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $200, Liste[21] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $400, Liste[22] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $800, Liste[23] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $1000, Liste[24] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $2000, Liste[25] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $4000, Liste[26] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $8000, Liste[27] = '1' );

                StaticTile.Flags := StaticTile.Flags + AddFlag( $10000, Liste[28] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $20000, Liste[29] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $40000, Liste[30] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $80000, Liste[31] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $100000, Liste[32] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $200000, Liste[33] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $400000, Liste[34] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $800000, Liste[35] = '1' );

                StaticTile.Flags := StaticTile.Flags + AddFlag( $1000000, Liste[36] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $2000000, Liste[37] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $4000000, Liste[38] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $8000000, Liste[39] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $10000000, Liste[40] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $20000000, Liste[41] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $40000000, Liste[42] = '1' );
                StaticTile.Flags := StaticTile.Flags + AddFlag( $80000000, Liste[43] = '1' );

                SetStaticTile( Id, StaticTile );
                Liste.Free;
                except
                        showmessage( 'Bug in Zeile: ' + inttostr( i+2 ) );
                end;
                Inc( I );
        end;
        CloseFile( Datei );
end;

procedure TTiledata.FillStatics;
var     I, J : Integer;
        StaticTile : TStaticTileRecord;
        Flag : Integer;
begin
        if not Loaded then exit;

        StaticTile.Flags := 0;
        StaticTile.Weight := 0;
        StaticTile.Quality := 0;
        StaticTile.Unknown1 := 0;
        StaticTile.Unknown2 := 0;
        StaticTile.Quantity := 0;
        StaticTile.AnimID := 0;
        StaticTile.Unknown3 := 0;
        StaticTile.Hue := 0;
        StaticTile.Unknown4 := 0;
        StaticTile.Unknown5 := 0;
        StaticTile.Height := 0;
        StrPCopy( StaticTile.Name, '' );

        Flag := 0;

        while GetStaticTileCount < $7FFF do begin
                mulStream.Seek( 0, soFromEnd );
                mulStream.Write( Flag, 4 );
                for J := 0 to 31 do begin
                        mulStream.Write( StaticTile, sizeof( TStaticTileRecord ) );
                end;
        end;
end;


end.
