www.pudn.com > Tank拊親蚔牁測鎢.rar > TILEUNIT.PAS


unit tileunit; 
 
interface 
 
uses SysUtils, Classes, Graphics, util; 
 
type 
  // 圖片屬性: 可以通過, 圖片可被打破, 子彈可以通過, 此圖片是軍旗 
  TTileAttr = set of (taCanPass, taCanBreak, taBulletCanPass, taFlag); 
   
  TTile = class // 單一圖片 
  private 
    FBits: TBitmap; // 存放圖片的 bitmap 
    FAttr: TTileAttr; // 屬性 
    FDisposed: Boolean; // 是否已棄置不用 
     
    FFirstTile: Boolean; // 是不是圖片群組裡的第一張圖片 
    FXNum, FYNum: Byte; // 圖片群組的橫向及縱向圖片數目 
  protected 
  public 
    constructor Create; 
    destructor Destroy; override; 
     
    // 載入及儲存圖片 
    procedure LoadFromStream(Stream: TStream); 
    procedure SaveToStream(Stream: TStream); 
     
    // 提供給外界存取的屬性 
    property Bitmap: TBitmap read FBits; 
    property Attr: TTileAttr read FAttr write FAttr; 
    property Disposed: Boolean read FDisposed write FDisposed; 
     
    property FirstTile: Boolean read FFirstTile write FFirstTile; 
    property xNum: Byte read FXNum write FXNum; 
    property yNum: Byte read FYNum write FYNum; 
  end; 
   
  TTiles = class // 圖庫 
  private 
    FTiles: array of TTile; // 所擁有的圖片陣列 
     
    function GetTileNum: Integer; // 圖片數目 
     
    function GetTile(No: Integer): TTile; // 利用索引取得圖片 
  protected 
  public 
    constructor Create; 
    destructor Destroy; override; 
     
    function AddTile(NewTile: TTile): Integer; // 加入新的圖片 
    procedure FreeTiles; // 釋放所有圖片 
     
    // 載入及儲存圖庫 
    procedure LoadFromFile(Filename: string); 
    procedure SaveToFile(Filename: string); 
     
    property TileNum: Integer read GetTileNum; 
    property Tile[No: Integer]: TTile read GetTile; default; // 預設陣列屬性 
  end; 
   
var 
  Tiles: TTiles; // 一個圖庫就夠了 
   
implementation 
 
constructor TTile.Create; 
begin 
  inherited Create; 
   
  // 儲放圖片的 bitmap, 大小為 TILE_WIDTH * TILE_HEIGHT 
  FBits := TBitmap.Create; 
  FBits.Width := TILE_WIDTH; 
  FBits.Height := tile_height; 
  FBits.Transparent := True; 
  FBits.TransparentColor := TRANSPARENT_COLOR; 
   
  // 預設為單張圖片形成一個群組 
  FFirstTile := True; 
  FXNum := 1; 
  FYNum := 1; 
end; 
 
destructor TTile.Destroy; 
begin 
  FBits.Free; 
   
  inherited Destroy; 
end; 
 
procedure TTile.LoadFromStream(Stream: TStream); 
begin 
  with Stream do 
  begin 
    read (FDisposed, sizeof(Boolean)); 
    // 是否已棄置不用 ?? 是的話就不再讀取其它屬性 
    if FDisposed then Exit; 
 
    FBits.LoadFromStream(Stream); // 圖形 
    read (FAttr, sizeof(TTileAttr)); // 屬性 
     
    read (FFirstTile, sizeof(Boolean)); 
     
    if FFirstTile then // 若是群組頭頭, 則讀取群組長寬 
    begin 
      read (FXNum, sizeof(Byte)); 
      read (FYNum, sizeof(Byte)); 
    end; 
  end; 
end; 
 
procedure TTile.SaveToStream(Stream: TStream); 
begin 
  with Stream do 
  begin 
    write (FDisposed, sizeof(Boolean)); 
    // 是否已棄置不用 ?? 是的話就不再寫入其它屬性 
    if FDisposed then Exit; 
     
    FBits.SaveToStream(Stream); // 圖形 
    write (FAttr, sizeof(TTileAttr)); // 屬性 
     
    write (FFirstTile, sizeof(Boolean)); 
     
    if FFirstTile then // 若是群組頭頭, 則寫入群組長寬 
    begin 
      write (FXNum, sizeof(Byte)); 
      write (FYNum, sizeof(Byte)); 
    end; 
  end; 
end; 
 
{ TTiles class } 
 
constructor TTiles.Create; 
begin 
  inherited Create; 
   
  SetLength(FTiles, 0); 
end; 
 
destructor TTiles.Destroy; 
begin 
  FreeTiles; 
   
  inherited Destroy; 
end; 
 
// 加入新圖片, 放在陣列最後 
function TTiles.AddTile(NewTile: TTile): Integer; 
begin 
  SetLength(FTiles, Length(FTiles) + 1); 
  FTiles[Length(FTiles) - 1] := NewTile; 
  Result := Length(FTiles) - 1; 
end; 
 
// 釋放所有圖片 
procedure TTiles.FreeTiles; 
var 
  I: Integer; 
begin 
  for I := 0 to Length(FTiles) - 1 do 
    FTiles[I].Free; 
  SetLength(FTiles, 0); 
end; 
 
// 從檔案讀取圖庫 
procedure TTiles.LoadFromFile(Filename: string); 
var 
  fs    : TFileStream; 
  I, Val: Integer;     
begin 
  fs := TFileStream.Create(Filename, fmOpenRead); 
  try 
    CheckSignature(fs, SIG_MYFILE); // 檢查檔頭標籤 
    CheckSignature(fs, ClassName); // 檢查副檔頭標籤 
     
    fs.read (Val, sizeof(Integer)); // 讀入 tiles 數目 
    if Val = 0 then 
      raise Exception.Create('No tiles'); 
     
    FreeTiles; 
    SetLength(FTiles, Val); 
     
    for I := 0 to Val - 1 do 
    begin 
      FTiles[I] := TTile.Create; 
      FTiles[I].LoadFromStream(fs); // 讀入所有 tiles 
    end; 
  finally 
    fs.Free; 
  end; 
end; 
 
// 寫入圖庫 
procedure TTiles.SaveToFile(Filename: string); 
var 
  fs: TFileStream; 
  S : string;      
  I : Integer;     
begin 
  fs := TFileStream.Create(Filename, fmCreate or fmOpenWrite); 
  try 
    fs.write (SIG_MYFILE, Length(SIG_MYFILE)); 
    S := ClassName; 
    fs.write (S[1], Length(S)); 
     
    I := TileNum; 
    fs.write (I, sizeof(Integer)); 
     
    for I := 0 to TileNum - 1 do 
      FTiles[I].SaveToStream(fs); // 寫入所有 tiles 
  finally 
    fs.Free; 
  end; 
end; 
 
function TTiles.GetTileNum: Integer; 
begin 
  Result := Length(FTiles); 
end; 
 
function TTiles.GetTile(No: Integer): TTile; 
begin 
  Result := FTiles[No]; 
end; 
 
end.